feat(query-editor): enhance current statement framing
This commit is contained in:
18 files changed
+480
-10
No files matched your search
@@ -1,6 +1,6 @@
|
||||
import { Text } from "@codemirror/state";
|
||||
import { describe, expect, it, vi } from "vitest";
|
||||
import { executableStatementRangeCacheForDoc, executableStatementRangeStartingAt, type ExecutableStatementRangeParser } from "@/lib/sql/executableStatementRangeCache";
|
||||
import { executableStatementRangeAtCursor, executableStatementRangeCacheForDoc, executableStatementRangeStartingAt, type ExecutableStatementRangeParser } from "@/lib/sql/executableStatementRangeCache";
|
||||
|
||||
describe("executableStatementRangeCacheForDoc", () => {
|
||||
it("reuses parsed executable statement ranges for the same document and database type", () => {
|
||||
@@ -27,6 +27,41 @@ describe("executableStatementRangeCacheForDoc", () => {
|
||||
expect(executableStatementRangeStartingAt(cache, secondStatementLine.from)?.sql).toBe("SELECT *\nFROM menus AS mn\nLIMIT 100");
|
||||
});
|
||||
|
||||
it("resolves the current statement from a cursor inside a continuation line", () => {
|
||||
const doc = Text.of(["SELECT *", "FROM apis AS ap", "LIMIT 100;", "", "SELECT *", "FROM menus AS mn", "LIMIT 100;"]);
|
||||
const cache = executableStatementRangeCacheForDoc(null, doc, "mysql");
|
||||
const cursor = doc.toString().indexOf("menus");
|
||||
|
||||
expect(executableStatementRangeAtCursor(cache, cursor)?.sql).toBe("SELECT *\nFROM menus AS mn\nLIMIT 100");
|
||||
});
|
||||
|
||||
it("keeps indentation and same-line semicolon gaps attached to the current statement", () => {
|
||||
const doc = Text.of(["SELECT 1;", " SELECT 2;"]);
|
||||
const cache = executableStatementRangeCacheForDoc(null, doc, "mysql");
|
||||
const indentationCursor = doc.line(2).from + 2;
|
||||
const semicolonGapCursor = doc.toString().indexOf(";") + 1;
|
||||
|
||||
expect(executableStatementRangeAtCursor(cache, indentationCursor)?.sql).toBe("SELECT 2");
|
||||
expect(executableStatementRangeAtCursor(cache, semicolonGapCursor)?.sql).toBe("SELECT 1");
|
||||
});
|
||||
|
||||
it("returns null for blank and pure comment cursor lines", () => {
|
||||
const doc = Text.of(["SELECT 1;", "-- comment", "/* block comment */", "", "SELECT 2;"]);
|
||||
const cache = executableStatementRangeCacheForDoc(null, doc, "mysql");
|
||||
|
||||
expect(executableStatementRangeAtCursor(cache, doc.line(2).from + 3)).toBeNull();
|
||||
expect(executableStatementRangeAtCursor(cache, doc.line(3).from + 3)).toBeNull();
|
||||
expect(executableStatementRangeAtCursor(cache, doc.line(4).from)).toBeNull();
|
||||
});
|
||||
|
||||
it("resolves SQL after a leading block comment on the same line", () => {
|
||||
const doc = Text.of(["/* comment */ SELECT 1;"]);
|
||||
const cache = executableStatementRangeCacheForDoc(null, doc, "mysql");
|
||||
|
||||
expect(executableStatementRangeAtCursor(cache, doc.toString().indexOf("SELECT"))?.sql).toBe("SELECT 1");
|
||||
expect(executableStatementRangeAtCursor(cache, doc.toString().indexOf("comment"))).toBeNull();
|
||||
});
|
||||
|
||||
it("rebuilds the cache when the document instance changes", () => {
|
||||
const firstDoc = Text.of(["SELECT 1;"]);
|
||||
const secondDoc = Text.of(["SELECT 1;"]);
|
||||
|
||||
Reference in new issue
Block a user