1 parent
ec50662793
commit
c210efbcc5
4 files changed
+204
-2
No files matched your search
@@ -1035,6 +1035,22 @@ WHERE request_json LIKE '%"paperFlag":null%';`;
|
||||
expect(rangeSqlTexts(executableStatementRanges(sql, "mysql"))).toEqual([sql.slice(0, -1)]);
|
||||
});
|
||||
|
||||
it("keeps a line-start MySQL TRUNCATE function inside a SELECT projection", () => {
|
||||
const sql = `SELECT
|
||||
order_id,
|
||||
TRUNCATE(amount, 2) AS rounded_amount
|
||||
FROM orders;`;
|
||||
|
||||
expect(rangeSqlTexts(executableStatementRanges(sql, "mysql"))).toEqual([sql.slice(0, -1)]);
|
||||
expect(currentExecutableStatementRange(sql, indexOf(sql, "TRUNCATE"), "mysql")?.sql.trim()).toBe(sql.slice(0, -1));
|
||||
});
|
||||
|
||||
it("keeps standalone TRUNCATE TABLE statements separate", () => {
|
||||
const sql = "SELECT 1;\nTRUNCATE TABLE t;";
|
||||
|
||||
expect(rangeSqlTexts(executableStatementRanges(sql, "mysql"))).toEqual(["SELECT 1", "TRUNCATE TABLE t"]);
|
||||
});
|
||||
|
||||
it("does not merge a plain MySQL DESC table statement with the next query", () => {
|
||||
const sql = "DESC users\nSELECT * FROM users;";
|
||||
expect(statementRangeAtCursor(sql, indexOf(sql, "DESC"), "mysql")?.sql.trim()).toBe("DESC users");
|
||||
|
||||
@@ -431,6 +431,11 @@ const MYSQL_SQL_KEYWORDS = [
|
||||
"SHOW",
|
||||
"DESCRIBE",
|
||||
"REPLACE",
|
||||
"REPEAT",
|
||||
"DATABASE",
|
||||
"SCHEMA",
|
||||
"USER",
|
||||
"CURRENT_USER",
|
||||
"DUPLICATE KEY",
|
||||
"JSON_EXTRACT",
|
||||
"JSON_UNQUOTE",
|
||||
@@ -940,6 +945,20 @@ const MYSQL_FUNCTION_SIGNATURES = new Map<string, string[]>([
|
||||
["DAYOFYEAR", ["date"]],
|
||||
["LAST_DAY", ["date"]],
|
||||
["STR_TO_DATE", ["string", "format"]],
|
||||
["MONTHNAME", ["date"]],
|
||||
["DAYOFMONTH", ["date"]],
|
||||
["WEEKDAY", ["date"]],
|
||||
["WEEK", ["date", "mode"]],
|
||||
["QUARTER", ["date"]],
|
||||
["ADDDATE", ["date", "days"]],
|
||||
["SUBDATE", ["date", "days"]],
|
||||
["ADDTIME", ["datetime", "time"]],
|
||||
["SUBTIME", ["datetime", "time"]],
|
||||
["TIMEDIFF", ["datetime1", "datetime2"]],
|
||||
["FROM_DAYS", ["day_number"]],
|
||||
["TO_DAYS", ["date"]],
|
||||
["MAKEDATE", ["year", "day_of_year"]],
|
||||
["MAKETIME", ["hour", "minute", "second"]],
|
||||
["IFNULL", ["expression", "fallback"]],
|
||||
["IF", ["condition", "true_value", "false_value"]],
|
||||
["CONCAT_WS", ["separator", "...values"]],
|
||||
@@ -952,20 +971,67 @@ const MYSQL_FUNCTION_SIGNATURES = new Map<string, string[]>([
|
||||
["LPAD", ["string", "length", "pad"]],
|
||||
["RPAD", ["string", "length", "pad"]],
|
||||
["REVERSE", ["string"]],
|
||||
["POSITION", ["substring", "string"]],
|
||||
["REPEAT", ["string", "count"]],
|
||||
["STRCMP", ["string1", "string2"]],
|
||||
["FIND_IN_SET", ["string", "string_list"]],
|
||||
["ELT", ["index", "string1", "...strings"]],
|
||||
["FIELD", ["value", "value1", "...values"]],
|
||||
["MAKE_SET", ["bits", "string1", "...strings"]],
|
||||
["RAND", []],
|
||||
["POW", ["base", "exponent"]],
|
||||
["EXP", ["number"]],
|
||||
["LN", ["number"]],
|
||||
["LOG", ["base", "number"]],
|
||||
["LOG10", ["number"]],
|
||||
["LOG2", ["number"]],
|
||||
["SIN", ["number"]],
|
||||
["PI", []],
|
||||
["COS", ["number"]],
|
||||
["TAN", ["number"]],
|
||||
["ASIN", ["number"]],
|
||||
["ACOS", ["number"]],
|
||||
["ATAN", ["number"]],
|
||||
["ATAN2", ["y", "x"]],
|
||||
["DEGREES", ["radians"]],
|
||||
["RADIANS", ["degrees"]],
|
||||
["BIN", ["number"]],
|
||||
["HEX", ["value"]],
|
||||
["UNHEX", ["string"]],
|
||||
["OCT", ["number"]],
|
||||
["CONV", ["number", "from_base", "to_base"]],
|
||||
["TRUNCATE", ["number", "decimals"]],
|
||||
["MD5", ["string"]],
|
||||
["SHA1", ["string"]],
|
||||
["SHA2", ["string", "bit_length"]],
|
||||
["JSON_EXTRACT", ["json", "path"]],
|
||||
["JSON_UNQUOTE", ["json"]],
|
||||
["JSON_OBJECT", ["key", "value", "...pairs"]],
|
||||
["JSON_ARRAY", ["...values"]],
|
||||
["JSON_SET", ["json", "path", "value", "...path_value_pairs"]],
|
||||
["JSON_INSERT", ["json", "path", "value", "...path_value_pairs"]],
|
||||
["JSON_REPLACE", ["json", "path", "value", "...path_value_pairs"]],
|
||||
["JSON_REMOVE", ["json", "path", "...paths"]],
|
||||
["JSON_CONTAINS", ["target", "candidate"]],
|
||||
["JSON_LENGTH", ["json"]],
|
||||
["GROUP_CONCAT", ["expression"]],
|
||||
["PASSWORD", ["string"]],
|
||||
["DATABASE", []],
|
||||
["SCHEMA", []],
|
||||
["USER", []],
|
||||
["CURRENT_USER", []],
|
||||
["COLLATION", ["string"]],
|
||||
["FOUND_ROWS", []],
|
||||
["LAST_INSERT_ID", []],
|
||||
["BENCHMARK", ["count", "expression"]],
|
||||
["SLEEP", ["seconds"]],
|
||||
["UUID", []],
|
||||
["UUID_SHORT", []],
|
||||
["NOW", []],
|
||||
]);
|
||||
|
||||
/** Keywords that may also exist as built-in functions; keep both completion entries. */
|
||||
const DUAL_ROLE_SQL_KEYWORDS = new Set(["LEFT", "RIGHT", "IF"]);
|
||||
const DUAL_ROLE_SQL_KEYWORDS = new Set(["LEFT", "RIGHT", "IF", "TRUNCATE", "REPEAT", "DATABASE", "SCHEMA", "USER", "CURRENT_USER"]);
|
||||
|
||||
const SQLITE_FUNCTION_SIGNATURES = new Map<string, string[]>([
|
||||
["JSON_EXTRACT", ["json", "path"]],
|
||||
@@ -1048,6 +1114,7 @@ const DATABASE_FUNCTION_SIGNATURES: Partial<Record<DatabaseType, Map<string, str
|
||||
const MYSQL_FUNCTION_APPLY_TEMPLATES = new Map<string, string>([
|
||||
["DATE_ADD", "DATE_ADD(${date}, INTERVAL ${expr} ${unit})"],
|
||||
["DATE_SUB", "DATE_SUB(${date}, INTERVAL ${expr} ${unit})"],
|
||||
["POSITION", "POSITION(${substring} IN ${string})"],
|
||||
]);
|
||||
|
||||
const COMMON_SQL_FUNCTION_NAMES = new Set([
|
||||
|
||||
@@ -231,6 +231,8 @@ const COMMON_SOFT_STATEMENT_START_KEYWORDS = [
|
||||
"COPY",
|
||||
] as const;
|
||||
|
||||
const SOFT_STATEMENT_FUNCTION_KEYWORDS = new Set(["REPLACE", "TRUNCATE"]);
|
||||
|
||||
const DATABASE_SOFT_STATEMENT_KEYWORDS: Partial<Record<DatabaseType, readonly string[]>> = {
|
||||
mysql: ["HANDLER", "LOAD", "OPTIMIZE", "REPAIR"],
|
||||
postgres: ["DO", "LISTEN", "NOTIFY", "UNLISTEN"],
|
||||
@@ -957,7 +959,7 @@ function softStatementKeywordAt(sql: string, pos: number, databaseType?: Databas
|
||||
const match = /^[A-Za-z_][\w$]*/.exec(sql.slice(pos));
|
||||
if (!match) return null;
|
||||
const keyword = match[0].toUpperCase();
|
||||
if (keyword === "REPLACE" && nextNonWhitespaceChar(sql, pos + match[0].length) === "(") return null;
|
||||
if (SOFT_STATEMENT_FUNCTION_KEYWORDS.has(keyword) && nextNonWhitespaceChar(sql, pos + match[0].length) === "(") return null;
|
||||
// COMMENT is also a common column name. Only COMMENT ON starts a standalone
|
||||
// SQL command; otherwise a line-start projection column must stay in SELECT.
|
||||
if (keyword === "COMMENT" && nextSqlWord(sql, pos + match[0].length, databaseType, parameterOptions) !== "ON") return null;
|
||||
|
||||
Reference in new issue
Block a user