@marimo-team/codemirror-sql
Advanced tools
@@ -77,3 +77,5 @@ import type { EditorState } from "@codemirror/state"; | ||
| */ | ||
| extractTableReferences(sql: string): Promise<string[]>; | ||
| extractTableReferences(sql: string, opts?: { | ||
| state: EditorState; | ||
| }): Promise<string[]>; | ||
| /** | ||
@@ -84,3 +86,5 @@ * Extracts column references from a SQL query using node-sql-parser | ||
| */ | ||
| extractColumnReferences(sql: string): Promise<string[]>; | ||
| extractColumnReferences(sql: string, opts?: { | ||
| state: EditorState; | ||
| }): Promise<string[]>; | ||
| } | ||
@@ -87,0 +91,0 @@ type CommentType = "--" | "/*"; |
@@ -1,1 +0,1 @@ | ||
| {"version":3,"file":"parser.d.ts","sourceRoot":"","sources":["../../src/sql/parser.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AACrD,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAU,MAAM,iBAAiB,CAAC;AAG3D,OAAO,KAAK,EAAE,aAAa,EAAE,cAAc,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAE3E,MAAM,WAAW,YAAa,SAAQ,MAAM;IAC1C,QAAQ,EAAE,iBAAiB,CAAC;IAC5B;;;;;;;;;;OAUG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;CAC1B;AAED,MAAM,WAAW,oBAAoB;IACnC,gBAAgB,CAAC,EAAE,CAAC,KAAK,EAAE,WAAW,KAAK,YAAY,CAAC;CACzD;AAED,MAAM,WAAW,mBAAoB,SAAQ,cAAc;IACzD,GAAG,CAAC,EAAE,GAAG,GAAG,GAAG,EAAE,CAAC;CACnB;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,qBAAa,aAAc,YAAW,SAAS;IAC7C,OAAO,CAAC,IAAI,CAAuB;IACnC,OAAO,CAAC,MAAM,CAAuB;IAGrC,OAAO,CAAC,YAAY,CAA8B;gBAEtC,IAAI,GAAE,oBAAyB;IAI3C;;OAEG;IACH,OAAO,CAAC,SAAS,CASd;IAEG,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,mBAAmB,CAAC;IA+B9E,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,YAAY,GAAG,OAAO,CAAC,MAAM,CAAC;IAS7E;;;OAGG;YACW,sBAAsB;IAmCpC;;;;;OAKG;IACH,OAAO,CAAC,gBAAgB;IA0DxB,OAAO,CAAC,iBAAiB;IASnB,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC;IAKtF;;;;OAIG;IACG,sBAAsB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;IAc5D;;;;OAIG;IACG,uBAAuB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;CAe9D;AAED,KAAK,WAAW,GAAG,IAAI,GAAG,IAAI,CAAC;AAE/B,iBAAS,uBAAuB,CAAC,GAAG,EAAE,MAAM,EAAE,YAAY,GAAE,WAAW,EAAiB,GAAG,MAAM,CA0BhG;AAID;;;;;;;;;;;;;GAaG;AACH,iBAAS,yBAAyB,CAAC,GAAG,EAAE,MAAM,GAAG;IAC/C,GAAG,EAAE,MAAM,CAAC;IACZ,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACtC,CAsBA;AAED,eAAO,MAAM,kBAAkB;;;CAAyD,CAAC;AAEzF;;;GAGG;AACH,MAAM,MAAM,iBAAiB,GACzB,QAAQ,GACR,UAAU,GACV,KAAK,GACL,MAAM,GACN,SAAS,GACT,OAAO,GACP,YAAY,GACZ,QAAQ,GACR,UAAU,GACV,QAAQ,GACR,aAAa,GACb,UAAU,GACV,WAAW,GACX,MAAM,CAAC"} | ||
| {"version":3,"file":"parser.d.ts","sourceRoot":"","sources":["../../src/sql/parser.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AACrD,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAU,MAAM,iBAAiB,CAAC;AAG3D,OAAO,KAAK,EAAE,aAAa,EAAE,cAAc,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAE3E,MAAM,WAAW,YAAa,SAAQ,MAAM;IAC1C,QAAQ,EAAE,iBAAiB,CAAC;IAC5B;;;;;;;;;;OAUG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;CAC1B;AAED,MAAM,WAAW,oBAAoB;IACnC,gBAAgB,CAAC,EAAE,CAAC,KAAK,EAAE,WAAW,KAAK,YAAY,CAAC;CACzD;AAED,MAAM,WAAW,mBAAoB,SAAQ,cAAc;IACzD,GAAG,CAAC,EAAE,GAAG,GAAG,GAAG,EAAE,CAAC;CACnB;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,qBAAa,aAAc,YAAW,SAAS;IAC7C,OAAO,CAAC,IAAI,CAAuB;IACnC,OAAO,CAAC,MAAM,CAAuB;IAGrC,OAAO,CAAC,YAAY,CAA8B;gBAEtC,IAAI,GAAE,oBAAyB;IAI3C;;OAEG;IACH,OAAO,CAAC,SAAS,CASd;IAEG,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,mBAAmB,CAAC;IA+B9E,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,YAAY,GAAG,OAAO,CAAC,MAAM,CAAC;IAS7E;;;OAGG;YACW,sBAAsB;IAmCpC;;;;;OAKG;IACH,OAAO,CAAC,gBAAgB;IA0DxB,OAAO,CAAC,iBAAiB;IASnB,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC;IAKtF;;;;OAIG;IACG,sBAAsB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;IAgB3F;;;;OAIG;IACG,uBAAuB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;CAiB7F;AAED,KAAK,WAAW,GAAG,IAAI,GAAG,IAAI,CAAC;AAE/B,iBAAS,uBAAuB,CAAC,GAAG,EAAE,MAAM,EAAE,YAAY,GAAE,WAAW,EAAiB,GAAG,MAAM,CA0BhG;AAID;;;;;;;;;;;;;GAaG;AACH,iBAAS,yBAAyB,CAAC,GAAG,EAAE,MAAM,GAAG;IAC/C,GAAG,EAAE,MAAM,CAAC;IACZ,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACtC,CAsBA;AAED,eAAO,MAAM,kBAAkB;;;CAAyD,CAAC;AAEzF;;;GAGG;AACH,MAAM,MAAM,iBAAiB,GACzB,QAAQ,GACR,UAAU,GACV,KAAK,GACL,MAAM,GACN,SAAS,GACT,OAAO,GACP,YAAY,GACZ,QAAQ,GACR,UAAU,GACV,QAAQ,GACR,aAAa,GACb,UAAU,GACV,WAAW,GACX,MAAM,CAAC"} |
@@ -180,6 +180,7 @@ import { debug } from "../debug.js"; | ||
| */ | ||
| async extractTableReferences(sql) { | ||
| async extractTableReferences(sql, opts) { | ||
| const parserOptions = opts ? this.opts.getParserOptions?.(opts.state) : undefined; | ||
| try { | ||
| const parser = await this.getParser(); | ||
| const tableList = parser.tableList(sql); | ||
| const tableList = parser.tableList(sql, parserOptions); | ||
| // Clean up table names - node-sql-parser returns format like "select::null::users" | ||
@@ -200,6 +201,7 @@ return tableList.map((table) => { | ||
| */ | ||
| async extractColumnReferences(sql) { | ||
| async extractColumnReferences(sql, opts) { | ||
| const parserOptions = opts?.state ? this.opts.getParserOptions?.(opts.state) : undefined; | ||
| try { | ||
| const parser = await this.getParser(); | ||
| const columnList = parser.columnList(sql); | ||
| const columnList = parser.columnList(sql, parserOptions); | ||
| // Clean up column names - node-sql-parser returns format like "select::null::users" | ||
@@ -206,0 +208,0 @@ const cleanColumnList = columnList.map((column) => { |
@@ -1,1 +0,1 @@ | ||
| {"version":3,"file":"parser.js","sourceRoot":"","sources":["../../src/sql/parser.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,EAAE,MAAM,aAAa,CAAC;AACpC,OAAO,EAAE,IAAI,EAAE,MAAM,aAAa,CAAC;AA2BnC;;;;;;;;;;;;;;;;;GAiBG;AACH,MAAM,OAAO,aAAa;IAChB,IAAI,CAAuB;IAC3B,MAAM,GAAkB,IAAI,CAAC;IAErC,gDAAgD;IACxC,YAAY,GAA2B,EAAE,CAAC;IAElD,YAAY,OAA6B,EAAE;QACzC,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;IACnB,CAAC;IAED;;OAEG;IACK,SAAS,GAAG,IAAI,CAAC,KAAK,IAAI,EAAE;QAClC,IAAI,IAAI,CAAC,MAAM,EAAE,CAAC;YAChB,OAAO,IAAI,CAAC,MAAM,CAAC;QACrB,CAAC;QACD,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,iBAAiB,CAAC,CAAC;QAC/C,0BAA0B;QAC1B,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,CAAC,OAAO,IAAI,MAAM,CAAC;QAC5C,IAAI,CAAC,MAAM,GAAG,IAAI,MAAM,EAAE,CAAC;QAC3B,OAAO,IAAI,CAAC,MAAM,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH,KAAK,CAAC,KAAK,CAAC,GAAW,EAAE,IAA4B;QACnD,qCAAqC;QACrC,IAAI,CAAC,YAAY,GAAG,EAAE,CAAC;QAEvB,MAAM,aAAa,GAAG,IAAI,CAAC,IAAI,CAAC,gBAAgB,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC/D,MAAM,YAAY,GAAG,MAAM,IAAI,CAAC,WAAW,CAAC,GAAG,EAAE,aAAa,CAAC,CAAC;QAEhE,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,EAAE,CAAC;YAEtC,8DAA8D;YAC9D,IAAI,aAAa,EAAE,QAAQ,KAAK,QAAQ,EAAE,CAAC;gBACzC,OAAO,IAAI,CAAC,sBAAsB,CAAC,YAAY,EAAE,aAAa,CAAC,CAAC;YAClE,CAAC;YAED,MAAM,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,YAAY,EAAE,aAAa,CAAC,CAAC;YAEvD,OAAO;gBACL,OAAO,EAAE,IAAI;gBACb,MAAM,EAAE,EAAE;gBACV,GAAG;aACJ,CAAC;QACJ,CAAC;QAAC,OAAO,KAAc,EAAE,CAAC;YACxB,MAAM,UAAU,GAAG,IAAI,CAAC,gBAAgB,CAAC,KAAK,EAAE,YAAY,CAAC,CAAC;YAC9D,OAAO;gBACL,OAAO,EAAE,KAAK;gBACd,MAAM,EAAE,CAAC,UAAU,CAAC;aACrB,CAAC;QACJ,CAAC;IACH,CAAC;IAED,KAAK,CAAC,WAAW,CAAC,GAAW,EAAE,aAA4B;QACzD,IAAI,aAAa,EAAE,cAAc,EAAE,CAAC;YAClC,MAAM,EAAE,GAAG,EAAE,WAAW,EAAE,YAAY,EAAE,GAAG,yBAAyB,CAAC,GAAG,CAAC,CAAC;YAC1E,IAAI,CAAC,YAAY,GAAG,YAAY,CAAC;YACjC,OAAO,WAAW,CAAC;QACrB,CAAC;QACD,OAAO,GAAG,CAAC;IACb,CAAC;IAED;;;OAGG;IACK,KAAK,CAAC,sBAAsB,CAClC,GAAW,EACX,aAAqB;QAErB,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,EAAE,CAAC;QAEtC,qDAAqD;QACrD,MAAM,UAAU,GAAG,uBAAuB,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,CAAC,WAAW,EAAE,CAAC;QAE1E,4CAA4C;QAC5C,IAAI,UAAU,CAAC,UAAU,CAAC,MAAM,CAAC,IAAI,UAAU,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC;YAClE,KAAK,CAAC,2BAA2B,CAAC,CAAC;YACnC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;QACvC,CAAC;QAED,IAAI,WAAW,GAAG,GAAG,CAAC;QACtB,2DAA2D;QAC3D,IAAI,UAAU,CAAC,QAAQ,CAAC,yBAAyB,CAAC,EAAE,CAAC;YACnD,MAAM,MAAM,GAAG,yBAAyB,CAAC,MAAM,GAAG,cAAc,CAAC,MAAM,CAAC;YACxE,IAAI,CAAC,YAAY,CAAC,GAAG,CAAC,OAAO,CAAC,yBAAyB,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC;YACpE,WAAW,GAAG,GAAG,CAAC,OAAO,CAAC,0BAA0B,EAAE,cAAc,CAAC,CAAC;QACxE,CAAC;QAED,+CAA+C;QAC/C,IAAI,CAAC;YACH,MAAM,eAAe,GAAG,EAAE,GAAG,aAAa,EAAE,QAAQ,EAAE,YAAY,EAAE,CAAC;YACrE,MAAM,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,WAAW,EAAE,eAAe,CAAC,CAAC;YACxD,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC;QAC5C,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,0DAA0D;YAC1D,MAAM,UAAU,GAAG,IAAI,CAAC,gBAAgB,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC;YACrD,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC,UAAU,CAAC,EAAE,CAAC;QAClD,CAAC;IACH,CAAC;IAED;;;;;OAKG;IACK,gBAAgB,CAAC,KAAc,EAAE,GAAW;QAClD,IAAI,IAAI,GAAG,CAAC,CAAC;QACb,IAAI,MAAM,GAAG,CAAC,CAAC;QACf,MAAM,OAAO,GAAI,KAAe,EAAE,OAAO,IAAI,mBAAmB,CAAC;QAEjE,MAAM,QAAQ,GAAG,KAGhB,CAAC;QACF,IAAI,QAAQ,EAAE,QAAQ,EAAE,CAAC;YACvB,IAAI,GAAG,QAAQ,CAAC,QAAQ,CAAC,KAAK,EAAE,IAAI,IAAI,CAAC,CAAC;YAC1C,MAAM,GAAG,QAAQ,CAAC,QAAQ,CAAC,KAAK,EAAE,MAAM,IAAI,CAAC,CAAC;QAChD,CAAC;aAAM,IAAI,QAAQ,EAAE,IAAI,EAAE,CAAC;YAC1B,IAAI,GAAG,QAAQ,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC,CAAC;YAC/B,MAAM,GAAG,QAAQ,CAAC,IAAI,CAAC,GAAG,EAAE,YAAY,IAAI,CAAC,CAAC;QAChD,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,GAAG,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC;YAC/C,MAAM,WAAW,GAAG,OAAO,CAAC,KAAK,CAAC,eAAe,CAAC,CAAC;YAEnD,IAAI,SAAS,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;gBACnB,IAAI,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YACpC,CAAC;YACD,IAAI,WAAW,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;gBACrB,MAAM,GAAG,QAAQ,CAAC,WAAW,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YACxC,CAAC;QACH,CAAC;QAED;;;;;;;;;;;WAWG;QACH,KAAK,MAAM,CAAC,QAAQ,EAAE,MAAM,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,YAAY,CAAC,EAAE,CAAC;YACnE,IAAI,MAAM,GAAG,QAAQ,CAAC,QAAQ,EAAE,EAAE,CAAC,EAAE,CAAC;gBACpC,MAAM,IAAI,MAAM,CAAC;YACnB,CAAC;QACH,CAAC;QAED,wCAAwC;QACxC,IAAI,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,CAAC;YACxB,MAAM,GAAG,GAAG,CAAC,MAAM,CAAC;QACtB,CAAC;QAED,OAAO;YACL,OAAO,EAAE,IAAI,CAAC,iBAAiB,CAAC,OAAO,CAAC;YACxC,IAAI,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC;YACvB,MAAM,EAAE,MAAM;YACd,QAAQ,EAAE,OAAgB;SAC3B,CAAC;IACJ,CAAC;IAEO,iBAAiB,CAAC,OAAe;QACvC,OAAO,OAAO;aACX,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC;aACvB,OAAO,CAAC,6BAA6B,EAAE,CAAC,KAAK,EAAE,EAAE,CAChD,KAAK,CAAC,OAAO,CAAC,cAAc,EAAE,wBAAwB,CAAC,CACxD;aACA,IAAI,EAAE,CAAC;IACZ,CAAC;IAED,KAAK,CAAC,WAAW,CAAC,GAAW,EAAE,IAA4B;QACzD,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC;QAC3C,OAAO,MAAM,CAAC,MAAM,CAAC;IACvB,CAAC;IAED;;;;OAIG;IACH,KAAK,CAAC,sBAAsB,CAAC,GAAW;QACtC,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,EAAE,CAAC;YACtC,MAAM,SAAS,GAAG,MAAM,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC;YACxC,mFAAmF;YACnF,OAAO,SAAS,CAAC,GAAG,CAAC,CAAC,KAAa,EAAE,EAAE;gBACrC,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;gBAChC,OAAO,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,IAAI,KAAK,CAAC;YAC1C,CAAC,CAAC,CAAC;QACL,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,EAAE,CAAC;QACZ,CAAC;IACH,CAAC;IAED;;;;OAIG;IACH,KAAK,CAAC,uBAAuB,CAAC,GAAW;QACvC,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,SAAS,EAAE,CAAC;YACtC,MAAM,UAAU,GAAG,MAAM,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;YAE1C,oFAAoF;YACpF,MAAM,eAAe,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC,MAAc,EAAE,EAAE;gBACxD,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;gBACjC,OAAO,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,IAAI,MAAM,CAAC;YAC3C,CAAC,CAAC,CAAC;YACH,OAAO,eAAe,CAAC;QACzB,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,EAAE,CAAC;QACZ,CAAC;IACH,CAAC;CACF;AAID,SAAS,uBAAuB,CAAC,GAAW,EAAE,eAA8B,CAAC,IAAI,EAAE,IAAI,CAAC;IACtF,MAAM,aAAa,GAAa,EAAE,CAAC;IAEnC,sBAAsB;IACtB,IAAI,YAAY,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;QAChC,aAAa,CAAC,IAAI,CAAC,oBAAoB,CAAC,CAAC;IAC3C,CAAC;IACD,uBAAuB;IACvB,IAAI,YAAY,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;QAChC,aAAa,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;IAClC,CAAC;IAED,IAAI,aAAa,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,GAAG,CAAC;IAE3C,MAAM,YAAY,GAAG,IAAI,MAAM,CAAC,SAAS,aAAa,CAAC,IAAI,CAAC,GAAG,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC;IAE7E,gEAAgE;IAChE,IAAI,MAAM,GAAG,GAAG,CAAC;IACjB,IAAI,UAAU,GAAG,EAAE,CAAC;IAEpB,OAAO,MAAM,KAAK,UAAU,EAAE,CAAC;QAC7B,UAAU,GAAG,MAAM,CAAC;QACpB,MAAM,GAAG,MAAM,CAAC,OAAO,CAAC,YAAY,EAAE,EAAE,CAAC,CAAC;IAC5C,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,MAAM,YAAY,GAAG,IAAI,CAAC,MAAM,CAAC;AAEjC;;;;;;;;;;;;;GAaG;AACH,SAAS,yBAAyB,CAAC,GAAW;IAI5C,MAAM,YAAY,GAA2B,EAAE,CAAC;IAEhD,MAAM,WAAW,GAAG,GAAG,CAAC,OAAO,CAC7B,sDAAsD,EACtD,CAAC,KAAK,EAAE,YAAY,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,EAAE,EAAE;QACrD,2CAA2C;QAC3C,IAAI,YAAY,IAAI,YAAY,EAAE,CAAC;YACjC,OAAO,KAAK,CAAC;QACf,CAAC;QAED,oDAAoD;QACpD,IAAI,OAAO,EAAE,CAAC;YACZ,YAAY,CAAC,MAAM,CAAC,GAAG,YAAY,CAAC;YACpC,OAAO,IAAI,OAAO,GAAG,CAAC;QACxB,CAAC;QAED,OAAO,KAAK,CAAC;IACf,CAAC,CACF,CAAC;IAEF,OAAO,EAAE,GAAG,EAAE,WAAW,EAAE,YAAY,EAAE,CAAC;AAC5C,CAAC;AAED,MAAM,CAAC,MAAM,kBAAkB,GAAG,EAAE,yBAAyB,EAAE,uBAAuB,EAAE,CAAC","sourcesContent":["import type { EditorState } from \"@codemirror/state\";\nimport type { AST, Option, Parser } from \"node-sql-parser\";\nimport { debug } from \"../debug.js\";\nimport { lazy } from \"../utils.js\";\nimport type { SqlParseError, SqlParseResult, SqlParser } from \"./types.js\";\n\nexport interface ParserOption extends Option {\n database: SupportedDialects;\n /**\n * If true, the parser will quote brackets in the SQL query which will satisfy the parser.\n * This is useful if you want to interpolate variables in f-strings.\n *\n * @example\n * ```sql\n * SELECT {id} -> SELECT '{id}'\n * ```\n *\n * @experimental This is an experimental feature and may break parsing.\n */\n ignoreBrackets?: boolean;\n}\n\nexport interface NodeSqlParserOptions {\n getParserOptions?: (state: EditorState) => ParserOption;\n}\n\nexport interface NodeSqlParserResult extends SqlParseResult {\n ast?: AST | AST[];\n}\n\n/**\n * A SQL parser wrapper around node-sql-parser with enhanced error handling\n * and validation capabilities for CodeMirror integration.\n *\n * @example Custom dialect\n * ```ts\n * import { NodeSqlParser } from \"@marimo-team/codemirror-sql\";\n *\n * const myParser = new NodeSqlParser({\n * getParserOptions: (state) => ({\n * dialect: getDialect(state),\n * parseOptions: {\n * includeLocations: true,\n * },\n * }),\n * });\n * ```\n */\nexport class NodeSqlParser implements SqlParser {\n private opts: NodeSqlParserOptions;\n private parser: Parser | null = null;\n\n // Record the column number to the offset amount\n private offsetRecord: Record<number, number> = {};\n\n constructor(opts: NodeSqlParserOptions = {}) {\n this.opts = opts;\n }\n\n /**\n * Lazy import of the node-sql-parser package and create a new Parser instance.\n */\n private getParser = lazy(async () => {\n if (this.parser) {\n return this.parser;\n }\n const module = await import(\"node-sql-parser\");\n // Support for ESM and CJS\n const { Parser } = module.default || module;\n this.parser = new Parser();\n return this.parser;\n });\n\n async parse(sql: string, opts: { state: EditorState }): Promise<NodeSqlParserResult> {\n // Reset the offset map on each parse\n this.offsetRecord = {};\n\n const parserOptions = this.opts.getParserOptions?.(opts.state);\n const sanitizedSql = await this.sanitizeSql(sql, parserOptions);\n\n try {\n const parser = await this.getParser();\n\n // Check if this is DuckDB dialect and apply custom processing\n if (parserOptions?.database === \"DuckDB\") {\n return this.parseWithDuckDBSupport(sanitizedSql, parserOptions);\n }\n\n const ast = parser.astify(sanitizedSql, parserOptions);\n\n return {\n success: true,\n errors: [],\n ast,\n };\n } catch (error: unknown) {\n const parseError = this.extractErrorInfo(error, sanitizedSql);\n return {\n success: false,\n errors: [parseError],\n };\n }\n }\n\n async sanitizeSql(sql: string, parserOptions?: ParserOption): Promise<string> {\n if (parserOptions?.ignoreBrackets) {\n const { sql: replacedSql, offsetRecord } = replaceBracketsWithQuotes(sql);\n this.offsetRecord = offsetRecord;\n return replacedSql;\n }\n return sql;\n }\n\n /**\n * Parse SQL with DuckDB syntax support\n * This is not robust, we catch main cases.\n */\n private async parseWithDuckDBSupport(\n sql: string,\n parserOptions: Option,\n ): Promise<NodeSqlParserResult> {\n const parser = await this.getParser();\n\n // Remove comments and normalize for pattern checking\n const sqlToCheck = removeCommentsFromStart(sql).trimStart().toLowerCase();\n\n // Handle unsupported DuckDB syntax patterns\n if (sqlToCheck.startsWith(\"from\") || sqlToCheck.includes(\"macro\")) {\n debug(\"Unsupported DuckDB syntax\");\n return { success: true, errors: [] };\n }\n\n let modifiedSql = sql;\n // Postgres does not support `CREATE OR REPLACE` for tables\n if (sqlToCheck.includes(\"create or replace table\")) {\n const offset = \"create or replace table\".length - \"create table\".length;\n this.offsetRecord[sql.indexOf(\"create or replace table\")] = -offset;\n modifiedSql = sql.replace(/create or replace table/i, \"create table\");\n }\n\n // Try standard parsing with PostgreSQL dialect\n try {\n const postgresOptions = { ...parserOptions, database: \"PostgreSQL\" };\n const ast = parser.astify(modifiedSql, postgresOptions);\n return { success: true, errors: [], ast };\n } catch (error) {\n // Use the original sql since we manually apply the offset\n const parseError = this.extractErrorInfo(error, sql);\n return { success: false, errors: [parseError] };\n }\n }\n\n /**\n * @param error - The error object\n * @param sql - The SQL string\n * @param offset - The offset to add to the column position. Default is 0.\n * @returns The parsed error information\n */\n private extractErrorInfo(error: unknown, sql: string): SqlParseError {\n let line = 1;\n let column = 1;\n const message = (error as Error)?.message || \"SQL parsing error\";\n\n const errorObj = error as {\n location?: { start?: { line: number; column: number } };\n hash?: { line: number; loc?: { first_column: number } };\n };\n if (errorObj?.location) {\n line = errorObj.location.start?.line || 1;\n column = errorObj.location.start?.column || 1;\n } else if (errorObj?.hash) {\n line = errorObj.hash.line || 1;\n column = errorObj.hash.loc?.first_column || 1;\n } else {\n const lineMatch = message.match(/line (\\d+)/i);\n const columnMatch = message.match(/column (\\d+)/i);\n\n if (lineMatch?.[1]) {\n line = parseInt(lineMatch[1], 10);\n }\n if (columnMatch?.[1]) {\n column = parseInt(columnMatch[1], 10);\n }\n }\n\n /**\n * Add offset to the column position to get the correct position of the error\n * SELECT {id} FRO users\n * ^ error position should be here\n *\n * SELECT {id} FRO users\n * ^ user sees this\n * So in this case, we subtract the offset from the column position.\n *\n * If the error is before the brackets, we don't need to add the offset because it just increases the string length\n * Column position will be the same as the user sees.\n */\n for (const [position, offset] of Object.entries(this.offsetRecord)) {\n if (column > parseInt(position, 10)) {\n column -= offset;\n }\n }\n\n // Ensure we don't exceed the sql length\n if (column > sql.length) {\n column = sql.length;\n }\n\n return {\n message: this.cleanErrorMessage(message),\n line: Math.max(1, line),\n column: column,\n severity: \"error\" as const,\n };\n }\n\n private cleanErrorMessage(message: string): string {\n return message\n .replace(/^Error: /, \"\")\n .replace(/Expected .* but .* found\\./i, (match) =>\n match.replace(/but .* found/, \"found unexpected token\"),\n )\n .trim();\n }\n\n async validateSql(sql: string, opts: { state: EditorState }): Promise<SqlParseError[]> {\n const result = await this.parse(sql, opts);\n return result.errors;\n }\n\n /**\n * Extracts table references from a SQL query using node-sql-parser\n * @param sql The SQL query to analyze\n * @returns Array of table names referenced in the query\n */\n async extractTableReferences(sql: string): Promise<string[]> {\n try {\n const parser = await this.getParser();\n const tableList = parser.tableList(sql);\n // Clean up table names - node-sql-parser returns format like \"select::null::users\"\n return tableList.map((table: string) => {\n const parts = table.split(\"::\");\n return parts[parts.length - 1] || table;\n });\n } catch {\n return [];\n }\n }\n\n /**\n * Extracts column references from a SQL query using node-sql-parser\n * @param sql The SQL query to analyze\n * @returns Array of column names referenced in the query\n */\n async extractColumnReferences(sql: string): Promise<string[]> {\n try {\n const parser = await this.getParser();\n const columnList = parser.columnList(sql);\n\n // Clean up column names - node-sql-parser returns format like \"select::null::users\"\n const cleanColumnList = columnList.map((column: string) => {\n const parts = column.split(\"::\");\n return parts[parts.length - 1] || column;\n });\n return cleanColumnList;\n } catch {\n return [];\n }\n }\n}\n\ntype CommentType = \"--\" | \"/*\";\n\nfunction removeCommentsFromStart(sql: string, commentTypes: CommentType[] = [\"/*\", \"--\"]): string {\n const regexPatterns: string[] = [];\n\n // Multi-line comments\n if (commentTypes.includes(\"/*\")) {\n regexPatterns.push(\"/\\\\*[\\\\s\\\\S]*?\\\\*/\");\n }\n // Single-line comments\n if (commentTypes.includes(\"--\")) {\n regexPatterns.push(\"--[^\\\\n]*\");\n }\n\n if (regexPatterns.length === 0) return sql;\n\n const commentRegex = new RegExp(`^\\\\s*(${regexPatterns.join(\"|\")})\\\\s*`, \"\");\n\n // Keep removing comments from the start until no more are found\n let result = sql;\n let prevResult = \"\";\n\n while (result !== prevResult) {\n prevResult = result;\n result = result.replace(commentRegex, \"\");\n }\n\n return result;\n}\n\nconst QUOTE_LENGTH = \"''\".length;\n\n/**\n * Replaces unquoted curly bracket expressions (e.g., {id}) with quoted strings (e.g., '{id}'),\n * ignoring brackets already inside single or double quotes.\n *\n * Returns the modified SQL and a record mapping the index of each replaced bracket to the\n * number of characters added (for offset tracking).\n *\n * @example\n * replaceBracketsWithQuotes(\"SELECT {id}, '{name}' FROM users\");\n * // => {\n * // sql: \"SELECT '{id}', '{name}' FROM users\",\n * // offsetRecord: { 7: 2 }\n * // }\n */\nfunction replaceBracketsWithQuotes(sql: string): {\n sql: string;\n offsetRecord: Record<number, number>;\n} {\n const offsetRecord: Record<number, number> = {};\n\n const replacedSql = sql.replace(\n /(\"(?:[^\"\\\\]|\\\\.)*\")|('(?:[^'\\\\]|\\\\.)*')|(\\{[^}]*\\})/g,\n (match, doubleQuoted, singleQuoted, bracket, offset) => {\n // If it's a quoted string, return it as-is\n if (doubleQuoted || singleQuoted) {\n return match;\n }\n\n // If it's a bracket, quote it and record the offset\n if (bracket) {\n offsetRecord[offset] = QUOTE_LENGTH;\n return `'${bracket}'`;\n }\n\n return match;\n },\n );\n\n return { sql: replacedSql, offsetRecord };\n}\n\nexport const exportedForTesting = { replaceBracketsWithQuotes, removeCommentsFromStart };\n\n/**\n * https://github.com/taozhi8833998/node-sql-parser?tab=readme-ov-file#supported-database-sql-syntax\n * While DuckDB is not supported in the library, we perform some special handling for it and treat it as PostgreSQL.\n */\nexport type SupportedDialects =\n | \"Athena\"\n | \"BigQuery\"\n | \"DB2\"\n | \"Hive\"\n | \"MariaDB\"\n | \"MySQL\"\n | \"PostgreSQL\"\n | \"DuckDB\"\n | \"Redshift\"\n | \"Sqlite\"\n | \"TransactSQL\"\n | \"FlinkSQL\"\n | \"Snowflake\"\n | \"Noql\";\n"]} | ||
| {"version":3,"file":"parser.js","sourceRoot":"","sources":["../../src/sql/parser.ts"],"names":[],"mappings":"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","sourcesContent":["import type { EditorState } from \"@codemirror/state\";\nimport type { AST, Option, Parser } from \"node-sql-parser\";\nimport { debug } from \"../debug.js\";\nimport { lazy } from \"../utils.js\";\nimport type { SqlParseError, SqlParseResult, SqlParser } from \"./types.js\";\n\nexport interface ParserOption extends Option {\n database: SupportedDialects;\n /**\n * If true, the parser will quote brackets in the SQL query which will satisfy the parser.\n * This is useful if you want to interpolate variables in f-strings.\n *\n * @example\n * ```sql\n * SELECT {id} -> SELECT '{id}'\n * ```\n *\n * @experimental This is an experimental feature and may break parsing.\n */\n ignoreBrackets?: boolean;\n}\n\nexport interface NodeSqlParserOptions {\n getParserOptions?: (state: EditorState) => ParserOption;\n}\n\nexport interface NodeSqlParserResult extends SqlParseResult {\n ast?: AST | AST[];\n}\n\n/**\n * A SQL parser wrapper around node-sql-parser with enhanced error handling\n * and validation capabilities for CodeMirror integration.\n *\n * @example Custom dialect\n * ```ts\n * import { NodeSqlParser } from \"@marimo-team/codemirror-sql\";\n *\n * const myParser = new NodeSqlParser({\n * getParserOptions: (state) => ({\n * dialect: getDialect(state),\n * parseOptions: {\n * includeLocations: true,\n * },\n * }),\n * });\n * ```\n */\nexport class NodeSqlParser implements SqlParser {\n private opts: NodeSqlParserOptions;\n private parser: Parser | null = null;\n\n // Record the column number to the offset amount\n private offsetRecord: Record<number, number> = {};\n\n constructor(opts: NodeSqlParserOptions = {}) {\n this.opts = opts;\n }\n\n /**\n * Lazy import of the node-sql-parser package and create a new Parser instance.\n */\n private getParser = lazy(async () => {\n if (this.parser) {\n return this.parser;\n }\n const module = await import(\"node-sql-parser\");\n // Support for ESM and CJS\n const { Parser } = module.default || module;\n this.parser = new Parser();\n return this.parser;\n });\n\n async parse(sql: string, opts: { state: EditorState }): Promise<NodeSqlParserResult> {\n // Reset the offset map on each parse\n this.offsetRecord = {};\n\n const parserOptions = this.opts.getParserOptions?.(opts.state);\n const sanitizedSql = await this.sanitizeSql(sql, parserOptions);\n\n try {\n const parser = await this.getParser();\n\n // Check if this is DuckDB dialect and apply custom processing\n if (parserOptions?.database === \"DuckDB\") {\n return this.parseWithDuckDBSupport(sanitizedSql, parserOptions);\n }\n\n const ast = parser.astify(sanitizedSql, parserOptions);\n\n return {\n success: true,\n errors: [],\n ast,\n };\n } catch (error: unknown) {\n const parseError = this.extractErrorInfo(error, sanitizedSql);\n return {\n success: false,\n errors: [parseError],\n };\n }\n }\n\n async sanitizeSql(sql: string, parserOptions?: ParserOption): Promise<string> {\n if (parserOptions?.ignoreBrackets) {\n const { sql: replacedSql, offsetRecord } = replaceBracketsWithQuotes(sql);\n this.offsetRecord = offsetRecord;\n return replacedSql;\n }\n return sql;\n }\n\n /**\n * Parse SQL with DuckDB syntax support\n * This is not robust, we catch main cases.\n */\n private async parseWithDuckDBSupport(\n sql: string,\n parserOptions: Option,\n ): Promise<NodeSqlParserResult> {\n const parser = await this.getParser();\n\n // Remove comments and normalize for pattern checking\n const sqlToCheck = removeCommentsFromStart(sql).trimStart().toLowerCase();\n\n // Handle unsupported DuckDB syntax patterns\n if (sqlToCheck.startsWith(\"from\") || sqlToCheck.includes(\"macro\")) {\n debug(\"Unsupported DuckDB syntax\");\n return { success: true, errors: [] };\n }\n\n let modifiedSql = sql;\n // Postgres does not support `CREATE OR REPLACE` for tables\n if (sqlToCheck.includes(\"create or replace table\")) {\n const offset = \"create or replace table\".length - \"create table\".length;\n this.offsetRecord[sql.indexOf(\"create or replace table\")] = -offset;\n modifiedSql = sql.replace(/create or replace table/i, \"create table\");\n }\n\n // Try standard parsing with PostgreSQL dialect\n try {\n const postgresOptions = { ...parserOptions, database: \"PostgreSQL\" };\n const ast = parser.astify(modifiedSql, postgresOptions);\n return { success: true, errors: [], ast };\n } catch (error) {\n // Use the original sql since we manually apply the offset\n const parseError = this.extractErrorInfo(error, sql);\n return { success: false, errors: [parseError] };\n }\n }\n\n /**\n * @param error - The error object\n * @param sql - The SQL string\n * @param offset - The offset to add to the column position. Default is 0.\n * @returns The parsed error information\n */\n private extractErrorInfo(error: unknown, sql: string): SqlParseError {\n let line = 1;\n let column = 1;\n const message = (error as Error)?.message || \"SQL parsing error\";\n\n const errorObj = error as {\n location?: { start?: { line: number; column: number } };\n hash?: { line: number; loc?: { first_column: number } };\n };\n if (errorObj?.location) {\n line = errorObj.location.start?.line || 1;\n column = errorObj.location.start?.column || 1;\n } else if (errorObj?.hash) {\n line = errorObj.hash.line || 1;\n column = errorObj.hash.loc?.first_column || 1;\n } else {\n const lineMatch = message.match(/line (\\d+)/i);\n const columnMatch = message.match(/column (\\d+)/i);\n\n if (lineMatch?.[1]) {\n line = parseInt(lineMatch[1], 10);\n }\n if (columnMatch?.[1]) {\n column = parseInt(columnMatch[1], 10);\n }\n }\n\n /**\n * Add offset to the column position to get the correct position of the error\n * SELECT {id} FRO users\n * ^ error position should be here\n *\n * SELECT {id} FRO users\n * ^ user sees this\n * So in this case, we subtract the offset from the column position.\n *\n * If the error is before the brackets, we don't need to add the offset because it just increases the string length\n * Column position will be the same as the user sees.\n */\n for (const [position, offset] of Object.entries(this.offsetRecord)) {\n if (column > parseInt(position, 10)) {\n column -= offset;\n }\n }\n\n // Ensure we don't exceed the sql length\n if (column > sql.length) {\n column = sql.length;\n }\n\n return {\n message: this.cleanErrorMessage(message),\n line: Math.max(1, line),\n column: column,\n severity: \"error\" as const,\n };\n }\n\n private cleanErrorMessage(message: string): string {\n return message\n .replace(/^Error: /, \"\")\n .replace(/Expected .* but .* found\\./i, (match) =>\n match.replace(/but .* found/, \"found unexpected token\"),\n )\n .trim();\n }\n\n async validateSql(sql: string, opts: { state: EditorState }): Promise<SqlParseError[]> {\n const result = await this.parse(sql, opts);\n return result.errors;\n }\n\n /**\n * Extracts table references from a SQL query using node-sql-parser\n * @param sql The SQL query to analyze\n * @returns Array of table names referenced in the query\n */\n async extractTableReferences(sql: string, opts?: { state: EditorState }): Promise<string[]> {\n const parserOptions = opts ? this.opts.getParserOptions?.(opts.state) : undefined;\n\n try {\n const parser = await this.getParser();\n const tableList = parser.tableList(sql, parserOptions);\n // Clean up table names - node-sql-parser returns format like \"select::null::users\"\n return tableList.map((table: string) => {\n const parts = table.split(\"::\");\n return parts[parts.length - 1] || table;\n });\n } catch {\n return [];\n }\n }\n\n /**\n * Extracts column references from a SQL query using node-sql-parser\n * @param sql The SQL query to analyze\n * @returns Array of column names referenced in the query\n */\n async extractColumnReferences(sql: string, opts?: { state: EditorState }): Promise<string[]> {\n const parserOptions = opts?.state ? this.opts.getParserOptions?.(opts.state) : undefined;\n\n try {\n const parser = await this.getParser();\n const columnList = parser.columnList(sql, parserOptions);\n\n // Clean up column names - node-sql-parser returns format like \"select::null::users\"\n const cleanColumnList = columnList.map((column: string) => {\n const parts = column.split(\"::\");\n return parts[parts.length - 1] || column;\n });\n return cleanColumnList;\n } catch {\n return [];\n }\n }\n}\n\ntype CommentType = \"--\" | \"/*\";\n\nfunction removeCommentsFromStart(sql: string, commentTypes: CommentType[] = [\"/*\", \"--\"]): string {\n const regexPatterns: string[] = [];\n\n // Multi-line comments\n if (commentTypes.includes(\"/*\")) {\n regexPatterns.push(\"/\\\\*[\\\\s\\\\S]*?\\\\*/\");\n }\n // Single-line comments\n if (commentTypes.includes(\"--\")) {\n regexPatterns.push(\"--[^\\\\n]*\");\n }\n\n if (regexPatterns.length === 0) return sql;\n\n const commentRegex = new RegExp(`^\\\\s*(${regexPatterns.join(\"|\")})\\\\s*`, \"\");\n\n // Keep removing comments from the start until no more are found\n let result = sql;\n let prevResult = \"\";\n\n while (result !== prevResult) {\n prevResult = result;\n result = result.replace(commentRegex, \"\");\n }\n\n return result;\n}\n\nconst QUOTE_LENGTH = \"''\".length;\n\n/**\n * Replaces unquoted curly bracket expressions (e.g., {id}) with quoted strings (e.g., '{id}'),\n * ignoring brackets already inside single or double quotes.\n *\n * Returns the modified SQL and a record mapping the index of each replaced bracket to the\n * number of characters added (for offset tracking).\n *\n * @example\n * replaceBracketsWithQuotes(\"SELECT {id}, '{name}' FROM users\");\n * // => {\n * // sql: \"SELECT '{id}', '{name}' FROM users\",\n * // offsetRecord: { 7: 2 }\n * // }\n */\nfunction replaceBracketsWithQuotes(sql: string): {\n sql: string;\n offsetRecord: Record<number, number>;\n} {\n const offsetRecord: Record<number, number> = {};\n\n const replacedSql = sql.replace(\n /(\"(?:[^\"\\\\]|\\\\.)*\")|('(?:[^'\\\\]|\\\\.)*')|(\\{[^}]*\\})/g,\n (match, doubleQuoted, singleQuoted, bracket, offset) => {\n // If it's a quoted string, return it as-is\n if (doubleQuoted || singleQuoted) {\n return match;\n }\n\n // If it's a bracket, quote it and record the offset\n if (bracket) {\n offsetRecord[offset] = QUOTE_LENGTH;\n return `'${bracket}'`;\n }\n\n return match;\n },\n );\n\n return { sql: replacedSql, offsetRecord };\n}\n\nexport const exportedForTesting = { replaceBracketsWithQuotes, removeCommentsFromStart };\n\n/**\n * https://github.com/taozhi8833998/node-sql-parser?tab=readme-ov-file#supported-database-sql-syntax\n * While DuckDB is not supported in the library, we perform some special handling for it and treat it as PostgreSQL.\n */\nexport type SupportedDialects =\n | \"Athena\"\n | \"BigQuery\"\n | \"DB2\"\n | \"Hive\"\n | \"MariaDB\"\n | \"MySQL\"\n | \"PostgreSQL\"\n | \"DuckDB\"\n | \"Redshift\"\n | \"Sqlite\"\n | \"TransactSQL\"\n | \"FlinkSQL\"\n | \"Snowflake\"\n | \"Noql\";\n"]} |
+10
-4
@@ -30,3 +30,3 @@ import type { EditorState } from "@codemirror/state"; | ||
| * @param sql - The SQL statement to parse | ||
| * @param opts - The options for the parser | ||
| * @param opts - The state of the editor | ||
| * @returns The parsed AST | ||
@@ -40,3 +40,3 @@ */ | ||
| * @param sql - The SQL statement to validate | ||
| * @param opts - The options for the parser | ||
| * @param opts - The state of the editor | ||
| * @returns An array of errors | ||
@@ -50,12 +50,18 @@ */ | ||
| * @param sql - The SQL query to analyze | ||
| * @param opts - The state of the editor | ||
| * @returns Array of table names referenced in the query | ||
| */ | ||
| extractTableReferences(sql: string): Promise<string[]>; | ||
| extractTableReferences(sql: string, opts?: { | ||
| state: EditorState; | ||
| }): Promise<string[]>; | ||
| /** | ||
| * Extract column references from a SQL query | ||
| * @param sql - The SQL query to analyze | ||
| * @param opts - The state of the editor | ||
| * @returns Array of column names referenced in the query | ||
| */ | ||
| extractColumnReferences(sql: string): Promise<string[]>; | ||
| extractColumnReferences(sql: string, opts?: { | ||
| state: EditorState; | ||
| }): Promise<string[]>; | ||
| } | ||
| //# sourceMappingURL=types.d.ts.map |
@@ -1,1 +0,1 @@ | ||
| {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/sql/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,yCAAyC;IACzC,OAAO,EAAE,MAAM,CAAC;IAChB,uDAAuD;IACvD,IAAI,EAAE,MAAM,CAAC;IACb,yDAAyD;IACzD,MAAM,EAAE,MAAM,CAAC;IACf,kCAAkC;IAClC,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;CAC/B;AACD;;GAEG;AAEH,MAAM,WAAW,cAAc;IAC7B,qCAAqC;IACrC,OAAO,EAAE,OAAO,CAAC;IACjB,sCAAsC;IACtC,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB,mCAAmC;IACnC,GAAG,CAAC,EAAE,OAAO,CAAC;CACf;AAED,MAAM,WAAW,SAAS;IACxB;;;;;OAKG;IACH,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,cAAc,CAAC,CAAC;IAC1E;;;;;OAKG;IACH,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC,CAAC;IACjF;;;;OAIG;IACH,sBAAsB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACvD;;;;OAIG;IACH,uBAAuB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;CACzD"} | ||
| {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/sql/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,yCAAyC;IACzC,OAAO,EAAE,MAAM,CAAC;IAChB,uDAAuD;IACvD,IAAI,EAAE,MAAM,CAAC;IACb,yDAAyD;IACzD,MAAM,EAAE,MAAM,CAAC;IACf,kCAAkC;IAClC,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;CAC/B;AACD;;GAEG;AAEH,MAAM,WAAW,cAAc;IAC7B,qCAAqC;IACrC,OAAO,EAAE,OAAO,CAAC;IACjB,sCAAsC;IACtC,MAAM,EAAE,aAAa,EAAE,CAAC;IACxB,mCAAmC;IACnC,GAAG,CAAC,EAAE,OAAO,CAAC;CACf;AAED,MAAM,WAAW,SAAS;IACxB;;;;;OAKG;IACH,KAAK,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,cAAc,CAAC,CAAC;IAC1E;;;;;OAKG;IACH,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC,CAAC;IACjF;;;;;OAKG;IACH,sBAAsB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACtF;;;;;OAKG;IACH,uBAAuB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;QAAE,KAAK,EAAE,WAAW,CAAA;KAAE,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;CACxF"} |
@@ -1,1 +0,1 @@ | ||
| {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/sql/types.ts"],"names":[],"mappings":"","sourcesContent":["import type { EditorState } from \"@codemirror/state\";\n\n/**\n * Represents a SQL parsing error with location information\n */\nexport interface SqlParseError {\n /** Error message describing the issue */\n message: string;\n /** Line number where the error occurred (1-indexed) */\n line: number;\n /** Column number where the error occurred (1-indexed) */\n column: number;\n /** Severity level of the error */\n severity: \"error\" | \"warning\";\n}\n/**\n * Result of parsing a SQL statement\n */\n\nexport interface SqlParseResult {\n /** Whether parsing was successful */\n success: boolean;\n /** Array of parsing errors, if any */\n errors: SqlParseError[];\n /** The parsed AST if successful */\n ast?: unknown;\n}\n\nexport interface SqlParser {\n /**\n * Parse a SQL statement and return the AST\n * @param sql - The SQL statement to parse\n * @param opts - The options for the parser\n * @returns The parsed AST\n */\n parse(sql: string, opts: { state: EditorState }): Promise<SqlParseResult>;\n /**\n * Validate a SQL statement and return any errors\n * @param sql - The SQL statement to validate\n * @param opts - The options for the parser\n * @returns An array of errors\n */\n validateSql(sql: string, opts: { state: EditorState }): Promise<SqlParseError[]>;\n /**\n * Extract table references from a SQL query\n * @param sql - The SQL query to analyze\n * @returns Array of table names referenced in the query\n */\n extractTableReferences(sql: string): Promise<string[]>;\n /**\n * Extract column references from a SQL query\n * @param sql - The SQL query to analyze\n * @returns Array of column names referenced in the query\n */\n extractColumnReferences(sql: string): Promise<string[]>;\n}\n"]} | ||
| {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/sql/types.ts"],"names":[],"mappings":"","sourcesContent":["import type { EditorState } from \"@codemirror/state\";\n\n/**\n * Represents a SQL parsing error with location information\n */\nexport interface SqlParseError {\n /** Error message describing the issue */\n message: string;\n /** Line number where the error occurred (1-indexed) */\n line: number;\n /** Column number where the error occurred (1-indexed) */\n column: number;\n /** Severity level of the error */\n severity: \"error\" | \"warning\";\n}\n/**\n * Result of parsing a SQL statement\n */\n\nexport interface SqlParseResult {\n /** Whether parsing was successful */\n success: boolean;\n /** Array of parsing errors, if any */\n errors: SqlParseError[];\n /** The parsed AST if successful */\n ast?: unknown;\n}\n\nexport interface SqlParser {\n /**\n * Parse a SQL statement and return the AST\n * @param sql - The SQL statement to parse\n * @param opts - The state of the editor\n * @returns The parsed AST\n */\n parse(sql: string, opts: { state: EditorState }): Promise<SqlParseResult>;\n /**\n * Validate a SQL statement and return any errors\n * @param sql - The SQL statement to validate\n * @param opts - The state of the editor\n * @returns An array of errors\n */\n validateSql(sql: string, opts: { state: EditorState }): Promise<SqlParseError[]>;\n /**\n * Extract table references from a SQL query\n * @param sql - The SQL query to analyze\n * @param opts - The state of the editor\n * @returns Array of table names referenced in the query\n */\n extractTableReferences(sql: string, opts?: { state: EditorState }): Promise<string[]>;\n /**\n * Extract column references from a SQL query\n * @param sql - The SQL query to analyze\n * @param opts - The state of the editor\n * @returns Array of column names referenced in the query\n */\n extractColumnReferences(sql: string, opts?: { state: EditorState }): Promise<string[]>;\n}\n"]} |
+8
-8
| { | ||
| "$schema": "https://json.schemastore.org/package.json", | ||
| "name": "@marimo-team/codemirror-sql", | ||
| "version": "0.2.3", | ||
| "version": "0.2.4", | ||
| "publishConfig": { | ||
@@ -21,2 +21,4 @@ "access": "public" | ||
| "peerDependencies": { | ||
| "@codemirror/autocomplete": "^6", | ||
| "@codemirror/lint": "^6", | ||
| "@codemirror/state": "^6", | ||
@@ -26,10 +28,10 @@ "@codemirror/view": "^6" | ||
| "devDependencies": { | ||
| "@biomejs/biome": "^2.2.4", | ||
| "@biomejs/biome": "^2.2.6", | ||
| "@codemirror/lang-sql": "^6.10.0", | ||
| "@codemirror/view": "^6.38.3", | ||
| "@codemirror/view": "^6.38.6", | ||
| "@vitest/coverage-v8": "3.2.4", | ||
| "codemirror": "^6.0.2", | ||
| "jsdom": "^27.0.0", | ||
| "typescript": "^5.9.2", | ||
| "vite": "^7.1.7", | ||
| "typescript": "^5.9.3", | ||
| "vite": "^7.1.10", | ||
| "vitest": "^3.2.4" | ||
@@ -65,5 +67,3 @@ }, | ||
| "dependencies": { | ||
| "@codemirror/autocomplete": "^6.18.7", | ||
| "@codemirror/lint": "^6.8.5", | ||
| "node-sql-parser": "^5.3.12" | ||
| "node-sql-parser": "^5.3.13" | ||
| }, | ||
@@ -70,0 +70,0 @@ "scripts": { |
Network access
Supply chain riskThis module accesses the network.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Network access
Supply chain riskThis module accesses the network.
Found 1 instance in 1 package
Long strings
Supply chain riskContains long string literals, which may be a sign of obfuscated or packed code.
Found 1 instance in 1 package
333970
0.42%3323
0.36%1
-50%- Removed
- Removed
Updated