Skip to content

Commit a3e448e

Browse files
Merge pull request #1930 from taozhi8833998/feat-create-table-mysql
feat: support create table in mysql 8.x and drop view in sqlite
2 parents 7d9ef8c + cfcbfdf commit a3e448e

File tree

7 files changed

+51
-13
lines changed

7 files changed

+51
-13
lines changed

pegjs/mariadb.pegjs

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -891,7 +891,7 @@ drop_stmt
891891
keyword: r.toLowerCase(),
892892
prefix: ife,
893893
name: t,
894-
options: [{ type: 'origin', value: op }],
894+
options: op && [{ type: 'origin', value: op }],
895895
}
896896
};
897897
}
@@ -1203,7 +1203,8 @@ column_ref_idx_list
12031203
}
12041204

12051205
cte_idx_column_definition
1206-
= LPAREN __ l:column_ref_idx_list __ RPAREN {
1206+
= LPAREN __ l:(column_ref_idx_list / expr_list) __ RPAREN {
1207+
if (l.type) return l.value
12071208
return l
12081209
}
12091210

@@ -3247,6 +3248,7 @@ cast_expr
32473248
type: 'cast',
32483249
keyword: c.toLowerCase(),
32493250
expr: e,
3251+
symbol: 'as',
32503252
target: t
32513253
};
32523254
}
@@ -3255,6 +3257,7 @@ cast_expr
32553257
type: 'cast',
32563258
keyword: c.toLowerCase(),
32573259
expr: e,
3260+
symbol: 'as',
32583261
target: {
32593262
dataType: 'DECIMAL(' + precision + ')'
32603263
}
@@ -3265,6 +3268,7 @@ cast_expr
32653268
type: 'cast',
32663269
keyword: c.toLowerCase(),
32673270
expr: e,
3271+
symbol: 'as',
32683272
target: {
32693273
dataType: 'DECIMAL(' + precision + ', ' + scale + ')'
32703274
}
@@ -3275,6 +3279,7 @@ cast_expr
32753279
type: 'cast',
32763280
keyword: c.toLowerCase(),
32773281
expr: e,
3282+
symbol: 'as',
32783283
target: {
32793284
dataType: s + (t ? ' ' + t: '')
32803285
}
@@ -3933,8 +3938,8 @@ binary_type
39333938

39343939

39353940
character_string_type
3936-
= t:(KW_CHAR / KW_VARCHAR) __ LPAREN __ l:[0-9]+ __ RPAREN {
3937-
return { dataType: t, length: parseInt(l.join(''), 10), parentheses: true };
3941+
= t:(KW_CHAR / KW_VARCHAR) __ LPAREN __ l:[0-9]+ __ RPAREN __ s:('ARRAY'i)? {
3942+
return { dataType: t, length: parseInt(l.join(''), 10), parentheses: true, suffix: s && ['ARRAY'] };
39383943
}
39393944
/ t:KW_CHAR { return { dataType: t }; }
39403945
/ t:KW_VARCHAR { return { dataType: t }; }

pegjs/mysql.pegjs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1092,7 +1092,7 @@ drop_stmt
10921092
keyword: r.toLowerCase(),
10931093
prefix: ife,
10941094
name: t,
1095-
options: [{ type: 'origin', value: op }],
1095+
options: op && [{ type: 'origin', value: op }],
10961096
}
10971097
};
10981098
}
@@ -2093,7 +2093,8 @@ column_ref_idx_list
20932093
}
20942094

20952095
cte_idx_column_definition
2096-
= LPAREN __ l:column_ref_idx_list __ RPAREN {
2096+
= LPAREN __ l:(column_ref_idx_list / expr_list) __ RPAREN {
2097+
if (l.type) return l.value
20972098
return l
20982099
}
20992100

@@ -4253,8 +4254,8 @@ binary_type
42534254
/ t:KW_BINARY { return { dataType: t }; }
42544255

42554256
character_string_type
4256-
= t:(KW_CHAR / KW_VARCHAR) __ LPAREN __ l:[0-9]+ __ RPAREN {
4257-
return { dataType: t, length: parseInt(l.join(''), 10), parentheses: true };
4257+
= t:(KW_CHAR / KW_VARCHAR) __ LPAREN __ l:[0-9]+ __ RPAREN __ s:('ARRAY'i)? {
4258+
return { dataType: t, length: parseInt(l.join(''), 10), parentheses: true, suffix: s && ['ARRAY'] };
42584259
}
42594260
/ t:KW_CHAR { return { dataType: t }; }
42604261
/ t:KW_VARCHAR { return { dataType: t }; }

pegjs/sqlite.pegjs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -289,6 +289,11 @@ if_not_exists_stmt
289289
return 'IF NOT EXISTS'
290290
}
291291

292+
if_exists
293+
= 'if'i __ 'exists'i {
294+
return 'if exists'
295+
}
296+
292297
create_trigger_stmt
293298
= kw: KW_CREATE __
294299
tp:(KW_TEMPORARY / KW_TEMP)? __
@@ -622,6 +627,21 @@ drop_stmt
622627
}
623628
};
624629
}
630+
/ a:KW_DROP __
631+
r:KW_VIEW __
632+
ife:if_exists? __
633+
t:table_ref_list {
634+
return {
635+
tableList: Array.from(tableList),
636+
columnList: columnListTableAlias(columnList),
637+
ast: {
638+
type: a.toLowerCase(),
639+
keyword: r.toLowerCase(),
640+
prefix: ife,
641+
name: t,
642+
}
643+
};
644+
}
625645
/ a:KW_DROP __
626646
r:KW_INDEX __
627647
i:column_ref __

