Skip to content

Commit 3fc1390

Browse files
committed
+
1 parent 40fcf6e commit 3fc1390

File tree

10 files changed

+183
-119
lines changed

10 files changed

+183
-119
lines changed

drizzle-kit/src/dialects/mysql/grammar.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -498,7 +498,7 @@ export const Year: SqlType = {
498498

499499
export const Enum: SqlType = {
500500
is: (type) => /^(?:enum)(?:[\s(].*)?$/i.test(type),
501-
drizzleImport: () => 'enum',
501+
drizzleImport: () => 'mysqlEnum',
502502
defaultFromDrizzle: (value) => {
503503
return String(value);
504504
},
@@ -510,7 +510,7 @@ export const Enum: SqlType = {
510510
if (it.startsWith('(')) return it;
511511
return `'${escapeForSqlDefault(it)}'`;
512512
},
513-
toTs: (type, def) => {
513+
toTs: (_, def) => {
514514
if (!def) return { default: '' };
515515
const unescaped = escapeForTsLiteral(def);
516516
return { default: `"${unescaped}"` };

drizzle-kit/src/dialects/mysql/typescript.ts

Lines changed: 5 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
/* eslint-disable @typescript-eslint/no-unsafe-argument */
22
import { toCamelCase } from 'drizzle-orm/casing';
33
import { Casing } from 'src/cli/validations/common';
4-
import { unescapeSingleQuotes } from 'src/utils';
54
import { assertUnreachable } from '../../utils';
65
import { CheckConstraint, Column, ForeignKey, Index, MysqlDDL, PrimaryKey, ViewColumn } from './ddl';
76
import { Enum, parseEnum, typeFor } from './grammar';
@@ -32,13 +31,12 @@ export const imports = [
3231
'varbinary',
3332
'varchar',
3433
'year',
35-
'enum',
34+
'mysqlEnum',
3635
] as const;
3736
export type Import = typeof imports[number];
3837

3938
const mysqlImportsList = new Set([
4039
'mysqlTable',
41-
'mysqlEnum',
4240
...imports,
4341
]);
4442

@@ -64,7 +62,6 @@ function inspect(it: any): string {
6462

6563
const objToStatement2 = (json: any) => {
6664
json = Object.fromEntries(Object.entries(json).filter((it) => it[1]));
67-
6865
const keys = Object.keys(json);
6966
if (keys.length === 0) return;
7067

@@ -74,35 +71,6 @@ const objToStatement2 = (json: any) => {
7471
return statement;
7572
};
7673

77-
const timeConfig = (json: any) => {
78-
json = Object.fromEntries(Object.entries(json).filter((it) => it[1]));
79-
80-
const keys = Object.keys(json);
81-
if (keys.length === 0) return;
82-
83-
let statement = '{ ';
84-
statement += keys.map((it) => `${it}: ${json[it]}`).join(', ');
85-
statement += ' }';
86-
return statement;
87-
};
88-
89-
const binaryConfig = (json: any) => {
90-
json = Object.fromEntries(Object.entries(json).filter((it) => it[1]));
91-
92-
const keys = Object.keys(json);
93-
if (keys.length === 0) return;
94-
95-
let statement = '{ ';
96-
statement += keys.map((it) => `${it}: ${json[it]}`).join(', ');
97-
statement += ' }';
98-
return statement;
99-
};
100-
101-
const importsPatch = {
102-
'double precision': 'doublePrecision',
103-
'timestamp without time zone': 'timestamp',
104-
} as Record<string, string>;
105-
10674
const relations = new Set<string>();
10775

10876
const escapeColumnKey = (value: string) => {
@@ -158,6 +126,7 @@ export const ddlToTypeScript = (
158126
...it,
159127
} as const;
160128
});
129+
161130
for (const it of [...ddl.entities.list(), ...viewEntities]) {
162131
if (it.entityType === 'indexes') imports.add(it.isUnique ? 'uniqueIndex' : 'index');
163132
if (it.entityType === 'fks') imports.add('foreignKey');
@@ -166,31 +135,9 @@ export const ddlToTypeScript = (
166135
if (it.entityType === 'views') imports.add('mysqlView');
167136

168137
if (it.entityType === 'columns' || it.entityType === 'viewColumn') {
169-
let patched = it.type;
170-
patched = patched.startsWith('varchar(') ? 'varchar' : patched;
171-
patched = patched.startsWith('char(') ? 'char' : patched;
172-
patched = patched.startsWith('binary(') ? 'binary' : patched;
173-
patched = patched.startsWith('decimal(') ? 'decimal' : patched;
174-
patched = patched.startsWith('smallint(') ? 'smallint' : patched;
175-
patched = patched.startsWith('enum(') ? 'mysqlEnum' : patched;
176-
patched = patched.startsWith('datetime(') ? 'datetime' : patched;
177-
patched = patched.startsWith('varbinary(') ? 'varbinary' : patched;
178-
patched = patched.startsWith('int(') ? 'int' : patched;
179-
patched = patched.startsWith('double(') ? 'double' : patched;
180-
patched = patched.startsWith('double unsigned') ? 'double' : patched;
181-
patched = patched.startsWith('float(') ? 'float' : patched;
182-
patched = patched.startsWith('float unsigned') ? 'float' : patched;
183-
patched = patched.startsWith('int unsigned') ? 'int' : patched;
184-
patched = patched === 'tinyint(1)' ? 'boolean' : patched;
185-
patched = patched.startsWith('tinyint(') ? 'tinyint' : patched;
186-
patched = patched.startsWith('tinyint unsigned') ? 'tinyint' : patched;
187-
patched = patched.startsWith('smallint unsigned') ? 'smallint' : patched;
188-
patched = patched.startsWith('mediumint unsigned') ? 'mediumint' : patched;
189-
patched = patched.startsWith('bigint unsigned') ? 'bigint' : patched;
190-
patched = patched.startsWith('time(') ? 'time' : patched;
191-
patched = patched.startsWith('timestamp(') ? 'timestamp' : patched;
192-
193-
if (mysqlImportsList.has(patched)) imports.add(patched);
138+
const grammarType=typeFor(it.type);
139+
if(grammarType)imports.add(grammarType.drizzleImport());
140+
if (mysqlImportsList.has(it.type)) imports.add(it.type);
194141
}
195142
}
196143

drizzle-kit/src/dialects/postgres/drizzle.ts

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ import {
6464
minRangeForIdentityBasedOn,
6565
splitSqlType,
6666
stringFromIdentityProperty,
67+
typeFor,
6768
} from './grammar';
6869

6970
export const policyFrom = (policy: PgPolicy | GelPolicy, dialect: PgDialect | GelDialect) => {
@@ -179,6 +180,17 @@ export const defaultFromColumn = (
179180
};
180181
}
181182

183+
const sqlTypeLowered = base.getSQLType().toLowerCase();
184+
const grammarType = typeFor(base.getSQLType());
185+
if (grammarType) {
186+
// if (dimensions > 0 && !Array.isArray(def)) return { value: String(def), type: 'unknown' };
187+
if (dimensions > 0 && Array.isArray(def)) {
188+
if (def.flat(5).length === 0) return { value: '[]', type: 'unknown' };
189+
return grammarType.defaultArrayFromDrizzle(def);
190+
}
191+
return grammarType.defaultFromDrizzle(def);
192+
}
193+
182194
if (is(base, PgLineABC)) {
183195
return {
184196
value: stringifyArray(def, 'sql', (x: { a: number; b: number; c: number }, depth: number) => {
@@ -223,7 +235,6 @@ export const defaultFromColumn = (
223235
return defaultForVector(def as any);
224236
}
225237

226-
const sqlTypeLowered = base.getSQLType().toLowerCase();
227238
if (sqlTypeLowered === 'jsonb' || sqlTypeLowered === 'json') {
228239
const value = dimensions > 0 && Array.isArray(def) ? buildArrayString(def, sqlTypeLowered) : JSON.stringify(def);
229240
return {
@@ -472,7 +483,6 @@ export const fromDrizzleSchema = (
472483

473484
const { baseColumn, dimensions, sqlType, baseType, options, typeSchema } = unwrapColumn(column);
474485
const columnDefault = defaultFromColumn(baseColumn, column.default, dimensions, dialect);
475-
console.log(columnDefault, column.default);
476486

477487
return {
478488
entityType: 'columns',

drizzle-kit/src/dialects/postgres/grammar.ts

Lines changed: 86 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,65 @@
1-
import { stringifyArray, stringifyTuplesArray, trimChar } from '../../utils';
1+
import { ArrayValue, stringifyArray, stringifyTuplesArray, trimChar } from '../../utils';
22
import { assertUnreachable } from '../../utils';
33
import { parseArray } from '../../utils/parse-pgarray';
44
import { hash } from '../common';
5-
import { Column, PostgresEntities } from './ddl';
5+
import type { Column, PostgresEntities } from './ddl';
6+
import type { Import } from './typescript';
7+
8+
export interface SqlType {
9+
is(type: string): boolean;
10+
drizzleImport(): Import;
11+
defaultFromDrizzle<MODE = unknown>(value: unknown, mode?: MODE): Column['default'];
12+
defaultArrayFromDrizzle<MODE = unknown>(value: any[], mode?: MODE): Column['default'];
13+
defaultFromIntrospect(value: string): Column['default'];
14+
defaultArrayFromIntrospect(value: ArrayValue): Column['default'];
15+
defaultToSQL(value: string): string;
16+
defaultArrayToSQL(value: any[]): string;
17+
toTs(type: string, value: string): { options?: Record<string, unknown>; default: string };
18+
toArrayTs(type: string, value: any[]): { options?: Record<string, unknown>; default: string };
19+
}
620

7-
const columnUnknown = {
8-
drizzleImport() {
9-
return 'unknown';
21+
export const SmallInt: SqlType = {
22+
is: (type: string) => /^\s*smallint(?:\s*\[\s*\])*\s*$/i.test(type),
23+
drizzleImport: () => 'smallint',
24+
defaultFromDrizzle: (value) => {
25+
return { value: String(value), type: 'unknown' };
1026
},
11-
canHandle(type: string) {
12-
return true;
27+
defaultArrayFromDrizzle: (value) => {
28+
return { value: JSON.stringify(value), type: 'unknown' };
1329
},
14-
15-
defaultFromDrizzle(it: any, dimensions: number): Column['default'] {
16-
return { type: 'unknown', value: String(it).replaceAll("'", "''").replaceAll('\\', '\\\\') };
30+
defaultFromIntrospect: (value) => {
31+
return { value: trimChar(value, "'"), type: 'unknown' }; // 10, but '-10'
1732
},
18-
19-
printToTypeScript(column: Column) {
20-
return `unknown('${column.name}').default(sql\`${
21-
column.default?.value.replaceAll("''", "'").replaceAll('\\\\', '\\')
22-
}\`)`;
33+
defaultArrayFromIntrospect: (value) => {
34+
const stringified = JSON.stringify(value, (_, v) => typeof v === 'string' ? Number(v) : v);
35+
return { value: stringified, type: 'unknown' };
2336
},
37+
defaultToSQL: (value) => value,
38+
defaultArrayToSQL: (value) => {
39+
return `'${stringifyArray(value, 'sql', (v) => String(v))}'`;
40+
},
41+
toTs: (_, value) => ({ default: value }),
42+
toArrayTs: (_, value) => ({ default: JSON.stringify(value) }),
43+
};
44+
45+
export const Int: SqlType = {
46+
is: (type: string) => /^\s*integer(?:\s*\[\s*\])*\s*$/i.test(type),
47+
drizzleImport: () => 'integer',
48+
defaultFromDrizzle: SmallInt.defaultFromDrizzle,
49+
defaultArrayFromDrizzle: SmallInt.defaultArrayFromDrizzle,
50+
defaultFromIntrospect: SmallInt.defaultFromIntrospect,
51+
defaultArrayFromIntrospect: SmallInt.defaultArrayFromIntrospect,
52+
defaultToSQL: SmallInt.defaultToSQL,
53+
defaultArrayToSQL: SmallInt.defaultArrayToSQL,
54+
toTs: SmallInt.toTs,
55+
toArrayTs: SmallInt.toArrayTs,
56+
};
57+
58+
export const typeFor = (type: string): SqlType | null => {
59+
if (SmallInt.is(type)) return SmallInt;
60+
if (Int.is(type)) return Int;
61+
console.log('nosqltype');
62+
return null;
2463
};
2564

2665
export const splitSqlType = (sqlType: string) => {
@@ -362,9 +401,25 @@ export const defaultForColumn = (
362401
return { type: 'number', value: String(def) };
363402
}
364403

365-
// trim ::type and []
366404
let value = trimDefaultValueSuffix(def);
367405

406+
const grammarType = typeFor(type);
407+
if (grammarType) {
408+
if (dimensions > 0) {
409+
try {
410+
let trimmed = value.startsWith('(') ? value.slice(1, value.length - 1) : value;
411+
trimmed = trimChar(trimmed, "'");
412+
const res = parseArray(trimmed);
413+
return grammarType.defaultArrayFromIntrospect(res);
414+
} catch {
415+
return { value, type: 'unknown' };
416+
}
417+
}
418+
return grammarType.defaultFromIntrospect(String(value));
419+
}
420+
421+
// trim ::type and []
422+
368423
if (type.startsWith('vector')) {
369424
return { value: value, type: 'unknown' };
370425
}
@@ -439,6 +494,21 @@ export const defaultToSQL = (
439494

440495
const suffix = arrsuffix ? `::${columnType}${arrsuffix}` : '';
441496

497+
const grammarType = typeFor(it.type);
498+
if (grammarType) {
499+
if (dimensions > 0) {
500+
try {
501+
const parsed = JSON.parse(it.default.value) as any[];
502+
if (parsed.flat(5).length === 0) return `'{}'${suffix}`;
503+
return `${grammarType.defaultArrayToSQL(parsed)}${suffix}`;
504+
} catch {
505+
return it.default;
506+
}
507+
}
508+
const value = grammarType.defaultToSQL(it.default.value);
509+
return `${value}${suffix}`;
510+
}
511+
442512
if (type === 'string') {
443513
return `'${value}'${suffix}`;
444514
}

drizzle-kit/src/dialects/postgres/introspect.ts

Lines changed: 26 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,8 @@ import type {
1313
Policy,
1414
PostgresEntities,
1515
PrimaryKey,
16-
Role,
1716
Privilege,
17+
Role,
1818
Schema,
1919
Sequence,
2020
UniqueConstraint,
@@ -412,7 +412,7 @@ export const fromDatabase = async (
412412
throw err;
413413
});
414414

415-
const rolesQuery = db.query<
415+
const rolesQuery = db.query<
416416
{
417417
rolname: string;
418418
rolsuper: boolean;
@@ -594,19 +594,28 @@ const rolesQuery = db.query<
594594
throw err;
595595
});
596596

597-
const [dependList, enumsList, serialsList, sequencesList, policiesList, rolesList, privilegesList, constraintsList, columnsList] =
598-
await Promise
599-
.all([
600-
dependQuery,
601-
enumsQuery,
602-
serialsQuery,
603-
sequencesQuery,
604-
policiesQuery,
605-
rolesQuery,
606-
privilegesQuery,
607-
constraintsQuery,
608-
columnsQuery,
609-
]);
597+
const [
598+
dependList,
599+
enumsList,
600+
serialsList,
601+
sequencesList,
602+
policiesList,
603+
rolesList,
604+
privilegesList,
605+
constraintsList,
606+
columnsList,
607+
] = await Promise
608+
.all([
609+
dependQuery,
610+
enumsQuery,
611+
serialsQuery,
612+
sequencesQuery,
613+
policiesQuery,
614+
rolesQuery,
615+
privilegesQuery,
616+
constraintsQuery,
617+
columnsQuery,
618+
]);
610619

611620
const groupedEnums = enumsList.reduce((acc, it) => {
612621
if (!(it.oid in acc)) {
@@ -711,7 +720,7 @@ const rolesQuery = db.query<
711720
table: privilege.table,
712721
type: privilege.type,
713722
isGrantable: privilege.isGrantable,
714-
})
723+
});
715724
}
716725

717726
for (const it of policiesList) {
@@ -1244,6 +1253,7 @@ export const fromDatabaseForDrizzle = async (
12441253
const res = await fromDatabase(db, tableFilter, schemaFilters, entities, progressCallback);
12451254
res.schemas = res.schemas.filter((it) => it.name !== 'public');
12461255
res.indexes = res.indexes.filter((it) => !it.forPK && !it.forUnique);
1256+
res.privileges = [];
12471257

12481258
return res;
12491259
};

0 commit comments

Comments
 (0)