bun-query-builder 0.2.19 → 0.2.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bin/cli.js +36 -74
- package/dist/drivers/mysql.d.ts +2 -2
- package/dist/drivers/postgres.d.ts +2 -2
- package/dist/migrations.d.ts +7 -1
- package/dist/src/index.js +35 -73
- package/package.json +1 -1
package/dist/bin/cli.js
CHANGED
|
@@ -17890,7 +17890,10 @@ async function buildPgTable(qb, table, enumLabels) {
|
|
|
17890
17890
|
WHERE t.relname = $1 AND t.relkind = 'r'
|
|
17891
17891
|
ORDER BY i.relname, ord`, [table]);
|
|
17892
17892
|
const fkRows = await qb.unsafe(`SELECT kcu.column_name, ccu.table_name AS ref_table, ccu.column_name AS ref_column,
|
|
17893
|
-
rc.delete_rule, rc.update_rule
|
|
17893
|
+
tc.constraint_name, rc.delete_rule, rc.update_rule,
|
|
17894
|
+
(SELECT COUNT(*) FROM information_schema.key_column_usage count_kcu
|
|
17895
|
+
WHERE count_kcu.constraint_name = tc.constraint_name
|
|
17896
|
+
AND count_kcu.constraint_schema = tc.constraint_schema) AS constraint_column_count
|
|
17894
17897
|
FROM information_schema.table_constraints tc
|
|
17895
17898
|
JOIN information_schema.key_column_usage kcu ON kcu.constraint_name = tc.constraint_name
|
|
17896
17899
|
JOIN information_schema.constraint_column_usage ccu ON ccu.constraint_name = tc.constraint_name
|
|
@@ -17898,11 +17901,15 @@ async function buildPgTable(qb, table, enumLabels) {
|
|
|
17898
17901
|
WHERE tc.constraint_type = 'FOREIGN KEY' AND tc.table_name = $1 AND tc.table_schema = 'public'`, [table]);
|
|
17899
17902
|
const fkByColumn = new Map;
|
|
17900
17903
|
for (const fk of fkRows) {
|
|
17901
|
-
|
|
17904
|
+
const name = String(fk.column_name);
|
|
17905
|
+
const existing = fkByColumn.get(name);
|
|
17906
|
+
const constraintNames = Number(fk.constraint_column_count) === 1 ? [...new Set([...existing?.constraintNames ?? [], String(fk.constraint_name)])] : existing?.constraintNames;
|
|
17907
|
+
fkByColumn.set(name, existing ? { ...existing, constraintNames } : {
|
|
17902
17908
|
table: String(fk.ref_table),
|
|
17903
17909
|
column: String(fk.ref_column ?? "id"),
|
|
17904
17910
|
onDelete: asAction(fk.delete_rule),
|
|
17905
|
-
onUpdate: asAction(fk.update_rule)
|
|
17911
|
+
onUpdate: asAction(fk.update_rule),
|
|
17912
|
+
constraintNames
|
|
17906
17913
|
});
|
|
17907
17914
|
}
|
|
17908
17915
|
const { indexes, uniqueColumns } = groupPhysicalIndexes(table, idxRows.map((r) => ({
|
|
@@ -17941,18 +17948,27 @@ async function buildMysqlTable(qb, table) {
|
|
|
17941
17948
|
WHERE table_name = ? AND table_schema = DATABASE()
|
|
17942
17949
|
ORDER BY index_name, seq_in_index`, [table]);
|
|
17943
17950
|
const fkRows = await qb.unsafe(`SELECT kcu.column_name, kcu.referenced_table_name AS ref_table, kcu.referenced_column_name AS ref_column,
|
|
17944
|
-
rc.delete_rule, rc.update_rule
|
|
17951
|
+
kcu.constraint_name, rc.delete_rule, rc.update_rule,
|
|
17952
|
+
(SELECT COUNT(*) FROM information_schema.key_column_usage count_kcu
|
|
17953
|
+
WHERE count_kcu.constraint_name = kcu.constraint_name
|
|
17954
|
+
AND count_kcu.constraint_schema = kcu.constraint_schema) AS constraint_column_count
|
|
17945
17955
|
FROM information_schema.key_column_usage kcu
|
|
17946
17956
|
JOIN information_schema.referential_constraints rc
|
|
17947
17957
|
ON rc.constraint_name = kcu.constraint_name AND rc.constraint_schema = kcu.table_schema
|
|
17948
17958
|
WHERE kcu.table_name = ? AND kcu.table_schema = DATABASE() AND kcu.referenced_table_name IS NOT NULL`, [table]);
|
|
17949
17959
|
const fkByColumn = new Map;
|
|
17950
17960
|
for (const fk of fkRows) {
|
|
17951
|
-
|
|
17961
|
+
const name = String(fk.column_name ?? fk.COLUMN_NAME);
|
|
17962
|
+
const existing = fkByColumn.get(name);
|
|
17963
|
+
const columnCount = Number(fk.constraint_column_count ?? fk.CONSTRAINT_COLUMN_COUNT);
|
|
17964
|
+
const constraintName = String(fk.constraint_name ?? fk.CONSTRAINT_NAME);
|
|
17965
|
+
const constraintNames = columnCount === 1 ? [...new Set([...existing?.constraintNames ?? [], constraintName])] : existing?.constraintNames;
|
|
17966
|
+
fkByColumn.set(name, existing ? { ...existing, constraintNames } : {
|
|
17952
17967
|
table: String(fk.ref_table ?? fk.REF_TABLE),
|
|
17953
17968
|
column: String(fk.ref_column ?? fk.REF_COLUMN ?? "id"),
|
|
17954
17969
|
onDelete: asAction(fk.delete_rule ?? fk.DELETE_RULE),
|
|
17955
|
-
onUpdate: asAction(fk.update_rule ?? fk.UPDATE_RULE)
|
|
17970
|
+
onUpdate: asAction(fk.update_rule ?? fk.UPDATE_RULE),
|
|
17971
|
+
constraintNames
|
|
17956
17972
|
});
|
|
17957
17973
|
}
|
|
17958
17974
|
const { indexes, uniqueColumns } = groupPhysicalIndexes(table, idxRows.map((r) => ({
|
|
@@ -18213,49 +18229,17 @@ class MySQLDriver {
|
|
|
18213
18229
|
const columns = index.columns.map((c) => this.quoteIdentifier(c)).join(", ");
|
|
18214
18230
|
return `CREATE ${kind}INDEX ${this.quoteIdentifier(idxName)} ON ${this.quoteIdentifier(tableName)} (${columns});`;
|
|
18215
18231
|
}
|
|
18216
|
-
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate) {
|
|
18232
|
+
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate, existingConstraintNames = []) {
|
|
18217
18233
|
const fkName = `${tableName}_${columnName}_fk`;
|
|
18218
18234
|
let sql = `ALTER TABLE ${this.quoteIdentifier(tableName)} ADD CONSTRAINT ${this.quoteIdentifier(fkName)} FOREIGN KEY (${this.quoteIdentifier(columnName)}) REFERENCES ${this.quoteIdentifier(refTable)}(${this.quoteIdentifier(refColumn)})`;
|
|
18219
18235
|
if (onDelete)
|
|
18220
18236
|
sql += ` ON DELETE ${onDelete.toUpperCase()}`;
|
|
18221
18237
|
if (onUpdate)
|
|
18222
18238
|
sql += ` ON UPDATE ${onUpdate.toUpperCase()}`;
|
|
18223
|
-
|
|
18224
|
-
|
|
18225
|
-
|
|
18226
|
-
|
|
18227
|
-
const table = this.quoteLiteral(tableName);
|
|
18228
|
-
const column = this.quoteLiteral(columnName);
|
|
18229
|
-
return `SET @drop_fks := (
|
|
18230
|
-
SELECT CONCAT(
|
|
18231
|
-
'ALTER TABLE \`', ${table}, '\` DROP FOREIGN KEY \`',
|
|
18232
|
-
GROUP_CONCAT(kcu.CONSTRAINT_NAME SEPARATOR '\`, DROP FOREIGN KEY \`'),
|
|
18233
|
-
'\`'
|
|
18234
|
-
)
|
|
18235
|
-
FROM information_schema.KEY_COLUMN_USAGE kcu
|
|
18236
|
-
WHERE kcu.TABLE_SCHEMA = DATABASE()
|
|
18237
|
-
AND kcu.TABLE_NAME = ${table}
|
|
18238
|
-
AND kcu.COLUMN_NAME = ${column}
|
|
18239
|
-
AND kcu.REFERENCED_TABLE_NAME IS NOT NULL
|
|
18240
|
-
AND kcu.CONSTRAINT_NAME IN (
|
|
18241
|
-
SELECT single.CONSTRAINT_NAME FROM (
|
|
18242
|
-
SELECT inner_kcu.CONSTRAINT_NAME
|
|
18243
|
-
FROM information_schema.KEY_COLUMN_USAGE inner_kcu
|
|
18244
|
-
WHERE inner_kcu.TABLE_SCHEMA = DATABASE()
|
|
18245
|
-
AND inner_kcu.TABLE_NAME = ${table}
|
|
18246
|
-
AND inner_kcu.REFERENCED_TABLE_NAME IS NOT NULL
|
|
18247
|
-
GROUP BY inner_kcu.CONSTRAINT_NAME
|
|
18248
|
-
HAVING COUNT(*) = 1
|
|
18249
|
-
) AS single
|
|
18250
|
-
)
|
|
18251
|
-
);
|
|
18252
|
-
SET @drop_fks := IFNULL(@drop_fks, 'SELECT 1');
|
|
18253
|
-
PREPARE drop_fks_stmt FROM @drop_fks;
|
|
18254
|
-
EXECUTE drop_fks_stmt;
|
|
18255
|
-
DEALLOCATE PREPARE drop_fks_stmt;`;
|
|
18256
|
-
}
|
|
18257
|
-
quoteLiteral(value) {
|
|
18258
|
-
return `'${value.replace(/'/g, "''")}'`;
|
|
18239
|
+
const drops = [...new Set(existingConstraintNames)].map((name) => `ALTER TABLE ${this.quoteIdentifier(tableName)} DROP FOREIGN KEY ${this.quoteIdentifier(name)};`).join(`
|
|
18240
|
+
`);
|
|
18241
|
+
return drops ? `${drops}
|
|
18242
|
+
${sql};` : `${sql};`;
|
|
18259
18243
|
}
|
|
18260
18244
|
addColumn(tableName, column) {
|
|
18261
18245
|
const typeSql = this.getColumnType(column);
|
|
@@ -18438,41 +18422,17 @@ class PostgresDriver {
|
|
|
18438
18422
|
const where = index.where ? ` WHERE ${index.where}` : "";
|
|
18439
18423
|
return `CREATE ${kind}INDEX IF NOT EXISTS ${this.quoteIdentifier(idxName)} ON ${this.quoteIdentifier(tableName)} (${columns})${where};`;
|
|
18440
18424
|
}
|
|
18441
|
-
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate) {
|
|
18425
|
+
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate, existingConstraintNames = []) {
|
|
18442
18426
|
const fkName = `${tableName}_${columnName}_fk`;
|
|
18443
18427
|
let sql = `ALTER TABLE ${this.quoteIdentifier(tableName)} ADD CONSTRAINT ${this.quoteIdentifier(fkName)} FOREIGN KEY (${this.quoteIdentifier(columnName)}) REFERENCES ${this.quoteIdentifier(refTable)}(${this.quoteIdentifier(refColumn)})`;
|
|
18444
18428
|
if (onDelete)
|
|
18445
18429
|
sql += ` ON DELETE ${onDelete.toUpperCase()}`;
|
|
18446
18430
|
if (onUpdate)
|
|
18447
18431
|
sql += ` ON UPDATE ${onUpdate.toUpperCase()}`;
|
|
18448
|
-
|
|
18449
|
-
|
|
18450
|
-
|
|
18451
|
-
|
|
18452
|
-
const table = this.quoteLiteral(tableName);
|
|
18453
|
-
const column = this.quoteLiteral(columnName);
|
|
18454
|
-
return `DO $$
|
|
18455
|
-
DECLARE existing_name text;
|
|
18456
|
-
BEGIN
|
|
18457
|
-
FOR existing_name IN
|
|
18458
|
-
SELECT con.conname
|
|
18459
|
-
FROM pg_constraint con
|
|
18460
|
-
JOIN pg_class rel ON rel.oid = con.conrelid
|
|
18461
|
-
JOIN pg_namespace nsp ON nsp.oid = rel.relnamespace
|
|
18462
|
-
WHERE con.contype = 'f'
|
|
18463
|
-
AND rel.relname = ${table}
|
|
18464
|
-
AND nsp.nspname = current_schema()
|
|
18465
|
-
AND con.conkey = ARRAY[(
|
|
18466
|
-
SELECT att.attnum FROM pg_attribute att
|
|
18467
|
-
WHERE att.attrelid = rel.oid AND att.attname = ${column} AND att.attnum > 0
|
|
18468
|
-
)]::smallint[]
|
|
18469
|
-
LOOP
|
|
18470
|
-
EXECUTE format('ALTER TABLE %I DROP CONSTRAINT %I', ${table}, existing_name);
|
|
18471
|
-
END LOOP;
|
|
18472
|
-
END $$;`;
|
|
18473
|
-
}
|
|
18474
|
-
quoteLiteral(value) {
|
|
18475
|
-
return `'${value.replace(/'/g, "''")}'`;
|
|
18432
|
+
const drops = [...new Set(existingConstraintNames)].map((name) => `ALTER TABLE ${this.quoteIdentifier(tableName)} DROP CONSTRAINT ${this.quoteIdentifier(name)};`).join(`
|
|
18433
|
+
`);
|
|
18434
|
+
return drops ? `${drops}
|
|
18435
|
+
${sql};` : `${sql};`;
|
|
18476
18436
|
}
|
|
18477
18437
|
addColumn(tableName, column) {
|
|
18478
18438
|
const typeSql = this.getColumnType(column);
|
|
@@ -29271,6 +29231,8 @@ function referencesAreDifferent(r1, r2) {
|
|
|
29271
29231
|
return true;
|
|
29272
29232
|
if (!r1 || !r2)
|
|
29273
29233
|
return false;
|
|
29234
|
+
if ((r1.constraintNames?.length ?? 0) > 1)
|
|
29235
|
+
return true;
|
|
29274
29236
|
const act = (a2) => (a2 ?? "no action").toLowerCase();
|
|
29275
29237
|
return r1.table !== r2.table || r1.column !== r2.column || act(r1.onDelete) !== act(r2.onDelete) || act(r1.onUpdate) !== act(r2.onUpdate);
|
|
29276
29238
|
}
|
|
@@ -29518,7 +29480,7 @@ function generateDiffOperations(previous, next, opts = {}) {
|
|
|
29518
29480
|
const currCol = currCols[colName];
|
|
29519
29481
|
if (!currCol.references)
|
|
29520
29482
|
continue;
|
|
29521
|
-
const addFkStatement = driver.addForeignKey(curr.table, currCol.name, currCol.references.table, currCol.references.column, currCol.references.onDelete, currCol.references.onUpdate);
|
|
29483
|
+
const addFkStatement = driver.addForeignKey(curr.table, currCol.name, currCol.references.table, currCol.references.column, currCol.references.onDelete, currCol.references.onUpdate, prevCols[colName].references?.constraintNames);
|
|
29522
29484
|
if (!addFkStatement)
|
|
29523
29485
|
continue;
|
|
29524
29486
|
tableChanges.push(addFkStatement);
|
|
@@ -31668,7 +31630,7 @@ function getPrefix() {
|
|
|
31668
31630
|
}
|
|
31669
31631
|
var prefix = getPrefix();
|
|
31670
31632
|
// package.json
|
|
31671
|
-
var version2 = "0.2.
|
|
31633
|
+
var version2 = "0.2.20";
|
|
31672
31634
|
|
|
31673
31635
|
// bin/cli.ts
|
|
31674
31636
|
init_actions();
|
package/dist/drivers/mysql.d.ts
CHANGED
|
@@ -3,7 +3,7 @@ export declare interface DialectDriver {
|
|
|
3
3
|
createEnumType: (enumTypeName: string, values: string[]) => string
|
|
4
4
|
createTable: (table: TablePlan) => string
|
|
5
5
|
createIndex: (tableName: string, index: IndexPlan) => string
|
|
6
|
-
addForeignKey: (tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string) => string
|
|
6
|
+
addForeignKey: (tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string, existingConstraintNames?: string[]) => string
|
|
7
7
|
addColumn: (tableName: string, column: ColumnPlan) => string
|
|
8
8
|
modifyColumn: (tableName: string, column: ColumnPlan) => string
|
|
9
9
|
renameColumn: (tableName: string, from: string, to: string) => string
|
|
@@ -26,7 +26,7 @@ export declare class MySQLDriver implements DialectDriver {
|
|
|
26
26
|
createEnumType(_enumTypeName: string, _values: string[]): string;
|
|
27
27
|
createTable(table: TablePlan): string;
|
|
28
28
|
createIndex(tableName: string, index: IndexPlan): string;
|
|
29
|
-
addForeignKey(tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string): string;
|
|
29
|
+
addForeignKey(tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string, existingConstraintNames?: string[]): string;
|
|
30
30
|
addColumn(tableName: string, column: ColumnPlan): string;
|
|
31
31
|
modifyColumn(tableName: string, column: ColumnPlan): string;
|
|
32
32
|
renameColumn(tableName: string, from: string, to: string): string;
|
|
@@ -3,7 +3,7 @@ export declare interface DialectDriver {
|
|
|
3
3
|
createEnumType: (enumTypeName: string, values: string[]) => string
|
|
4
4
|
createTable: (table: TablePlan) => string
|
|
5
5
|
createIndex: (tableName: string, index: IndexPlan) => string
|
|
6
|
-
addForeignKey: (tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string) => string
|
|
6
|
+
addForeignKey: (tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string, existingConstraintNames?: string[]) => string
|
|
7
7
|
addColumn: (tableName: string, column: ColumnPlan) => string
|
|
8
8
|
modifyColumn: (tableName: string, column: ColumnPlan) => string
|
|
9
9
|
renameColumn: (tableName: string, from: string, to: string) => string
|
|
@@ -21,7 +21,7 @@ export declare class PostgresDriver implements DialectDriver {
|
|
|
21
21
|
createEnumType(enumTypeName: string, values: string[]): string;
|
|
22
22
|
createTable(table: TablePlan): string;
|
|
23
23
|
createIndex(tableName: string, index: IndexPlan): string;
|
|
24
|
-
addForeignKey(tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string): string;
|
|
24
|
+
addForeignKey(tableName: string, columnName: string, refTable: string, refColumn: string, onDelete?: string, onUpdate?: string, existingConstraintNames?: string[]): string;
|
|
25
25
|
addColumn(tableName: string, column: ColumnPlan): string;
|
|
26
26
|
modifyColumn(tableName: string, column: ColumnPlan): string;
|
|
27
27
|
renameColumn(tableName: string, from: string, to: string): string;
|
package/dist/migrations.d.ts
CHANGED
|
@@ -91,7 +91,13 @@ export declare interface ColumnPlan {
|
|
|
91
91
|
isNullable: boolean
|
|
92
92
|
hasDefault: boolean
|
|
93
93
|
defaultValue?: PrimitiveDefault
|
|
94
|
-
references?: {
|
|
94
|
+
references?: {
|
|
95
|
+
table: string
|
|
96
|
+
column: string
|
|
97
|
+
onDelete?: OnForeignKeyAction
|
|
98
|
+
onUpdate?: OnForeignKeyAction
|
|
99
|
+
constraintNames?: string[]
|
|
100
|
+
}
|
|
95
101
|
enumValues?: string[]
|
|
96
102
|
maxLength?: number
|
|
97
103
|
enumTypeName?: string
|
package/dist/src/index.js
CHANGED
|
@@ -17889,7 +17889,10 @@ async function buildPgTable(qb, table, enumLabels) {
|
|
|
17889
17889
|
WHERE t.relname = $1 AND t.relkind = 'r'
|
|
17890
17890
|
ORDER BY i.relname, ord`, [table]);
|
|
17891
17891
|
const fkRows = await qb.unsafe(`SELECT kcu.column_name, ccu.table_name AS ref_table, ccu.column_name AS ref_column,
|
|
17892
|
-
rc.delete_rule, rc.update_rule
|
|
17892
|
+
tc.constraint_name, rc.delete_rule, rc.update_rule,
|
|
17893
|
+
(SELECT COUNT(*) FROM information_schema.key_column_usage count_kcu
|
|
17894
|
+
WHERE count_kcu.constraint_name = tc.constraint_name
|
|
17895
|
+
AND count_kcu.constraint_schema = tc.constraint_schema) AS constraint_column_count
|
|
17893
17896
|
FROM information_schema.table_constraints tc
|
|
17894
17897
|
JOIN information_schema.key_column_usage kcu ON kcu.constraint_name = tc.constraint_name
|
|
17895
17898
|
JOIN information_schema.constraint_column_usage ccu ON ccu.constraint_name = tc.constraint_name
|
|
@@ -17897,11 +17900,15 @@ async function buildPgTable(qb, table, enumLabels) {
|
|
|
17897
17900
|
WHERE tc.constraint_type = 'FOREIGN KEY' AND tc.table_name = $1 AND tc.table_schema = 'public'`, [table]);
|
|
17898
17901
|
const fkByColumn = new Map;
|
|
17899
17902
|
for (const fk of fkRows) {
|
|
17900
|
-
|
|
17903
|
+
const name = String(fk.column_name);
|
|
17904
|
+
const existing = fkByColumn.get(name);
|
|
17905
|
+
const constraintNames = Number(fk.constraint_column_count) === 1 ? [...new Set([...existing?.constraintNames ?? [], String(fk.constraint_name)])] : existing?.constraintNames;
|
|
17906
|
+
fkByColumn.set(name, existing ? { ...existing, constraintNames } : {
|
|
17901
17907
|
table: String(fk.ref_table),
|
|
17902
17908
|
column: String(fk.ref_column ?? "id"),
|
|
17903
17909
|
onDelete: asAction(fk.delete_rule),
|
|
17904
|
-
onUpdate: asAction(fk.update_rule)
|
|
17910
|
+
onUpdate: asAction(fk.update_rule),
|
|
17911
|
+
constraintNames
|
|
17905
17912
|
});
|
|
17906
17913
|
}
|
|
17907
17914
|
const { indexes, uniqueColumns } = groupPhysicalIndexes(table, idxRows.map((r) => ({
|
|
@@ -17940,18 +17947,27 @@ async function buildMysqlTable(qb, table) {
|
|
|
17940
17947
|
WHERE table_name = ? AND table_schema = DATABASE()
|
|
17941
17948
|
ORDER BY index_name, seq_in_index`, [table]);
|
|
17942
17949
|
const fkRows = await qb.unsafe(`SELECT kcu.column_name, kcu.referenced_table_name AS ref_table, kcu.referenced_column_name AS ref_column,
|
|
17943
|
-
rc.delete_rule, rc.update_rule
|
|
17950
|
+
kcu.constraint_name, rc.delete_rule, rc.update_rule,
|
|
17951
|
+
(SELECT COUNT(*) FROM information_schema.key_column_usage count_kcu
|
|
17952
|
+
WHERE count_kcu.constraint_name = kcu.constraint_name
|
|
17953
|
+
AND count_kcu.constraint_schema = kcu.constraint_schema) AS constraint_column_count
|
|
17944
17954
|
FROM information_schema.key_column_usage kcu
|
|
17945
17955
|
JOIN information_schema.referential_constraints rc
|
|
17946
17956
|
ON rc.constraint_name = kcu.constraint_name AND rc.constraint_schema = kcu.table_schema
|
|
17947
17957
|
WHERE kcu.table_name = ? AND kcu.table_schema = DATABASE() AND kcu.referenced_table_name IS NOT NULL`, [table]);
|
|
17948
17958
|
const fkByColumn = new Map;
|
|
17949
17959
|
for (const fk of fkRows) {
|
|
17950
|
-
|
|
17960
|
+
const name = String(fk.column_name ?? fk.COLUMN_NAME);
|
|
17961
|
+
const existing = fkByColumn.get(name);
|
|
17962
|
+
const columnCount = Number(fk.constraint_column_count ?? fk.CONSTRAINT_COLUMN_COUNT);
|
|
17963
|
+
const constraintName = String(fk.constraint_name ?? fk.CONSTRAINT_NAME);
|
|
17964
|
+
const constraintNames = columnCount === 1 ? [...new Set([...existing?.constraintNames ?? [], constraintName])] : existing?.constraintNames;
|
|
17965
|
+
fkByColumn.set(name, existing ? { ...existing, constraintNames } : {
|
|
17951
17966
|
table: String(fk.ref_table ?? fk.REF_TABLE),
|
|
17952
17967
|
column: String(fk.ref_column ?? fk.REF_COLUMN ?? "id"),
|
|
17953
17968
|
onDelete: asAction(fk.delete_rule ?? fk.DELETE_RULE),
|
|
17954
|
-
onUpdate: asAction(fk.update_rule ?? fk.UPDATE_RULE)
|
|
17969
|
+
onUpdate: asAction(fk.update_rule ?? fk.UPDATE_RULE),
|
|
17970
|
+
constraintNames
|
|
17955
17971
|
});
|
|
17956
17972
|
}
|
|
17957
17973
|
const { indexes, uniqueColumns } = groupPhysicalIndexes(table, idxRows.map((r) => ({
|
|
@@ -18212,49 +18228,17 @@ class MySQLDriver {
|
|
|
18212
18228
|
const columns = index.columns.map((c) => this.quoteIdentifier(c)).join(", ");
|
|
18213
18229
|
return `CREATE ${kind}INDEX ${this.quoteIdentifier(idxName)} ON ${this.quoteIdentifier(tableName)} (${columns});`;
|
|
18214
18230
|
}
|
|
18215
|
-
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate) {
|
|
18231
|
+
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate, existingConstraintNames = []) {
|
|
18216
18232
|
const fkName = `${tableName}_${columnName}_fk`;
|
|
18217
18233
|
let sql = `ALTER TABLE ${this.quoteIdentifier(tableName)} ADD CONSTRAINT ${this.quoteIdentifier(fkName)} FOREIGN KEY (${this.quoteIdentifier(columnName)}) REFERENCES ${this.quoteIdentifier(refTable)}(${this.quoteIdentifier(refColumn)})`;
|
|
18218
18234
|
if (onDelete)
|
|
18219
18235
|
sql += ` ON DELETE ${onDelete.toUpperCase()}`;
|
|
18220
18236
|
if (onUpdate)
|
|
18221
18237
|
sql += ` ON UPDATE ${onUpdate.toUpperCase()}`;
|
|
18222
|
-
|
|
18223
|
-
|
|
18224
|
-
|
|
18225
|
-
|
|
18226
|
-
const table = this.quoteLiteral(tableName);
|
|
18227
|
-
const column = this.quoteLiteral(columnName);
|
|
18228
|
-
return `SET @drop_fks := (
|
|
18229
|
-
SELECT CONCAT(
|
|
18230
|
-
'ALTER TABLE \`', ${table}, '\` DROP FOREIGN KEY \`',
|
|
18231
|
-
GROUP_CONCAT(kcu.CONSTRAINT_NAME SEPARATOR '\`, DROP FOREIGN KEY \`'),
|
|
18232
|
-
'\`'
|
|
18233
|
-
)
|
|
18234
|
-
FROM information_schema.KEY_COLUMN_USAGE kcu
|
|
18235
|
-
WHERE kcu.TABLE_SCHEMA = DATABASE()
|
|
18236
|
-
AND kcu.TABLE_NAME = ${table}
|
|
18237
|
-
AND kcu.COLUMN_NAME = ${column}
|
|
18238
|
-
AND kcu.REFERENCED_TABLE_NAME IS NOT NULL
|
|
18239
|
-
AND kcu.CONSTRAINT_NAME IN (
|
|
18240
|
-
SELECT single.CONSTRAINT_NAME FROM (
|
|
18241
|
-
SELECT inner_kcu.CONSTRAINT_NAME
|
|
18242
|
-
FROM information_schema.KEY_COLUMN_USAGE inner_kcu
|
|
18243
|
-
WHERE inner_kcu.TABLE_SCHEMA = DATABASE()
|
|
18244
|
-
AND inner_kcu.TABLE_NAME = ${table}
|
|
18245
|
-
AND inner_kcu.REFERENCED_TABLE_NAME IS NOT NULL
|
|
18246
|
-
GROUP BY inner_kcu.CONSTRAINT_NAME
|
|
18247
|
-
HAVING COUNT(*) = 1
|
|
18248
|
-
) AS single
|
|
18249
|
-
)
|
|
18250
|
-
);
|
|
18251
|
-
SET @drop_fks := IFNULL(@drop_fks, 'SELECT 1');
|
|
18252
|
-
PREPARE drop_fks_stmt FROM @drop_fks;
|
|
18253
|
-
EXECUTE drop_fks_stmt;
|
|
18254
|
-
DEALLOCATE PREPARE drop_fks_stmt;`;
|
|
18255
|
-
}
|
|
18256
|
-
quoteLiteral(value) {
|
|
18257
|
-
return `'${value.replace(/'/g, "''")}'`;
|
|
18238
|
+
const drops = [...new Set(existingConstraintNames)].map((name) => `ALTER TABLE ${this.quoteIdentifier(tableName)} DROP FOREIGN KEY ${this.quoteIdentifier(name)};`).join(`
|
|
18239
|
+
`);
|
|
18240
|
+
return drops ? `${drops}
|
|
18241
|
+
${sql};` : `${sql};`;
|
|
18258
18242
|
}
|
|
18259
18243
|
addColumn(tableName, column) {
|
|
18260
18244
|
const typeSql = this.getColumnType(column);
|
|
@@ -18437,41 +18421,17 @@ class PostgresDriver {
|
|
|
18437
18421
|
const where = index.where ? ` WHERE ${index.where}` : "";
|
|
18438
18422
|
return `CREATE ${kind}INDEX IF NOT EXISTS ${this.quoteIdentifier(idxName)} ON ${this.quoteIdentifier(tableName)} (${columns})${where};`;
|
|
18439
18423
|
}
|
|
18440
|
-
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate) {
|
|
18424
|
+
addForeignKey(tableName, columnName, refTable, refColumn, onDelete, onUpdate, existingConstraintNames = []) {
|
|
18441
18425
|
const fkName = `${tableName}_${columnName}_fk`;
|
|
18442
18426
|
let sql = `ALTER TABLE ${this.quoteIdentifier(tableName)} ADD CONSTRAINT ${this.quoteIdentifier(fkName)} FOREIGN KEY (${this.quoteIdentifier(columnName)}) REFERENCES ${this.quoteIdentifier(refTable)}(${this.quoteIdentifier(refColumn)})`;
|
|
18443
18427
|
if (onDelete)
|
|
18444
18428
|
sql += ` ON DELETE ${onDelete.toUpperCase()}`;
|
|
18445
18429
|
if (onUpdate)
|
|
18446
18430
|
sql += ` ON UPDATE ${onUpdate.toUpperCase()}`;
|
|
18447
|
-
|
|
18448
|
-
|
|
18449
|
-
|
|
18450
|
-
|
|
18451
|
-
const table = this.quoteLiteral(tableName);
|
|
18452
|
-
const column = this.quoteLiteral(columnName);
|
|
18453
|
-
return `DO $$
|
|
18454
|
-
DECLARE existing_name text;
|
|
18455
|
-
BEGIN
|
|
18456
|
-
FOR existing_name IN
|
|
18457
|
-
SELECT con.conname
|
|
18458
|
-
FROM pg_constraint con
|
|
18459
|
-
JOIN pg_class rel ON rel.oid = con.conrelid
|
|
18460
|
-
JOIN pg_namespace nsp ON nsp.oid = rel.relnamespace
|
|
18461
|
-
WHERE con.contype = 'f'
|
|
18462
|
-
AND rel.relname = ${table}
|
|
18463
|
-
AND nsp.nspname = current_schema()
|
|
18464
|
-
AND con.conkey = ARRAY[(
|
|
18465
|
-
SELECT att.attnum FROM pg_attribute att
|
|
18466
|
-
WHERE att.attrelid = rel.oid AND att.attname = ${column} AND att.attnum > 0
|
|
18467
|
-
)]::smallint[]
|
|
18468
|
-
LOOP
|
|
18469
|
-
EXECUTE format('ALTER TABLE %I DROP CONSTRAINT %I', ${table}, existing_name);
|
|
18470
|
-
END LOOP;
|
|
18471
|
-
END $$;`;
|
|
18472
|
-
}
|
|
18473
|
-
quoteLiteral(value) {
|
|
18474
|
-
return `'${value.replace(/'/g, "''")}'`;
|
|
18431
|
+
const drops = [...new Set(existingConstraintNames)].map((name) => `ALTER TABLE ${this.quoteIdentifier(tableName)} DROP CONSTRAINT ${this.quoteIdentifier(name)};`).join(`
|
|
18432
|
+
`);
|
|
18433
|
+
return drops ? `${drops}
|
|
18434
|
+
${sql};` : `${sql};`;
|
|
18475
18435
|
}
|
|
18476
18436
|
addColumn(tableName, column) {
|
|
18477
18437
|
const typeSql = this.getColumnType(column);
|
|
@@ -29270,6 +29230,8 @@ function referencesAreDifferent(r1, r2) {
|
|
|
29270
29230
|
return true;
|
|
29271
29231
|
if (!r1 || !r2)
|
|
29272
29232
|
return false;
|
|
29233
|
+
if ((r1.constraintNames?.length ?? 0) > 1)
|
|
29234
|
+
return true;
|
|
29273
29235
|
const act = (a2) => (a2 ?? "no action").toLowerCase();
|
|
29274
29236
|
return r1.table !== r2.table || r1.column !== r2.column || act(r1.onDelete) !== act(r2.onDelete) || act(r1.onUpdate) !== act(r2.onUpdate);
|
|
29275
29237
|
}
|
|
@@ -29517,7 +29479,7 @@ function generateDiffOperations(previous, next, opts = {}) {
|
|
|
29517
29479
|
const currCol = currCols[colName];
|
|
29518
29480
|
if (!currCol.references)
|
|
29519
29481
|
continue;
|
|
29520
|
-
const addFkStatement = driver.addForeignKey(curr.table, currCol.name, currCol.references.table, currCol.references.column, currCol.references.onDelete, currCol.references.onUpdate);
|
|
29482
|
+
const addFkStatement = driver.addForeignKey(curr.table, currCol.name, currCol.references.table, currCol.references.column, currCol.references.onDelete, currCol.references.onUpdate, prevCols[colName].references?.constraintNames);
|
|
29521
29483
|
if (!addFkStatement)
|
|
29522
29484
|
continue;
|
|
29523
29485
|
tableChanges.push(addFkStatement);
|
package/package.json
CHANGED