src/column.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -174,7 +174,7 @@ function columnToSQL(column, isDual) {
174174
result.push([toUpper(type), type && '(', columnsStr, type && ')'].filter(hasVal).join(''))
175175
return result.filter(hasVal).join(' ')
176176
}
177-
if (expr.parentheses && Reflect.has(expr, 'array_index')) str = `(${str})`
177+
if (expr.parentheses && Reflect.has(expr, 'array_index') && expr.type !== 'cast') str = `(${str})`
178178
if (expr.array_index && expr.type !== 'column_ref') {
179179
str = `${str}${arrayIndexToSQL(expr.array_index)}`
180180
}

src/func.js

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ function arrayDimensionToSymbol(target) {
2323
}
2424

2525
function castToSQL(expr) {
26-
const { arrows = [], collate, target, expr: expression, keyword, symbol, as: alias, properties = [] } = expr
26+
const { arrows = [], collate, target, expr: expression, keyword, symbol, as: alias, parentheses: outParentheses, properties = [] } = expr
2727
const { length, dataType, parentheses, quoted, scale, suffix: dataTypeSuffix, expr: targetExpr } = target
2828
let str = targetExpr ? exprToSQL(targetExpr) : ''
2929
if (length != null) str = scale ? `${length}, ${scale}` : length
@@ -41,8 +41,8 @@ function castToSQL(expr) {
4141
if (alias) suffix += ` AS ${identifierToSql(alias)}`
4242
if (collate) suffix += ` ${commonTypeValue(collate).join(' ')}`
4343
const arrayDimension = arrayDimensionToSymbol(target)
44-
const result = [prefix, symbolChar, quoted, dataType, quoted, arrayDimension, str, suffix]
45-
return result.filter(hasVal).join('')
44+
const result = [prefix, symbolChar, quoted, dataType, quoted, arrayDimension, str, suffix].filter(hasVal).join('')
45+
return outParentheses ? `(${result})` : result
4646
}
4747

4848
function extractFunToSQL(stmt) {

test/mysql-mariadb.spec.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1023,6 +1023,16 @@ describe('mysql', () => {
10231023
"SET @_mystoredprocedure_0 = '1', @_mystoredprocedure_1 = '2'"
10241024
]
10251025
},
1026+
{
1027+
title: 'create table for key',
1028+
sql: [
1029+
`CREATE TABLE some_table (
1030+
col JSON,
1031+
KEY \`idx_col\` ((CAST(\`col\` AS CHAR(12) ARRAY)))
1032+
);`,
1033+
'CREATE TABLE `some_table` (`col` JSON, KEY idx_col ((CAST(`col` AS CHAR(12) ARRAY))))'
1034+
]
1035+
},
10261036
]
10271037
SQL_LIST.forEach(sqlInfo => {
10281038
const { title, sql } = sqlInfo

test/sqlite.spec.js

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -155,10 +155,12 @@ describe('sqlite', () => {
155155
expect(parser.sqlify(ast, DEFAULT_OPT)).to.be.equal('CREATE TABLE `Test` (`id` INT(11) NOT NULL, `name` VARCHAR(255) NOT NULL, PRIMARY KEY (`id`), UNIQUE (`name`))')
156156
})
157157

158-
it('should support create view', () => {
158+
it('should support create or drop view', () => {
159159
let sql = 'create view v1 as select * from t1'
160160
expect(getParsedSql(sql)).to.be.equal('CREATE VIEW `v1` AS SELECT * FROM `t1`')
161161
sql = 'create temp view if not exists s.v1(a, b, c) as select * from t1'
162162
expect(getParsedSql(sql)).to.be.equal('CREATE TEMP VIEW IF NOT EXISTS `s`.`v1` (`a`, `b`, `c`) AS SELECT * FROM `t1`')
163+
sql = 'DROP VIEW IF EXISTS view_name;',
164+
expect(getParsedSql(sql)).to.be.equal('DROP VIEW IF EXISTS `view_name`')
163165
})
164166
})

0 commit comments

Comments
 (0)