@elizaos/plugin-sql 2.0.0-alpha.17 → 2.0.0-alpha.18

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.
@@ -1036,170 +1036,533 @@ var init_rls = __esm(() => {
1036
1036
  init_server();
1037
1037
  });
1038
1038
 
1039
- // runtime-migrator/drizzle-adapters/diff-calculator.ts
1040
- var exports_diff_calculator = {};
1041
- __export(exports_diff_calculator, {
1042
- hasDiffChanges: () => hasDiffChanges,
1043
- calculateDiff: () => calculateDiff
1044
- });
1045
- function normalizeType(type) {
1046
- if (!type)
1047
- return "";
1048
- const normalized = type.toLowerCase().trim();
1049
- if (normalized === "timestamp without time zone" || normalized === "timestamp with time zone") {
1050
- return "timestamp";
1051
- }
1052
- if (normalized === "serial") {
1053
- return "integer";
1054
- }
1055
- if (normalized === "bigserial") {
1056
- return "bigint";
1057
- }
1058
- if (normalized === "smallserial") {
1059
- return "smallint";
1060
- }
1061
- if (normalized.startsWith("numeric") || normalized.startsWith("decimal")) {
1062
- const match = normalized.match(/\((\d+)(?:,\s*(\d+))?\)/);
1063
- if (match) {
1064
- return `numeric(${match[1]}${match[2] ? `,${match[2]}` : ""})`;
1065
- }
1066
- return "numeric";
1067
- }
1068
- if (normalized.startsWith("character varying")) {
1069
- return normalized.replace("character varying", "varchar");
1070
- }
1071
- if (normalized === "text[]" || normalized === "_text") {
1072
- return "text[]";
1039
+ // runtime-migrator/crypto-utils.ts
1040
+ function extendedHash(str) {
1041
+ const h1 = hashWithSeed(str, 5381);
1042
+ const h2 = hashWithSeed(str, 7919);
1043
+ const h3 = hashWithSeed(str, 104729);
1044
+ const h4 = hashWithSeed(str, 224737);
1045
+ return h1 + h2 + h3 + h4;
1046
+ }
1047
+ function hashWithSeed(str, seed) {
1048
+ let hash = seed;
1049
+ for (let i = 0;i < str.length; i++) {
1050
+ hash = hash * 33 ^ str.charCodeAt(i);
1073
1051
  }
1074
- return normalized;
1052
+ return (hash >>> 0).toString(16).padStart(8, "0");
1075
1053
  }
1076
- function isIndexChanged(prevIndex, currIndex) {
1077
- if (prevIndex.isUnique !== currIndex.isUnique)
1078
- return true;
1079
- if (prevIndex.method !== currIndex.method)
1080
- return true;
1081
- if (prevIndex.where !== currIndex.where)
1082
- return true;
1083
- if (prevIndex.concurrently !== currIndex.concurrently)
1084
- return true;
1085
- const prevColumns = prevIndex.columns || [];
1086
- const currColumns = currIndex.columns || [];
1087
- if (prevColumns.length !== currColumns.length)
1088
- return true;
1089
- for (let i = 0;i < prevColumns.length; i++) {
1090
- const prevCol = prevColumns[i];
1091
- const currCol = currColumns[i];
1092
- if (typeof prevCol === "string" && typeof currCol === "string") {
1093
- if (prevCol !== currCol)
1094
- return true;
1095
- } else if (typeof prevCol === "object" && typeof currCol === "object") {
1096
- if (prevCol.expression !== currCol.expression)
1097
- return true;
1098
- if (prevCol.isExpression !== currCol.isExpression)
1099
- return true;
1100
- if (prevCol.asc !== currCol.asc)
1101
- return true;
1102
- if (prevCol.nulls !== currCol.nulls)
1103
- return true;
1104
- } else {
1105
- return true;
1106
- }
1054
+ function stringToBigInt(str) {
1055
+ const hash = extendedHash(str);
1056
+ let lockId = BigInt(`0x${hash.slice(0, 16)}`);
1057
+ const mask63Bits = 0x7fffffffffffffffn;
1058
+ lockId = lockId & mask63Bits;
1059
+ if (lockId === 0n) {
1060
+ lockId = 1n;
1107
1061
  }
1108
- return false;
1062
+ return lockId;
1109
1063
  }
1110
- async function calculateDiff(previousSnapshot, currentSnapshot) {
1111
- const diff = {
1112
- tables: {
1113
- created: [],
1114
- deleted: [],
1115
- modified: []
1116
- },
1117
- columns: {
1118
- added: [],
1119
- deleted: [],
1120
- modified: []
1121
- },
1122
- indexes: {
1123
- created: [],
1124
- deleted: [],
1125
- altered: []
1126
- },
1127
- foreignKeys: {
1128
- created: [],
1129
- deleted: [],
1130
- altered: []
1131
- },
1132
- uniqueConstraints: {
1133
- created: [],
1134
- deleted: []
1135
- },
1136
- checkConstraints: {
1137
- created: [],
1138
- deleted: []
1139
- }
1140
- };
1141
- if (!previousSnapshot) {
1142
- diff.tables.created = Object.keys(currentSnapshot.tables);
1143
- for (const tableName in currentSnapshot.tables) {
1144
- const table = currentSnapshot.tables[tableName];
1145
- if (table.indexes) {
1146
- for (const indexName in table.indexes) {
1147
- diff.indexes.created.push({
1148
- ...table.indexes[indexName],
1149
- table: tableName
1150
- });
1151
- }
1064
+
1065
+ // runtime-migrator/drizzle-adapters/database-introspector.ts
1066
+ import { logger as logger3 } from "@elizaos/core";
1067
+ import { sql as sql21 } from "drizzle-orm";
1068
+ function getRows2(result) {
1069
+ return result.rows;
1070
+ }
1071
+
1072
+ class DatabaseIntrospector {
1073
+ db;
1074
+ constructor(db) {
1075
+ this.db = db;
1076
+ }
1077
+ async introspectSchema(schemaName = "public") {
1078
+ logger3.info({ src: "plugin:sql", schemaName }, "Starting database introspection");
1079
+ const tables = {};
1080
+ const schemas = {};
1081
+ const enums = {};
1082
+ const allTables = await this.getTables(schemaName);
1083
+ for (const tableInfo of allTables) {
1084
+ const tableName = tableInfo.table_name;
1085
+ const tableSchema = tableInfo.table_schema || "public";
1086
+ logger3.debug({ src: "plugin:sql", tableSchema, tableName }, "Introspecting table");
1087
+ const columns = await this.getColumns(tableSchema, tableName);
1088
+ const columnsObject = {};
1089
+ const uniqueConstraintObject = {};
1090
+ for (const col of columns) {
1091
+ columnsObject[col.column_name] = {
1092
+ name: col.column_name,
1093
+ type: col.data_type,
1094
+ primaryKey: col.is_primary || false,
1095
+ notNull: col.is_nullable === "NO",
1096
+ default: col.column_default ? this.parseDefault(col.column_default, col.data_type) : undefined
1097
+ };
1152
1098
  }
1153
- if (table.foreignKeys) {
1154
- for (const fkName in table.foreignKeys) {
1155
- diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1099
+ const indexes = await this.getIndexes(tableSchema, tableName);
1100
+ const indexesObject = {};
1101
+ for (const idx of indexes) {
1102
+ if (!idx.is_primary && !idx.is_unique_constraint) {
1103
+ if (idx.columns && Array.isArray(idx.columns) && idx.columns.length > 0) {
1104
+ indexesObject[idx.name] = {
1105
+ name: idx.name,
1106
+ columns: idx.columns.map((col) => ({
1107
+ expression: col,
1108
+ isExpression: false
1109
+ })),
1110
+ isUnique: idx.is_unique,
1111
+ method: idx.method || "btree"
1112
+ };
1113
+ }
1156
1114
  }
1157
1115
  }
1158
- }
1159
- return diff;
1160
- }
1161
- const prevTables = previousSnapshot.tables || {};
1162
- const currTables = currentSnapshot.tables || {};
1163
- for (const tableName in currTables) {
1164
- if (!(tableName in prevTables)) {
1165
- diff.tables.created.push(tableName);
1166
- const table = currTables[tableName];
1167
- if (table.indexes) {
1168
- for (const indexName in table.indexes) {
1169
- diff.indexes.created.push({
1170
- ...table.indexes[indexName],
1171
- table: tableName
1172
- });
1173
- }
1116
+ const foreignKeys = await this.getForeignKeys(tableSchema, tableName);
1117
+ const foreignKeysObject = {};
1118
+ for (const fk of foreignKeys) {
1119
+ foreignKeysObject[fk.name] = {
1120
+ name: fk.name,
1121
+ tableFrom: tableName,
1122
+ schemaFrom: tableSchema,
1123
+ tableTo: fk.foreign_table_name,
1124
+ schemaTo: fk.foreign_table_schema || "public",
1125
+ columnsFrom: [fk.column_name],
1126
+ columnsTo: [fk.foreign_column_name],
1127
+ onDelete: fk.delete_rule?.toLowerCase() || "no action",
1128
+ onUpdate: fk.update_rule?.toLowerCase() || "no action"
1129
+ };
1174
1130
  }
1175
- if (table.uniqueConstraints) {
1176
- for (const uqName in table.uniqueConstraints) {
1177
- diff.uniqueConstraints.created.push({
1178
- ...table.uniqueConstraints[uqName],
1179
- table: tableName
1180
- });
1181
- }
1131
+ const primaryKeys = await this.getPrimaryKeys(tableSchema, tableName);
1132
+ const primaryKeysObject = {};
1133
+ for (const pk of primaryKeys) {
1134
+ primaryKeysObject[pk.name] = {
1135
+ name: pk.name,
1136
+ columns: pk.columns
1137
+ };
1182
1138
  }
1183
- if (table.checkConstraints) {
1184
- for (const checkName in table.checkConstraints) {
1185
- diff.checkConstraints.created.push({
1186
- ...table.checkConstraints[checkName],
1187
- table: tableName
1188
- });
1189
- }
1139
+ const uniqueConstraints = await this.getUniqueConstraints(tableSchema, tableName);
1140
+ for (const unq of uniqueConstraints) {
1141
+ uniqueConstraintObject[unq.name] = {
1142
+ name: unq.name,
1143
+ columns: unq.columns,
1144
+ nullsNotDistinct: false
1145
+ };
1190
1146
  }
1191
- if (table.foreignKeys) {
1192
- for (const fkName in table.foreignKeys) {
1193
- diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1194
- }
1147
+ const checkConstraints = await this.getCheckConstraints(tableSchema, tableName);
1148
+ const checksObject = {};
1149
+ for (const check3 of checkConstraints) {
1150
+ checksObject[check3.name] = {
1151
+ name: check3.name,
1152
+ value: check3.definition
1153
+ };
1195
1154
  }
1196
- }
1197
- }
1198
- for (const tableName in prevTables) {
1199
- if (!(tableName in currTables)) {
1200
- diff.tables.deleted.push(tableName);
1201
- }
1202
- }
1155
+ tables[`${tableSchema}.${tableName}`] = {
1156
+ name: tableName,
1157
+ schema: tableSchema,
1158
+ columns: columnsObject,
1159
+ indexes: indexesObject,
1160
+ foreignKeys: foreignKeysObject,
1161
+ compositePrimaryKeys: primaryKeysObject,
1162
+ uniqueConstraints: uniqueConstraintObject,
1163
+ checkConstraints: checksObject
1164
+ };
1165
+ if (tableSchema && tableSchema !== "public") {
1166
+ schemas[tableSchema] = tableSchema;
1167
+ }
1168
+ }
1169
+ const enumsResult = await this.getEnums(schemaName);
1170
+ for (const enumInfo of enumsResult) {
1171
+ const key = `${enumInfo.schema}.${enumInfo.name}`;
1172
+ if (!enums[key]) {
1173
+ enums[key] = {
1174
+ name: enumInfo.name,
1175
+ schema: enumInfo.schema,
1176
+ values: []
1177
+ };
1178
+ }
1179
+ enums[key].values.push(enumInfo.value);
1180
+ }
1181
+ logger3.info({ src: "plugin:sql", tableCount: Object.keys(tables).length }, "Database introspection complete");
1182
+ return {
1183
+ version: "7",
1184
+ dialect: "postgresql",
1185
+ tables,
1186
+ schemas,
1187
+ enums,
1188
+ _meta: {
1189
+ schemas: {},
1190
+ tables: {},
1191
+ columns: {}
1192
+ }
1193
+ };
1194
+ }
1195
+ async getTables(schemaName) {
1196
+ const result = await this.db.execute(sql21`SELECT
1197
+ table_schema,
1198
+ table_name
1199
+ FROM information_schema.tables
1200
+ WHERE table_schema = ${schemaName}
1201
+ AND table_type = 'BASE TABLE'
1202
+ ORDER BY table_name`);
1203
+ return getRows2(result);
1204
+ }
1205
+ async getColumns(schemaName, tableName) {
1206
+ const result = await this.db.execute(sql21`SELECT
1207
+ a.attname AS column_name,
1208
+ CASE
1209
+ WHEN a.attnotnull THEN 'NO'
1210
+ ELSE 'YES'
1211
+ END AS is_nullable,
1212
+ CASE
1213
+ WHEN a.atttypid = ANY ('{int,int8,int2}'::regtype[])
1214
+ AND EXISTS (
1215
+ SELECT FROM pg_attrdef ad
1216
+ WHERE ad.adrelid = a.attrelid
1217
+ AND ad.adnum = a.attnum
1218
+ AND pg_get_expr(ad.adbin, ad.adrelid) = 'nextval('''
1219
+ || pg_get_serial_sequence(a.attrelid::regclass::text, a.attname)::regclass || '''::regclass)'
1220
+ )
1221
+ THEN CASE a.atttypid
1222
+ WHEN 'int'::regtype THEN 'serial'
1223
+ WHEN 'int8'::regtype THEN 'bigserial'
1224
+ WHEN 'int2'::regtype THEN 'smallserial'
1225
+ END
1226
+ ELSE format_type(a.atttypid, a.atttypmod)
1227
+ END AS data_type,
1228
+ pg_get_expr(ad.adbin, ad.adrelid) AS column_default,
1229
+ CASE
1230
+ WHEN con.contype = 'p' THEN true
1231
+ ELSE false
1232
+ END AS is_primary
1233
+ FROM pg_attribute a
1234
+ JOIN pg_class cls ON cls.oid = a.attrelid
1235
+ JOIN pg_namespace ns ON ns.oid = cls.relnamespace
1236
+ LEFT JOIN pg_attrdef ad ON ad.adrelid = a.attrelid AND ad.adnum = a.attnum
1237
+ LEFT JOIN pg_constraint con ON con.conrelid = a.attrelid
1238
+ AND a.attnum = ANY(con.conkey)
1239
+ AND con.contype = 'p'
1240
+ WHERE
1241
+ a.attnum > 0
1242
+ AND NOT a.attisdropped
1243
+ AND ns.nspname = ${schemaName}
1244
+ AND cls.relname = ${tableName}
1245
+ ORDER BY a.attnum`);
1246
+ return getRows2(result);
1247
+ }
1248
+ async getIndexes(schemaName, tableName) {
1249
+ const result = await this.db.execute(sql21`SELECT
1250
+ i.relname AS name,
1251
+ idx.indisunique AS is_unique,
1252
+ idx.indisprimary AS is_primary,
1253
+ con.contype = 'u' AS is_unique_constraint,
1254
+ ARRAY(
1255
+ SELECT a.attname
1256
+ FROM pg_attribute a
1257
+ WHERE a.attrelid = idx.indrelid
1258
+ AND a.attnum = ANY(idx.indkey::int[])
1259
+ ORDER BY a.attnum
1260
+ ) AS columns,
1261
+ am.amname AS method
1262
+ FROM pg_index idx
1263
+ JOIN pg_class i ON i.oid = idx.indexrelid
1264
+ JOIN pg_class c ON c.oid = idx.indrelid
1265
+ JOIN pg_namespace n ON n.oid = c.relnamespace
1266
+ JOIN pg_am am ON am.oid = i.relam
1267
+ LEFT JOIN pg_constraint con ON con.conindid = idx.indexrelid
1268
+ WHERE n.nspname = ${schemaName}
1269
+ AND c.relname = ${tableName}`);
1270
+ return getRows2(result);
1271
+ }
1272
+ async getForeignKeys(schemaName, tableName) {
1273
+ const result = await this.db.execute(sql21`SELECT
1274
+ con.conname AS name,
1275
+ att.attname AS column_name,
1276
+ fnsp.nspname AS foreign_table_schema,
1277
+ frel.relname AS foreign_table_name,
1278
+ fatt.attname AS foreign_column_name,
1279
+ CASE con.confupdtype
1280
+ WHEN 'a' THEN 'NO ACTION'
1281
+ WHEN 'r' THEN 'RESTRICT'
1282
+ WHEN 'n' THEN 'SET NULL'
1283
+ WHEN 'c' THEN 'CASCADE'
1284
+ WHEN 'd' THEN 'SET DEFAULT'
1285
+ END AS update_rule,
1286
+ CASE con.confdeltype
1287
+ WHEN 'a' THEN 'NO ACTION'
1288
+ WHEN 'r' THEN 'RESTRICT'
1289
+ WHEN 'n' THEN 'SET NULL'
1290
+ WHEN 'c' THEN 'CASCADE'
1291
+ WHEN 'd' THEN 'SET DEFAULT'
1292
+ END AS delete_rule
1293
+ FROM pg_catalog.pg_constraint con
1294
+ JOIN pg_catalog.pg_class rel ON rel.oid = con.conrelid
1295
+ JOIN pg_catalog.pg_namespace nsp ON nsp.oid = con.connamespace
1296
+ LEFT JOIN pg_catalog.pg_attribute att ON att.attnum = ANY (con.conkey)
1297
+ AND att.attrelid = con.conrelid
1298
+ LEFT JOIN pg_catalog.pg_class frel ON frel.oid = con.confrelid
1299
+ LEFT JOIN pg_catalog.pg_namespace fnsp ON fnsp.oid = frel.relnamespace
1300
+ LEFT JOIN pg_catalog.pg_attribute fatt ON fatt.attnum = ANY (con.confkey)
1301
+ AND fatt.attrelid = con.confrelid
1302
+ WHERE con.contype = 'f'
1303
+ AND nsp.nspname = ${schemaName}
1304
+ AND rel.relname = ${tableName}`);
1305
+ return getRows2(result);
1306
+ }
1307
+ async getPrimaryKeys(schemaName, tableName) {
1308
+ const result = await this.db.execute(sql21`SELECT
1309
+ con.conname AS name,
1310
+ ARRAY(
1311
+ SELECT a.attname
1312
+ FROM pg_attribute a
1313
+ WHERE a.attrelid = con.conrelid
1314
+ AND a.attnum = ANY(con.conkey)
1315
+ ORDER BY a.attnum
1316
+ ) AS columns
1317
+ FROM pg_constraint con
1318
+ JOIN pg_class rel ON rel.oid = con.conrelid
1319
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1320
+ WHERE con.contype = 'p'
1321
+ AND nsp.nspname = ${schemaName}
1322
+ AND rel.relname = ${tableName}`);
1323
+ return getRows2(result);
1324
+ }
1325
+ async getUniqueConstraints(schemaName, tableName) {
1326
+ const result = await this.db.execute(sql21`SELECT
1327
+ con.conname AS name,
1328
+ ARRAY(
1329
+ SELECT a.attname
1330
+ FROM pg_attribute a
1331
+ WHERE a.attrelid = con.conrelid
1332
+ AND a.attnum = ANY(con.conkey)
1333
+ ORDER BY a.attnum
1334
+ ) AS columns
1335
+ FROM pg_constraint con
1336
+ JOIN pg_class rel ON rel.oid = con.conrelid
1337
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1338
+ WHERE con.contype = 'u'
1339
+ AND nsp.nspname = ${schemaName}
1340
+ AND rel.relname = ${tableName}`);
1341
+ return getRows2(result);
1342
+ }
1343
+ async getCheckConstraints(schemaName, tableName) {
1344
+ const result = await this.db.execute(sql21`SELECT
1345
+ con.conname AS name,
1346
+ pg_get_constraintdef(con.oid) AS definition
1347
+ FROM pg_constraint con
1348
+ JOIN pg_class rel ON rel.oid = con.conrelid
1349
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1350
+ WHERE con.contype = 'c'
1351
+ AND nsp.nspname = ${schemaName}
1352
+ AND rel.relname = ${tableName}`);
1353
+ return getRows2(result);
1354
+ }
1355
+ async getEnums(schemaName) {
1356
+ const result = await this.db.execute(sql21`SELECT
1357
+ n.nspname AS schema,
1358
+ t.typname AS name,
1359
+ e.enumlabel AS value,
1360
+ e.enumsortorder AS sort_order
1361
+ FROM pg_type t
1362
+ JOIN pg_enum e ON t.oid = e.enumtypid
1363
+ JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
1364
+ WHERE n.nspname = ${schemaName}
1365
+ ORDER BY schema, name, sort_order`);
1366
+ return getRows2(result);
1367
+ }
1368
+ parseDefault(defaultValue, dataType) {
1369
+ if (!defaultValue)
1370
+ return;
1371
+ const match = defaultValue.match(/^'(.*)'::/);
1372
+ if (match) {
1373
+ return `'${match[1]}'`;
1374
+ }
1375
+ if (defaultValue.includes("nextval(")) {
1376
+ return;
1377
+ }
1378
+ if (dataType === "boolean") {
1379
+ if (defaultValue === "true")
1380
+ return "true";
1381
+ if (defaultValue === "false")
1382
+ return "false";
1383
+ }
1384
+ return defaultValue;
1385
+ }
1386
+ async hasExistingTables(pluginName) {
1387
+ const schemaName = pluginName === "@elizaos/plugin-sql" ? "public" : this.deriveSchemaName(pluginName);
1388
+ const result = await this.db.execute(sql21`SELECT COUNT(*) AS count
1389
+ FROM information_schema.tables
1390
+ WHERE table_schema = ${schemaName}
1391
+ AND table_type = 'BASE TABLE'`);
1392
+ const firstRow = result.rows?.[0];
1393
+ const count = parseInt(firstRow && firstRow.count || "0", 10);
1394
+ return count > 0;
1395
+ }
1396
+ deriveSchemaName(pluginName) {
1397
+ return pluginName.replace("@", "").replace("/", "_").replace(/-/g, "_").toLowerCase();
1398
+ }
1399
+ }
1400
+ var init_database_introspector = () => {};
1401
+
1402
+ // runtime-migrator/drizzle-adapters/diff-calculator.ts
1403
+ var exports_diff_calculator = {};
1404
+ __export(exports_diff_calculator, {
1405
+ hasDiffChanges: () => hasDiffChanges,
1406
+ calculateDiff: () => calculateDiff
1407
+ });
1408
+ function normalizeType(type) {
1409
+ if (!type)
1410
+ return "";
1411
+ const normalized = type.toLowerCase().trim();
1412
+ if (normalized === "timestamp without time zone" || normalized === "timestamp with time zone") {
1413
+ return "timestamp";
1414
+ }
1415
+ if (normalized === "serial") {
1416
+ return "integer";
1417
+ }
1418
+ if (normalized === "bigserial") {
1419
+ return "bigint";
1420
+ }
1421
+ if (normalized === "smallserial") {
1422
+ return "smallint";
1423
+ }
1424
+ if (normalized.startsWith("numeric") || normalized.startsWith("decimal")) {
1425
+ const match = normalized.match(/\((\d+)(?:,\s*(\d+))?\)/);
1426
+ if (match) {
1427
+ return `numeric(${match[1]}${match[2] ? `,${match[2]}` : ""})`;
1428
+ }
1429
+ return "numeric";
1430
+ }
1431
+ if (normalized.startsWith("character varying")) {
1432
+ return normalized.replace("character varying", "varchar");
1433
+ }
1434
+ if (normalized === "text[]" || normalized === "_text") {
1435
+ return "text[]";
1436
+ }
1437
+ return normalized;
1438
+ }
1439
+ function isIndexChanged(prevIndex, currIndex) {
1440
+ if (prevIndex.isUnique !== currIndex.isUnique)
1441
+ return true;
1442
+ if (prevIndex.method !== currIndex.method)
1443
+ return true;
1444
+ if (prevIndex.where !== currIndex.where)
1445
+ return true;
1446
+ if (prevIndex.concurrently !== currIndex.concurrently)
1447
+ return true;
1448
+ const prevColumns = prevIndex.columns || [];
1449
+ const currColumns = currIndex.columns || [];
1450
+ if (prevColumns.length !== currColumns.length)
1451
+ return true;
1452
+ for (let i = 0;i < prevColumns.length; i++) {
1453
+ const prevCol = prevColumns[i];
1454
+ const currCol = currColumns[i];
1455
+ if (typeof prevCol === "string" && typeof currCol === "string") {
1456
+ if (prevCol !== currCol)
1457
+ return true;
1458
+ } else if (typeof prevCol === "object" && typeof currCol === "object") {
1459
+ if (prevCol.expression !== currCol.expression)
1460
+ return true;
1461
+ if (prevCol.isExpression !== currCol.isExpression)
1462
+ return true;
1463
+ if (prevCol.asc !== currCol.asc)
1464
+ return true;
1465
+ if (prevCol.nulls !== currCol.nulls)
1466
+ return true;
1467
+ } else {
1468
+ return true;
1469
+ }
1470
+ }
1471
+ return false;
1472
+ }
1473
+ async function calculateDiff(previousSnapshot, currentSnapshot) {
1474
+ const diff = {
1475
+ tables: {
1476
+ created: [],
1477
+ deleted: [],
1478
+ modified: []
1479
+ },
1480
+ columns: {
1481
+ added: [],
1482
+ deleted: [],
1483
+ modified: []
1484
+ },
1485
+ indexes: {
1486
+ created: [],
1487
+ deleted: [],
1488
+ altered: []
1489
+ },
1490
+ foreignKeys: {
1491
+ created: [],
1492
+ deleted: [],
1493
+ altered: []
1494
+ },
1495
+ uniqueConstraints: {
1496
+ created: [],
1497
+ deleted: []
1498
+ },
1499
+ checkConstraints: {
1500
+ created: [],
1501
+ deleted: []
1502
+ }
1503
+ };
1504
+ if (!previousSnapshot) {
1505
+ diff.tables.created = Object.keys(currentSnapshot.tables);
1506
+ for (const tableName in currentSnapshot.tables) {
1507
+ const table = currentSnapshot.tables[tableName];
1508
+ if (table.indexes) {
1509
+ for (const indexName in table.indexes) {
1510
+ diff.indexes.created.push({
1511
+ ...table.indexes[indexName],
1512
+ table: tableName
1513
+ });
1514
+ }
1515
+ }
1516
+ if (table.foreignKeys) {
1517
+ for (const fkName in table.foreignKeys) {
1518
+ diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1519
+ }
1520
+ }
1521
+ }
1522
+ return diff;
1523
+ }
1524
+ const prevTables = previousSnapshot.tables || {};
1525
+ const currTables = currentSnapshot.tables || {};
1526
+ for (const tableName in currTables) {
1527
+ if (!(tableName in prevTables)) {
1528
+ diff.tables.created.push(tableName);
1529
+ const table = currTables[tableName];
1530
+ if (table.indexes) {
1531
+ for (const indexName in table.indexes) {
1532
+ diff.indexes.created.push({
1533
+ ...table.indexes[indexName],
1534
+ table: tableName
1535
+ });
1536
+ }
1537
+ }
1538
+ if (table.uniqueConstraints) {
1539
+ for (const uqName in table.uniqueConstraints) {
1540
+ diff.uniqueConstraints.created.push({
1541
+ ...table.uniqueConstraints[uqName],
1542
+ table: tableName
1543
+ });
1544
+ }
1545
+ }
1546
+ if (table.checkConstraints) {
1547
+ for (const checkName in table.checkConstraints) {
1548
+ diff.checkConstraints.created.push({
1549
+ ...table.checkConstraints[checkName],
1550
+ table: tableName
1551
+ });
1552
+ }
1553
+ }
1554
+ if (table.foreignKeys) {
1555
+ for (const fkName in table.foreignKeys) {
1556
+ diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1557
+ }
1558
+ }
1559
+ }
1560
+ }
1561
+ for (const tableName in prevTables) {
1562
+ if (!(tableName in currTables)) {
1563
+ diff.tables.deleted.push(tableName);
1564
+ }
1565
+ }
1203
1566
  for (const tableName in currTables) {
1204
1567
  if (tableName in prevTables) {
1205
1568
  const prevTable = prevTables[tableName];
@@ -1367,32 +1730,6 @@ function hasDiffChanges(diff) {
1367
1730
  return diff.tables.created.length > 0 || diff.tables.deleted.length > 0 || diff.tables.modified.length > 0 || diff.columns.added.length > 0 || diff.columns.deleted.length > 0 || diff.columns.modified.length > 0 || diff.indexes.created.length > 0 || diff.indexes.deleted.length > 0 || diff.indexes.altered.length > 0 || diff.foreignKeys.created.length > 0 || diff.foreignKeys.deleted.length > 0 || diff.foreignKeys.altered.length > 0 || diff.uniqueConstraints.created.length > 0 || diff.uniqueConstraints.deleted.length > 0 || diff.checkConstraints.created.length > 0 || diff.checkConstraints.deleted.length > 0;
1368
1731
  }
1369
1732
 
1370
- // runtime-migrator/crypto-utils.ts
1371
- function extendedHash(str) {
1372
- const h1 = hashWithSeed(str, 5381);
1373
- const h2 = hashWithSeed(str, 7919);
1374
- const h3 = hashWithSeed(str, 104729);
1375
- const h4 = hashWithSeed(str, 224737);
1376
- return h1 + h2 + h3 + h4;
1377
- }
1378
- function hashWithSeed(str, seed) {
1379
- let hash = seed;
1380
- for (let i = 0;i < str.length; i++) {
1381
- hash = hash * 33 ^ str.charCodeAt(i);
1382
- }
1383
- return (hash >>> 0).toString(16).padStart(8, "0");
1384
- }
1385
- function stringToBigInt(str) {
1386
- const hash = extendedHash(str);
1387
- let lockId = BigInt(`0x${hash.slice(0, 16)}`);
1388
- const mask63Bits = 0x7fffffffffffffffn;
1389
- lockId = lockId & mask63Bits;
1390
- if (lockId === 0n) {
1391
- lockId = 1n;
1392
- }
1393
- return lockId;
1394
- }
1395
-
1396
1733
  // runtime-migrator/drizzle-adapters/snapshot-generator.ts
1397
1734
  import { is, SQL } from "drizzle-orm";
1398
1735
  import { getTableConfig, PgDialect, PgTable } from "drizzle-orm/pg-core";
@@ -1621,7 +1958,7 @@ function hasChanges(previousSnapshot, currentSnapshot) {
1621
1958
  const currHash = hashSnapshot(currentSnapshot);
1622
1959
  return prevHash !== currHash;
1623
1960
  }
1624
- var sqlToStr = (sql21, _casing) => {
1961
+ var sqlToStr = (sql22, _casing) => {
1625
1962
  const config = {
1626
1963
  escapeName: () => {
1627
1964
  throw new Error("we don't support params for `sql` default values");
@@ -1634,12 +1971,12 @@ var sqlToStr = (sql21, _casing) => {
1634
1971
  },
1635
1972
  casing: undefined
1636
1973
  };
1637
- return sql21.toQuery(config).sql;
1974
+ return sql22.toQuery(config).sql;
1638
1975
  };
1639
1976
  var init_snapshot_generator = () => {};
1640
1977
 
1641
1978
  // runtime-migrator/drizzle-adapters/sql-generator.ts
1642
- import { logger as logger3 } from "@elizaos/core";
1979
+ import { logger as logger4 } from "@elizaos/core";
1643
1980
  function checkForDataLoss(diff) {
1644
1981
  const result = {
1645
1982
  hasDataLoss: false,
@@ -1769,7 +2106,7 @@ async function generateMigrationSQL(previousSnapshot, currentSnapshot, diff) {
1769
2106
  }
1770
2107
  const dataLossCheck = checkForDataLoss(diff);
1771
2108
  if (dataLossCheck.warnings.length > 0) {
1772
- logger3.warn({ src: "plugin:sql", warnings: dataLossCheck.warnings }, "Schema changes may cause data loss");
2109
+ logger4.warn({ src: "plugin:sql", warnings: dataLossCheck.warnings }, "Schema changes may cause data loss");
1773
2110
  }
1774
2111
  const schemasToCreate = new Set;
1775
2112
  for (const tableName of diff.tables.created) {
@@ -1922,24 +2259,29 @@ function generateCreateTableSQL(fullTableName, table) {
1922
2259
  const foreignKeys = table.foreignKeys || {};
1923
2260
  for (const [fkName, fkDef] of Object.entries(foreignKeys)) {
1924
2261
  const fk = fkDef;
1925
- const fkSQL = `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${fkName}" FOREIGN KEY (${fk.columnsFrom.map((c) => `"${c}"`).join(", ")}) REFERENCES "${fk.schemaTo || "public"}"."${fk.tableTo}" (${fk.columnsTo.map((c) => `"${c}"`).join(", ")})${fk.onDelete ? ` ON DELETE ${fk.onDelete}` : ""}${fk.onUpdate ? ` ON UPDATE ${fk.onUpdate}` : ""};`;
2262
+ const fkSQL = wrapConstraintCreationGuard(fkName, buildCreateForeignKeyBodySQL({
2263
+ ...fk,
2264
+ name: fkName,
2265
+ schemaFrom: schema,
2266
+ tableFrom: tableName
2267
+ }));
1926
2268
  fkSQLs.push(fkSQL);
1927
2269
  }
1928
2270
  return { tableSQL, fkSQLs };
1929
2271
  }
1930
2272
  function generateColumnDefinition(name, def) {
1931
- let sql21 = `"${name}" ${def.type}`;
2273
+ let sql22 = `"${name}" ${def.type}`;
1932
2274
  if (def.primaryKey && !def.type.includes("SERIAL")) {
1933
- sql21 += " PRIMARY KEY";
2275
+ sql22 += " PRIMARY KEY";
1934
2276
  }
1935
2277
  if (def.notNull) {
1936
- sql21 += " NOT NULL";
2278
+ sql22 += " NOT NULL";
1937
2279
  }
1938
2280
  if (def.default !== undefined) {
1939
2281
  const defaultValue = formatDefaultValue(def.default, def.type);
1940
- sql21 += ` DEFAULT ${defaultValue}`;
2282
+ sql22 += ` DEFAULT ${defaultValue}`;
1941
2283
  }
1942
- return sql21;
2284
+ return sql22;
1943
2285
  }
1944
2286
  function generateAddColumnSQL(table, column, definition) {
1945
2287
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
@@ -1949,543 +2291,213 @@ function generateAddColumnSQL(table, column, definition) {
1949
2291
  if (definition.primaryKey) {
1950
2292
  parts.push("PRIMARY KEY");
1951
2293
  }
1952
- if (definition.default !== undefined) {
1953
- const defaultValue = formatDefaultValue(definition.default, definition.type);
1954
- if (defaultValue) {
1955
- parts.push(`DEFAULT ${defaultValue}`);
1956
- }
1957
- }
1958
- const definitionWithGenerated = definition;
1959
- if (definitionWithGenerated.generated) {
1960
- parts.push(`GENERATED ALWAYS AS (${definitionWithGenerated.generated}) STORED`);
1961
- }
1962
- if (definition.notNull) {
1963
- parts.push("NOT NULL");
1964
- }
1965
- return `ALTER TABLE ${tableNameWithSchema} ADD COLUMN ${parts.join(" ")};`;
1966
- }
1967
- function generateDropColumnSQL(table, column) {
1968
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
1969
- const tableNameWithSchema = `"${schema}"."${tableName}"`;
1970
- return `ALTER TABLE ${tableNameWithSchema} DROP COLUMN "${column}" CASCADE;`;
1971
- }
1972
- function generateAlterColumnSQL(table, column, changes) {
1973
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
1974
- const tableNameWithSchema = `"${schema}"."${tableName}"`;
1975
- const statements = [];
1976
- const changesTo = changes.to;
1977
- const changesFrom = changes.from;
1978
- const changesToType = changesTo?.type;
1979
- const changesFromType = changesFrom?.type;
1980
- if (changesToType !== changesFromType) {
1981
- const newType = changesToType || "TEXT";
1982
- const needsUsing = checkIfNeedsUsingClause(changesFromType || "", newType);
1983
- if (needsUsing) {
1984
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" TYPE ${newType} USING "${column}"::text::${newType};`);
1985
- } else {
1986
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DATA TYPE ${newType};`);
1987
- }
1988
- }
1989
- const changesToNotNull = changesTo?.notNull;
1990
- const changesFromNotNull = changesFrom?.notNull;
1991
- if (changesToNotNull !== changesFromNotNull) {
1992
- if (changesToNotNull) {
1993
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET NOT NULL;`);
1994
- } else {
1995
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP NOT NULL;`);
1996
- }
1997
- }
1998
- const changesToDefault = changesTo?.default;
1999
- const changesFromDefault = changesFrom?.default;
2000
- if (changesToDefault !== changesFromDefault) {
2001
- if (changesToDefault !== undefined) {
2002
- const defaultValue = formatDefaultValue(changesToDefault, changesToType || "");
2003
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DEFAULT ${defaultValue};`);
2004
- } else {
2005
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP DEFAULT;`);
2006
- }
2007
- }
2008
- return statements;
2009
- }
2010
- function checkIfNeedsUsingClause(fromType, toType) {
2011
- if (!fromType || !toType)
2012
- return false;
2013
- if (fromType.includes("enum") || toType.includes("enum")) {
2014
- return true;
2015
- }
2016
- const fromBase = fromType.split("(")[0].toLowerCase();
2017
- const toBase = toType.split("(")[0].toLowerCase();
2018
- if ((fromBase === "text" || fromBase === "varchar" || fromBase === "character varying") && (toBase === "jsonb" || toBase === "json")) {
2019
- return true;
2020
- }
2021
- const needsUsingPairs = [
2022
- ["integer", "boolean"],
2023
- ["boolean", "integer"],
2024
- ["text", "integer"],
2025
- ["text", "numeric"],
2026
- ["text", "boolean"],
2027
- ["text", "uuid"],
2028
- ["text", "jsonb"],
2029
- ["text", "json"],
2030
- ["varchar", "integer"],
2031
- ["varchar", "numeric"],
2032
- ["varchar", "boolean"],
2033
- ["varchar", "uuid"],
2034
- ["varchar", "jsonb"],
2035
- ["varchar", "json"],
2036
- ["character varying", "jsonb"],
2037
- ["character varying", "json"]
2038
- ];
2039
- for (const [from, to] of needsUsingPairs) {
2040
- if (fromBase === from && toBase === to || fromBase === to && toBase === from) {
2041
- return true;
2042
- }
2043
- }
2044
- return false;
2045
- }
2046
- function formatDefaultValue(value, type) {
2047
- if (value === null || value === "NULL") {
2048
- return "NULL";
2049
- }
2050
- if (type && (type.toLowerCase().includes("boolean") || type.toLowerCase() === "bool")) {
2051
- if (value === true || value === "true" || value === "t" || value === 1) {
2052
- return "true";
2053
- }
2054
- if (value === false || value === "false" || value === "f" || value === 0) {
2055
- return "false";
2056
- }
2057
- }
2058
- if (type?.match(/^(integer|bigint|smallint|numeric|decimal|real|double)/i)) {
2059
- return String(value);
2060
- }
2061
- if (typeof value === "string") {
2062
- if (value.includes("::")) {
2063
- return value;
2064
- }
2065
- if (value.startsWith("'") && value.endsWith("'")) {
2066
- return value;
2067
- }
2068
- if (value.match(/^\w+\(\)/i) || value.includes("(") && value.includes(")")) {
2069
- return value;
2070
- }
2071
- if (value.toUpperCase().startsWith("CURRENT_")) {
2072
- return value;
2073
- }
2074
- return `'${value.replace(/'/g, "''")}'`;
2075
- }
2076
- return String(value);
2077
- }
2078
- function generateCreateIndexSQL(index7) {
2079
- const unique3 = index7.isUnique ? "UNIQUE " : "";
2080
- const method = index7.method || "btree";
2081
- const columns = index7.columns.map((c) => {
2082
- if (c.isExpression) {
2083
- return c.expression;
2084
- }
2085
- return `"${c.expression}"${c.asc === false ? " DESC" : ""}`;
2086
- }).join(", ");
2087
- const indexName = index7.name.includes(".") ? index7.name.split(".")[1] : index7.name;
2088
- let tableRef;
2089
- const indexTable = index7.table;
2090
- if (indexTable?.includes(".")) {
2091
- const [schema, table] = indexTable.split(".");
2092
- tableRef = `"${schema}"."${table}"`;
2093
- } else {
2094
- tableRef = `"${indexTable || ""}"`;
2095
- }
2096
- return `CREATE ${unique3}INDEX "${indexName}" ON ${tableRef} USING ${method} (${columns});`;
2097
- }
2098
- function generateDropIndexSQL(index7) {
2099
- const indexNameFull = typeof index7 === "string" ? index7 : index7.name;
2100
- const indexName = indexNameFull.includes(".") ? indexNameFull.split(".")[1] : indexNameFull;
2101
- return `DROP INDEX IF EXISTS "${indexName}";`;
2102
- }
2103
- function generateCreateForeignKeySQL(fk) {
2104
- const schemaFrom = fk.schemaFrom || "public";
2105
- const schemaTo = fk.schemaTo || "public";
2106
- const tableFrom = fk.tableFrom;
2107
- const columnsFrom = fk.columnsFrom.map((c) => `"${c}"`).join(", ");
2108
- const columnsTo = fk.columnsTo.map((c) => `"${c}"`).join(", ");
2109
- let sql21 = `ALTER TABLE "${schemaFrom}"."${tableFrom}" ADD CONSTRAINT "${fk.name}" FOREIGN KEY (${columnsFrom}) REFERENCES "${schemaTo}"."${fk.tableTo}" (${columnsTo})`;
2110
- if (fk.onDelete) {
2111
- sql21 += ` ON DELETE ${fk.onDelete}`;
2112
- }
2113
- if (fk.onUpdate) {
2114
- sql21 += ` ON UPDATE ${fk.onUpdate}`;
2115
- }
2116
- return `${sql21};`;
2117
- }
2118
- function generateDropForeignKeySQL(fk) {
2119
- const [schema, tableName] = fk.tableFrom ? fk.tableFrom.includes(".") ? fk.tableFrom.split(".") : ["public", fk.tableFrom] : ["public", ""];
2120
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${fk.name}";`;
2121
- }
2122
- function generateCreateUniqueConstraintSQL(constraint) {
2123
- const table = constraint.table || "";
2124
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2125
- const name = constraint.name;
2126
- const columns = constraint.columns.map((c) => `"${c}"`).join(", ");
2127
- let sql21 = `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" UNIQUE`;
2128
- if (constraint.nullsNotDistinct) {
2129
- sql21 += ` NULLS NOT DISTINCT`;
2294
+ if (definition.default !== undefined) {
2295
+ const defaultValue = formatDefaultValue(definition.default, definition.type);
2296
+ if (defaultValue) {
2297
+ parts.push(`DEFAULT ${defaultValue}`);
2298
+ }
2130
2299
  }
2131
- sql21 += ` (${columns});`;
2132
- return sql21;
2133
- }
2134
- function generateDropUniqueConstraintSQL(constraint) {
2135
- const table = constraint.table || "";
2136
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2137
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2300
+ const definitionWithGenerated = definition;
2301
+ if (definitionWithGenerated.generated) {
2302
+ parts.push(`GENERATED ALWAYS AS (${definitionWithGenerated.generated}) STORED`);
2303
+ }
2304
+ if (definition.notNull) {
2305
+ parts.push("NOT NULL");
2306
+ }
2307
+ return `ALTER TABLE ${tableNameWithSchema} ADD COLUMN ${parts.join(" ")};`;
2138
2308
  }
2139
- function generateCreateCheckConstraintSQL(constraint) {
2140
- const table = constraint.table || "";
2309
+ function generateDropColumnSQL(table, column) {
2141
2310
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2142
- const name = constraint.name;
2143
- const value = constraint.value;
2144
- return `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" CHECK (${value});`;
2311
+ const tableNameWithSchema = `"${schema}"."${tableName}"`;
2312
+ return `ALTER TABLE ${tableNameWithSchema} DROP COLUMN "${column}" CASCADE;`;
2145
2313
  }
2146
- function generateDropCheckConstraintSQL(constraint) {
2147
- const table = constraint.table || "";
2314
+ function generateAlterColumnSQL(table, column, changes) {
2148
2315
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2149
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2150
- }
2151
- var init_sql_generator = () => {};
2152
-
2153
- // runtime-migrator/drizzle-adapters/database-introspector.ts
2154
- import { logger as logger4 } from "@elizaos/core";
2155
- import { sql as sql21 } from "drizzle-orm";
2156
- function getRows2(result) {
2157
- return result.rows;
2158
- }
2159
-
2160
- class DatabaseIntrospector {
2161
- db;
2162
- constructor(db) {
2163
- this.db = db;
2164
- }
2165
- async introspectSchema(schemaName = "public") {
2166
- logger4.info({ src: "plugin:sql", schemaName }, "Starting database introspection");
2167
- const tables = {};
2168
- const schemas = {};
2169
- const enums = {};
2170
- const allTables = await this.getTables(schemaName);
2171
- for (const tableInfo of allTables) {
2172
- const tableName = tableInfo.table_name;
2173
- const tableSchema = tableInfo.table_schema || "public";
2174
- logger4.debug({ src: "plugin:sql", tableSchema, tableName }, "Introspecting table");
2175
- const columns = await this.getColumns(tableSchema, tableName);
2176
- const columnsObject = {};
2177
- const uniqueConstraintObject = {};
2178
- for (const col of columns) {
2179
- columnsObject[col.column_name] = {
2180
- name: col.column_name,
2181
- type: col.data_type,
2182
- primaryKey: col.is_primary || false,
2183
- notNull: col.is_nullable === "NO",
2184
- default: col.column_default ? this.parseDefault(col.column_default, col.data_type) : undefined
2185
- };
2186
- }
2187
- const indexes = await this.getIndexes(tableSchema, tableName);
2188
- const indexesObject = {};
2189
- for (const idx of indexes) {
2190
- if (!idx.is_primary && !idx.is_unique_constraint) {
2191
- if (idx.columns && Array.isArray(idx.columns) && idx.columns.length > 0) {
2192
- indexesObject[idx.name] = {
2193
- name: idx.name,
2194
- columns: idx.columns.map((col) => ({
2195
- expression: col,
2196
- isExpression: false
2197
- })),
2198
- isUnique: idx.is_unique,
2199
- method: idx.method || "btree"
2200
- };
2201
- }
2202
- }
2203
- }
2204
- const foreignKeys = await this.getForeignKeys(tableSchema, tableName);
2205
- const foreignKeysObject = {};
2206
- for (const fk of foreignKeys) {
2207
- foreignKeysObject[fk.name] = {
2208
- name: fk.name,
2209
- tableFrom: tableName,
2210
- schemaFrom: tableSchema,
2211
- tableTo: fk.foreign_table_name,
2212
- schemaTo: fk.foreign_table_schema || "public",
2213
- columnsFrom: [fk.column_name],
2214
- columnsTo: [fk.foreign_column_name],
2215
- onDelete: fk.delete_rule?.toLowerCase() || "no action",
2216
- onUpdate: fk.update_rule?.toLowerCase() || "no action"
2217
- };
2218
- }
2219
- const primaryKeys = await this.getPrimaryKeys(tableSchema, tableName);
2220
- const primaryKeysObject = {};
2221
- for (const pk of primaryKeys) {
2222
- primaryKeysObject[pk.name] = {
2223
- name: pk.name,
2224
- columns: pk.columns
2225
- };
2226
- }
2227
- const uniqueConstraints = await this.getUniqueConstraints(tableSchema, tableName);
2228
- for (const unq of uniqueConstraints) {
2229
- uniqueConstraintObject[unq.name] = {
2230
- name: unq.name,
2231
- columns: unq.columns,
2232
- nullsNotDistinct: false
2233
- };
2234
- }
2235
- const checkConstraints = await this.getCheckConstraints(tableSchema, tableName);
2236
- const checksObject = {};
2237
- for (const check3 of checkConstraints) {
2238
- checksObject[check3.name] = {
2239
- name: check3.name,
2240
- value: check3.definition
2241
- };
2242
- }
2243
- tables[`${tableSchema}.${tableName}`] = {
2244
- name: tableName,
2245
- schema: tableSchema,
2246
- columns: columnsObject,
2247
- indexes: indexesObject,
2248
- foreignKeys: foreignKeysObject,
2249
- compositePrimaryKeys: primaryKeysObject,
2250
- uniqueConstraints: uniqueConstraintObject,
2251
- checkConstraints: checksObject
2252
- };
2253
- if (tableSchema && tableSchema !== "public") {
2254
- schemas[tableSchema] = tableSchema;
2255
- }
2256
- }
2257
- const enumsResult = await this.getEnums(schemaName);
2258
- for (const enumInfo of enumsResult) {
2259
- const key = `${enumInfo.schema}.${enumInfo.name}`;
2260
- if (!enums[key]) {
2261
- enums[key] = {
2262
- name: enumInfo.name,
2263
- schema: enumInfo.schema,
2264
- values: []
2265
- };
2266
- }
2267
- enums[key].values.push(enumInfo.value);
2316
+ const tableNameWithSchema = `"${schema}"."${tableName}"`;
2317
+ const statements = [];
2318
+ const changesTo = changes.to;
2319
+ const changesFrom = changes.from;
2320
+ const changesToType = changesTo?.type;
2321
+ const changesFromType = changesFrom?.type;
2322
+ if (changesToType !== changesFromType) {
2323
+ const newType = changesToType || "TEXT";
2324
+ const needsUsing = checkIfNeedsUsingClause(changesFromType || "", newType);
2325
+ if (needsUsing) {
2326
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" TYPE ${newType} USING "${column}"::text::${newType};`);
2327
+ } else {
2328
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DATA TYPE ${newType};`);
2268
2329
  }
2269
- logger4.info({ src: "plugin:sql", tableCount: Object.keys(tables).length }, "Database introspection complete");
2270
- return {
2271
- version: "7",
2272
- dialect: "postgresql",
2273
- tables,
2274
- schemas,
2275
- enums,
2276
- _meta: {
2277
- schemas: {},
2278
- tables: {},
2279
- columns: {}
2280
- }
2281
- };
2282
- }
2283
- async getTables(schemaName) {
2284
- const result = await this.db.execute(sql21`SELECT
2285
- table_schema,
2286
- table_name
2287
- FROM information_schema.tables
2288
- WHERE table_schema = ${schemaName}
2289
- AND table_type = 'BASE TABLE'
2290
- ORDER BY table_name`);
2291
- return getRows2(result);
2292
2330
  }
2293
- async getColumns(schemaName, tableName) {
2294
- const result = await this.db.execute(sql21`SELECT
2295
- a.attname AS column_name,
2296
- CASE
2297
- WHEN a.attnotnull THEN 'NO'
2298
- ELSE 'YES'
2299
- END AS is_nullable,
2300
- CASE
2301
- WHEN a.atttypid = ANY ('{int,int8,int2}'::regtype[])
2302
- AND EXISTS (
2303
- SELECT FROM pg_attrdef ad
2304
- WHERE ad.adrelid = a.attrelid
2305
- AND ad.adnum = a.attnum
2306
- AND pg_get_expr(ad.adbin, ad.adrelid) = 'nextval('''
2307
- || pg_get_serial_sequence(a.attrelid::regclass::text, a.attname)::regclass || '''::regclass)'
2308
- )
2309
- THEN CASE a.atttypid
2310
- WHEN 'int'::regtype THEN 'serial'
2311
- WHEN 'int8'::regtype THEN 'bigserial'
2312
- WHEN 'int2'::regtype THEN 'smallserial'
2313
- END
2314
- ELSE format_type(a.atttypid, a.atttypmod)
2315
- END AS data_type,
2316
- pg_get_expr(ad.adbin, ad.adrelid) AS column_default,
2317
- CASE
2318
- WHEN con.contype = 'p' THEN true
2319
- ELSE false
2320
- END AS is_primary
2321
- FROM pg_attribute a
2322
- JOIN pg_class cls ON cls.oid = a.attrelid
2323
- JOIN pg_namespace ns ON ns.oid = cls.relnamespace
2324
- LEFT JOIN pg_attrdef ad ON ad.adrelid = a.attrelid AND ad.adnum = a.attnum
2325
- LEFT JOIN pg_constraint con ON con.conrelid = a.attrelid
2326
- AND a.attnum = ANY(con.conkey)
2327
- AND con.contype = 'p'
2328
- WHERE
2329
- a.attnum > 0
2330
- AND NOT a.attisdropped
2331
- AND ns.nspname = ${schemaName}
2332
- AND cls.relname = ${tableName}
2333
- ORDER BY a.attnum`);
2334
- return getRows2(result);
2331
+ const changesToNotNull = changesTo?.notNull;
2332
+ const changesFromNotNull = changesFrom?.notNull;
2333
+ if (changesToNotNull !== changesFromNotNull) {
2334
+ if (changesToNotNull) {
2335
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET NOT NULL;`);
2336
+ } else {
2337
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP NOT NULL;`);
2338
+ }
2335
2339
  }
2336
- async getIndexes(schemaName, tableName) {
2337
- const result = await this.db.execute(sql21`SELECT
2338
- i.relname AS name,
2339
- idx.indisunique AS is_unique,
2340
- idx.indisprimary AS is_primary,
2341
- con.contype = 'u' AS is_unique_constraint,
2342
- ARRAY(
2343
- SELECT a.attname
2344
- FROM pg_attribute a
2345
- WHERE a.attrelid = idx.indrelid
2346
- AND a.attnum = ANY(idx.indkey::int[])
2347
- ORDER BY a.attnum
2348
- ) AS columns,
2349
- am.amname AS method
2350
- FROM pg_index idx
2351
- JOIN pg_class i ON i.oid = idx.indexrelid
2352
- JOIN pg_class c ON c.oid = idx.indrelid
2353
- JOIN pg_namespace n ON n.oid = c.relnamespace
2354
- JOIN pg_am am ON am.oid = i.relam
2355
- LEFT JOIN pg_constraint con ON con.conindid = idx.indexrelid
2356
- WHERE n.nspname = ${schemaName}
2357
- AND c.relname = ${tableName}`);
2358
- return getRows2(result);
2340
+ const changesToDefault = changesTo?.default;
2341
+ const changesFromDefault = changesFrom?.default;
2342
+ if (changesToDefault !== changesFromDefault) {
2343
+ if (changesToDefault !== undefined) {
2344
+ const defaultValue = formatDefaultValue(changesToDefault, changesToType || "");
2345
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DEFAULT ${defaultValue};`);
2346
+ } else {
2347
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP DEFAULT;`);
2348
+ }
2359
2349
  }
2360
- async getForeignKeys(schemaName, tableName) {
2361
- const result = await this.db.execute(sql21`SELECT
2362
- con.conname AS name,
2363
- att.attname AS column_name,
2364
- fnsp.nspname AS foreign_table_schema,
2365
- frel.relname AS foreign_table_name,
2366
- fatt.attname AS foreign_column_name,
2367
- CASE con.confupdtype
2368
- WHEN 'a' THEN 'NO ACTION'
2369
- WHEN 'r' THEN 'RESTRICT'
2370
- WHEN 'n' THEN 'SET NULL'
2371
- WHEN 'c' THEN 'CASCADE'
2372
- WHEN 'd' THEN 'SET DEFAULT'
2373
- END AS update_rule,
2374
- CASE con.confdeltype
2375
- WHEN 'a' THEN 'NO ACTION'
2376
- WHEN 'r' THEN 'RESTRICT'
2377
- WHEN 'n' THEN 'SET NULL'
2378
- WHEN 'c' THEN 'CASCADE'
2379
- WHEN 'd' THEN 'SET DEFAULT'
2380
- END AS delete_rule
2381
- FROM pg_catalog.pg_constraint con
2382
- JOIN pg_catalog.pg_class rel ON rel.oid = con.conrelid
2383
- JOIN pg_catalog.pg_namespace nsp ON nsp.oid = con.connamespace
2384
- LEFT JOIN pg_catalog.pg_attribute att ON att.attnum = ANY (con.conkey)
2385
- AND att.attrelid = con.conrelid
2386
- LEFT JOIN pg_catalog.pg_class frel ON frel.oid = con.confrelid
2387
- LEFT JOIN pg_catalog.pg_namespace fnsp ON fnsp.oid = frel.relnamespace
2388
- LEFT JOIN pg_catalog.pg_attribute fatt ON fatt.attnum = ANY (con.confkey)
2389
- AND fatt.attrelid = con.confrelid
2390
- WHERE con.contype = 'f'
2391
- AND nsp.nspname = ${schemaName}
2392
- AND rel.relname = ${tableName}`);
2393
- return getRows2(result);
2350
+ return statements;
2351
+ }
2352
+ function checkIfNeedsUsingClause(fromType, toType) {
2353
+ if (!fromType || !toType)
2354
+ return false;
2355
+ if (fromType.includes("enum") || toType.includes("enum")) {
2356
+ return true;
2394
2357
  }
2395
- async getPrimaryKeys(schemaName, tableName) {
2396
- const result = await this.db.execute(sql21`SELECT
2397
- con.conname AS name,
2398
- ARRAY(
2399
- SELECT a.attname
2400
- FROM pg_attribute a
2401
- WHERE a.attrelid = con.conrelid
2402
- AND a.attnum = ANY(con.conkey)
2403
- ORDER BY a.attnum
2404
- ) AS columns
2405
- FROM pg_constraint con
2406
- JOIN pg_class rel ON rel.oid = con.conrelid
2407
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2408
- WHERE con.contype = 'p'
2409
- AND nsp.nspname = ${schemaName}
2410
- AND rel.relname = ${tableName}`);
2411
- return getRows2(result);
2358
+ const fromBase = fromType.split("(")[0].toLowerCase();
2359
+ const toBase = toType.split("(")[0].toLowerCase();
2360
+ if ((fromBase === "text" || fromBase === "varchar" || fromBase === "character varying") && (toBase === "jsonb" || toBase === "json")) {
2361
+ return true;
2412
2362
  }
2413
- async getUniqueConstraints(schemaName, tableName) {
2414
- const result = await this.db.execute(sql21`SELECT
2415
- con.conname AS name,
2416
- ARRAY(
2417
- SELECT a.attname
2418
- FROM pg_attribute a
2419
- WHERE a.attrelid = con.conrelid
2420
- AND a.attnum = ANY(con.conkey)
2421
- ORDER BY a.attnum
2422
- ) AS columns
2423
- FROM pg_constraint con
2424
- JOIN pg_class rel ON rel.oid = con.conrelid
2425
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2426
- WHERE con.contype = 'u'
2427
- AND nsp.nspname = ${schemaName}
2428
- AND rel.relname = ${tableName}`);
2429
- return getRows2(result);
2363
+ const needsUsingPairs = [
2364
+ ["integer", "boolean"],
2365
+ ["boolean", "integer"],
2366
+ ["text", "integer"],
2367
+ ["text", "numeric"],
2368
+ ["text", "boolean"],
2369
+ ["text", "uuid"],
2370
+ ["text", "jsonb"],
2371
+ ["text", "json"],
2372
+ ["varchar", "integer"],
2373
+ ["varchar", "numeric"],
2374
+ ["varchar", "boolean"],
2375
+ ["varchar", "uuid"],
2376
+ ["varchar", "jsonb"],
2377
+ ["varchar", "json"],
2378
+ ["character varying", "jsonb"],
2379
+ ["character varying", "json"]
2380
+ ];
2381
+ for (const [from, to] of needsUsingPairs) {
2382
+ if (fromBase === from && toBase === to || fromBase === to && toBase === from) {
2383
+ return true;
2384
+ }
2430
2385
  }
2431
- async getCheckConstraints(schemaName, tableName) {
2432
- const result = await this.db.execute(sql21`SELECT
2433
- con.conname AS name,
2434
- pg_get_constraintdef(con.oid) AS definition
2435
- FROM pg_constraint con
2436
- JOIN pg_class rel ON rel.oid = con.conrelid
2437
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2438
- WHERE con.contype = 'c'
2439
- AND nsp.nspname = ${schemaName}
2440
- AND rel.relname = ${tableName}`);
2441
- return getRows2(result);
2386
+ return false;
2387
+ }
2388
+ function formatDefaultValue(value, type) {
2389
+ if (value === null || value === "NULL") {
2390
+ return "NULL";
2442
2391
  }
2443
- async getEnums(schemaName) {
2444
- const result = await this.db.execute(sql21`SELECT
2445
- n.nspname AS schema,
2446
- t.typname AS name,
2447
- e.enumlabel AS value,
2448
- e.enumsortorder AS sort_order
2449
- FROM pg_type t
2450
- JOIN pg_enum e ON t.oid = e.enumtypid
2451
- JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
2452
- WHERE n.nspname = ${schemaName}
2453
- ORDER BY schema, name, sort_order`);
2454
- return getRows2(result);
2392
+ if (type && (type.toLowerCase().includes("boolean") || type.toLowerCase() === "bool")) {
2393
+ if (value === true || value === "true" || value === "t" || value === 1) {
2394
+ return "true";
2395
+ }
2396
+ if (value === false || value === "false" || value === "f" || value === 0) {
2397
+ return "false";
2398
+ }
2455
2399
  }
2456
- parseDefault(defaultValue, dataType) {
2457
- if (!defaultValue)
2458
- return;
2459
- const match = defaultValue.match(/^'(.*)'::/);
2460
- if (match) {
2461
- return `'${match[1]}'`;
2400
+ if (type?.match(/^(integer|bigint|smallint|numeric|decimal|real|double)/i)) {
2401
+ return String(value);
2402
+ }
2403
+ if (typeof value === "string") {
2404
+ if (value.includes("::")) {
2405
+ return value;
2462
2406
  }
2463
- if (defaultValue.includes("nextval(")) {
2464
- return;
2407
+ if (value.startsWith("'") && value.endsWith("'")) {
2408
+ return value;
2465
2409
  }
2466
- if (dataType === "boolean") {
2467
- if (defaultValue === "true")
2468
- return "true";
2469
- if (defaultValue === "false")
2470
- return "false";
2410
+ if (value.match(/^\w+\(\)/i) || value.includes("(") && value.includes(")")) {
2411
+ return value;
2471
2412
  }
2472
- return defaultValue;
2413
+ if (value.toUpperCase().startsWith("CURRENT_")) {
2414
+ return value;
2415
+ }
2416
+ return `'${value.replace(/'/g, "''")}'`;
2473
2417
  }
2474
- async hasExistingTables(pluginName) {
2475
- const schemaName = pluginName === "@elizaos/plugin-sql" ? "public" : this.deriveSchemaName(pluginName);
2476
- const result = await this.db.execute(sql21`SELECT COUNT(*) AS count
2477
- FROM information_schema.tables
2478
- WHERE table_schema = ${schemaName}
2479
- AND table_type = 'BASE TABLE'`);
2480
- const firstRow = result.rows?.[0];
2481
- const count = parseInt(firstRow && firstRow.count || "0", 10);
2482
- return count > 0;
2418
+ return String(value);
2419
+ }
2420
+ function generateCreateIndexSQL(index7) {
2421
+ const unique3 = index7.isUnique ? "UNIQUE " : "";
2422
+ const method = index7.method || "btree";
2423
+ const columns = index7.columns.map((c) => {
2424
+ if (c.isExpression) {
2425
+ return c.expression;
2426
+ }
2427
+ return `"${c.expression}"${c.asc === false ? " DESC" : ""}`;
2428
+ }).join(", ");
2429
+ const indexName = index7.name.includes(".") ? index7.name.split(".")[1] : index7.name;
2430
+ let tableRef;
2431
+ const indexTable = index7.table;
2432
+ if (indexTable?.includes(".")) {
2433
+ const [schema, table] = indexTable.split(".");
2434
+ tableRef = `"${schema}"."${table}"`;
2435
+ } else {
2436
+ tableRef = `"${indexTable || ""}"`;
2483
2437
  }
2484
- deriveSchemaName(pluginName) {
2485
- return pluginName.replace("@", "").replace("/", "_").replace(/-/g, "_").toLowerCase();
2438
+ return `CREATE ${unique3}INDEX "${indexName}" ON ${tableRef} USING ${method} (${columns});`;
2439
+ }
2440
+ function generateDropIndexSQL(index7) {
2441
+ const indexNameFull = typeof index7 === "string" ? index7 : index7.name;
2442
+ const indexName = indexNameFull.includes(".") ? indexNameFull.split(".")[1] : indexNameFull;
2443
+ return `DROP INDEX IF EXISTS "${indexName}";`;
2444
+ }
2445
+ function generateCreateForeignKeySQL(fk) {
2446
+ return wrapConstraintCreationGuard(fk.name, buildCreateForeignKeyBodySQL(fk));
2447
+ }
2448
+ function generateDropForeignKeySQL(fk) {
2449
+ const [schema, tableName] = fk.tableFrom ? fk.tableFrom.includes(".") ? fk.tableFrom.split(".") : ["public", fk.tableFrom] : ["public", ""];
2450
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${fk.name}";`;
2451
+ }
2452
+ function generateCreateUniqueConstraintSQL(constraint) {
2453
+ const table = constraint.table || "";
2454
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2455
+ const name = constraint.name;
2456
+ const columns = constraint.columns.map((c) => `"${c}"`).join(", ");
2457
+ let sql22 = `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" UNIQUE`;
2458
+ if (constraint.nullsNotDistinct) {
2459
+ sql22 += ` NULLS NOT DISTINCT`;
2486
2460
  }
2461
+ sql22 += ` (${columns});`;
2462
+ return sql22;
2487
2463
  }
2488
- var init_database_introspector = () => {};
2464
+ function generateDropUniqueConstraintSQL(constraint) {
2465
+ const table = constraint.table || "";
2466
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2467
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2468
+ }
2469
+ function generateCreateCheckConstraintSQL(constraint) {
2470
+ const table = constraint.table || "";
2471
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2472
+ const name = constraint.name;
2473
+ const value = constraint.value;
2474
+ return `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" CHECK (${value});`;
2475
+ }
2476
+ function generateDropCheckConstraintSQL(constraint) {
2477
+ const table = constraint.table || "";
2478
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2479
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2480
+ }
2481
+ function buildCreateForeignKeyBodySQL(fk) {
2482
+ const schemaFrom = fk.schemaFrom || "public";
2483
+ const schemaTo = fk.schemaTo || "public";
2484
+ const tableFrom = fk.tableFrom;
2485
+ const columnsFrom = fk.columnsFrom.map((c) => `"${c}"`).join(", ");
2486
+ const columnsTo = fk.columnsTo.map((c) => `"${c}"`).join(", ");
2487
+ let sql22 = `ALTER TABLE "${schemaFrom}"."${tableFrom}" ADD CONSTRAINT "${fk.name}" FOREIGN KEY (${columnsFrom}) REFERENCES "${schemaTo}"."${fk.tableTo}" (${columnsTo})`;
2488
+ if (fk.onDelete) {
2489
+ sql22 += ` ON DELETE ${fk.onDelete}`;
2490
+ }
2491
+ if (fk.onUpdate) {
2492
+ sql22 += ` ON UPDATE ${fk.onUpdate}`;
2493
+ }
2494
+ return sql22;
2495
+ }
2496
+ function wrapConstraintCreationGuard(constraintName, statement) {
2497
+ const escapedConstraintName = constraintName.replace(/'/g, "''");
2498
+ return `DO $$ BEGIN IF NOT EXISTS (SELECT 1 FROM pg_constraint WHERE conname = '${escapedConstraintName}') THEN ${statement}; END IF; END $$;`;
2499
+ }
2500
+ var init_sql_generator = () => {};
2489
2501
 
2490
2502
  // runtime-migrator/extension-manager.ts
2491
2503
  import { logger as logger5 } from "@elizaos/core";
@@ -3161,14 +3173,10 @@ var init_runtime_migrator = __esm(() => {
3161
3173
  init_migration_tracker();
3162
3174
  init_snapshot_storage();
3163
3175
  });
3176
+
3164
3177
  // runtime-migrator/index.ts
3165
3178
  var init_runtime_migrator2 = __esm(() => {
3166
- init_snapshot_generator();
3167
- init_sql_generator();
3168
3179
  init_runtime_migrator();
3169
- init_journal_storage();
3170
- init_migration_tracker();
3171
- init_snapshot_storage();
3172
3180
  });
3173
3181
 
3174
3182
  // migration-service.ts
@@ -3782,7 +3790,7 @@ class BaseDrizzleAdapter extends DatabaseAdapter {
3782
3790
  return [String(names)];
3783
3791
  }
3784
3792
  isValidUUID(value) {
3785
- return /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i.test(value);
3793
+ return /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(value);
3786
3794
  }
3787
3795
  normalizeWorldData(world) {
3788
3796
  const worldData = {
@@ -7095,5 +7103,5 @@ export {
7095
7103
  DatabaseMigrationService
7096
7104
  };
7097
7105
 
7098
- //# debugId=65F51AC9F4802DC764756E2164756E21
7106
+ //# debugId=11DF3BC6739C08E664756E2164756E21
7099
7107
  //# sourceMappingURL=index.node.js.map