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

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.
@@ -1086,172 +1086,537 @@ var init_rls = __esm(() => {
1086
1086
  import_drizzle_orm20 = require("drizzle-orm");
1087
1087
  });
1088
1088
 
1089
- // runtime-migrator/drizzle-adapters/diff-calculator.ts
1090
- var exports_diff_calculator = {};
1091
- __export(exports_diff_calculator, {
1092
- hasDiffChanges: () => hasDiffChanges,
1093
- calculateDiff: () => calculateDiff
1094
- });
1095
- function normalizeType(type) {
1096
- if (!type)
1097
- return "";
1098
- const normalized = type.toLowerCase().trim();
1099
- if (normalized === "timestamp without time zone" || normalized === "timestamp with time zone") {
1100
- return "timestamp";
1101
- }
1102
- if (normalized === "serial") {
1103
- return "integer";
1104
- }
1105
- if (normalized === "bigserial") {
1106
- return "bigint";
1107
- }
1108
- if (normalized === "smallserial") {
1109
- return "smallint";
1110
- }
1111
- if (normalized.startsWith("numeric") || normalized.startsWith("decimal")) {
1112
- const match = normalized.match(/\((\d+)(?:,\s*(\d+))?\)/);
1113
- if (match) {
1114
- return `numeric(${match[1]}${match[2] ? `,${match[2]}` : ""})`;
1115
- }
1116
- return "numeric";
1117
- }
1118
- if (normalized.startsWith("character varying")) {
1119
- return normalized.replace("character varying", "varchar");
1120
- }
1121
- if (normalized === "text[]" || normalized === "_text") {
1122
- return "text[]";
1089
+ // runtime-migrator/crypto-utils.ts
1090
+ function extendedHash(str) {
1091
+ const h1 = hashWithSeed(str, 5381);
1092
+ const h2 = hashWithSeed(str, 7919);
1093
+ const h3 = hashWithSeed(str, 104729);
1094
+ const h4 = hashWithSeed(str, 224737);
1095
+ return h1 + h2 + h3 + h4;
1096
+ }
1097
+ function hashWithSeed(str, seed) {
1098
+ let hash = seed;
1099
+ for (let i = 0;i < str.length; i++) {
1100
+ hash = hash * 33 ^ str.charCodeAt(i);
1123
1101
  }
1124
- return normalized;
1102
+ return (hash >>> 0).toString(16).padStart(8, "0");
1125
1103
  }
1126
- function isIndexChanged(prevIndex, currIndex) {
1127
- if (prevIndex.isUnique !== currIndex.isUnique)
1128
- return true;
1129
- if (prevIndex.method !== currIndex.method)
1130
- return true;
1131
- if (prevIndex.where !== currIndex.where)
1132
- return true;
1133
- if (prevIndex.concurrently !== currIndex.concurrently)
1134
- return true;
1135
- const prevColumns = prevIndex.columns || [];
1136
- const currColumns = currIndex.columns || [];
1137
- if (prevColumns.length !== currColumns.length)
1138
- return true;
1139
- for (let i = 0;i < prevColumns.length; i++) {
1140
- const prevCol = prevColumns[i];
1141
- const currCol = currColumns[i];
1142
- if (typeof prevCol === "string" && typeof currCol === "string") {
1143
- if (prevCol !== currCol)
1144
- return true;
1145
- } else if (typeof prevCol === "object" && typeof currCol === "object") {
1146
- if (prevCol.expression !== currCol.expression)
1147
- return true;
1148
- if (prevCol.isExpression !== currCol.isExpression)
1149
- return true;
1150
- if (prevCol.asc !== currCol.asc)
1151
- return true;
1152
- if (prevCol.nulls !== currCol.nulls)
1153
- return true;
1154
- } else {
1155
- return true;
1156
- }
1104
+ function stringToBigInt(str) {
1105
+ const hash = extendedHash(str);
1106
+ let lockId = BigInt(`0x${hash.slice(0, 16)}`);
1107
+ const mask63Bits = 0x7fffffffffffffffn;
1108
+ lockId = lockId & mask63Bits;
1109
+ if (lockId === 0n) {
1110
+ lockId = 1n;
1157
1111
  }
1158
- return false;
1112
+ return lockId;
1159
1113
  }
1160
- async function calculateDiff(previousSnapshot, currentSnapshot) {
1161
- const diff = {
1162
- tables: {
1163
- created: [],
1164
- deleted: [],
1165
- modified: []
1166
- },
1167
- columns: {
1168
- added: [],
1169
- deleted: [],
1170
- modified: []
1171
- },
1172
- indexes: {
1173
- created: [],
1174
- deleted: [],
1175
- altered: []
1176
- },
1177
- foreignKeys: {
1178
- created: [],
1179
- deleted: [],
1180
- altered: []
1181
- },
1182
- uniqueConstraints: {
1183
- created: [],
1184
- deleted: []
1185
- },
1186
- checkConstraints: {
1187
- created: [],
1188
- deleted: []
1189
- }
1190
- };
1191
- if (!previousSnapshot) {
1192
- diff.tables.created = Object.keys(currentSnapshot.tables);
1193
- for (const tableName in currentSnapshot.tables) {
1194
- const table = currentSnapshot.tables[tableName];
1195
- if (table.indexes) {
1196
- for (const indexName in table.indexes) {
1197
- diff.indexes.created.push({
1198
- ...table.indexes[indexName],
1199
- table: tableName
1200
- });
1201
- }
1114
+
1115
+ // runtime-migrator/drizzle-adapters/database-introspector.ts
1116
+ function getRows2(result) {
1117
+ return result.rows;
1118
+ }
1119
+
1120
+ class DatabaseIntrospector {
1121
+ db;
1122
+ constructor(db) {
1123
+ this.db = db;
1124
+ }
1125
+ async introspectSchema(schemaName = "public") {
1126
+ import_core4.logger.info({ src: "plugin:sql", schemaName }, "Starting database introspection");
1127
+ const tables = {};
1128
+ const schemas = {};
1129
+ const enums = {};
1130
+ const allTables = await this.getTables(schemaName);
1131
+ for (const tableInfo of allTables) {
1132
+ const tableName = tableInfo.table_name;
1133
+ const tableSchema = tableInfo.table_schema || "public";
1134
+ import_core4.logger.debug({ src: "plugin:sql", tableSchema, tableName }, "Introspecting table");
1135
+ const columns = await this.getColumns(tableSchema, tableName);
1136
+ const columnsObject = {};
1137
+ const uniqueConstraintObject = {};
1138
+ for (const col of columns) {
1139
+ columnsObject[col.column_name] = {
1140
+ name: col.column_name,
1141
+ type: col.data_type,
1142
+ primaryKey: col.is_primary || false,
1143
+ notNull: col.is_nullable === "NO",
1144
+ default: col.column_default ? this.parseDefault(col.column_default, col.data_type) : undefined
1145
+ };
1202
1146
  }
1203
- if (table.foreignKeys) {
1204
- for (const fkName in table.foreignKeys) {
1205
- diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1147
+ const indexes = await this.getIndexes(tableSchema, tableName);
1148
+ const indexesObject = {};
1149
+ for (const idx of indexes) {
1150
+ if (!idx.is_primary && !idx.is_unique_constraint) {
1151
+ if (idx.columns && Array.isArray(idx.columns) && idx.columns.length > 0) {
1152
+ indexesObject[idx.name] = {
1153
+ name: idx.name,
1154
+ columns: idx.columns.map((col) => ({
1155
+ expression: col,
1156
+ isExpression: false
1157
+ })),
1158
+ isUnique: idx.is_unique,
1159
+ method: idx.method || "btree"
1160
+ };
1161
+ }
1206
1162
  }
1207
1163
  }
1208
- }
1209
- return diff;
1210
- }
1211
- const prevTables = previousSnapshot.tables || {};
1212
- const currTables = currentSnapshot.tables || {};
1213
- for (const tableName in currTables) {
1214
- if (!(tableName in prevTables)) {
1215
- diff.tables.created.push(tableName);
1216
- const table = currTables[tableName];
1217
- if (table.indexes) {
1218
- for (const indexName in table.indexes) {
1219
- diff.indexes.created.push({
1220
- ...table.indexes[indexName],
1221
- table: tableName
1222
- });
1223
- }
1164
+ const foreignKeys = await this.getForeignKeys(tableSchema, tableName);
1165
+ const foreignKeysObject = {};
1166
+ for (const fk of foreignKeys) {
1167
+ foreignKeysObject[fk.name] = {
1168
+ name: fk.name,
1169
+ tableFrom: tableName,
1170
+ schemaFrom: tableSchema,
1171
+ tableTo: fk.foreign_table_name,
1172
+ schemaTo: fk.foreign_table_schema || "public",
1173
+ columnsFrom: [fk.column_name],
1174
+ columnsTo: [fk.foreign_column_name],
1175
+ onDelete: fk.delete_rule?.toLowerCase() || "no action",
1176
+ onUpdate: fk.update_rule?.toLowerCase() || "no action"
1177
+ };
1224
1178
  }
1225
- if (table.uniqueConstraints) {
1226
- for (const uqName in table.uniqueConstraints) {
1227
- diff.uniqueConstraints.created.push({
1228
- ...table.uniqueConstraints[uqName],
1229
- table: tableName
1230
- });
1231
- }
1179
+ const primaryKeys = await this.getPrimaryKeys(tableSchema, tableName);
1180
+ const primaryKeysObject = {};
1181
+ for (const pk of primaryKeys) {
1182
+ primaryKeysObject[pk.name] = {
1183
+ name: pk.name,
1184
+ columns: pk.columns
1185
+ };
1232
1186
  }
1233
- if (table.checkConstraints) {
1234
- for (const checkName in table.checkConstraints) {
1235
- diff.checkConstraints.created.push({
1236
- ...table.checkConstraints[checkName],
1237
- table: tableName
1238
- });
1239
- }
1187
+ const uniqueConstraints = await this.getUniqueConstraints(tableSchema, tableName);
1188
+ for (const unq of uniqueConstraints) {
1189
+ uniqueConstraintObject[unq.name] = {
1190
+ name: unq.name,
1191
+ columns: unq.columns,
1192
+ nullsNotDistinct: false
1193
+ };
1240
1194
  }
1241
- if (table.foreignKeys) {
1242
- for (const fkName in table.foreignKeys) {
1243
- diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1244
- }
1195
+ const checkConstraints = await this.getCheckConstraints(tableSchema, tableName);
1196
+ const checksObject = {};
1197
+ for (const check3 of checkConstraints) {
1198
+ checksObject[check3.name] = {
1199
+ name: check3.name,
1200
+ value: check3.definition
1201
+ };
1245
1202
  }
1246
- }
1247
- }
1248
- for (const tableName in prevTables) {
1249
- if (!(tableName in currTables)) {
1250
- diff.tables.deleted.push(tableName);
1251
- }
1252
- }
1253
- for (const tableName in currTables) {
1254
- if (tableName in prevTables) {
1203
+ tables[`${tableSchema}.${tableName}`] = {
1204
+ name: tableName,
1205
+ schema: tableSchema,
1206
+ columns: columnsObject,
1207
+ indexes: indexesObject,
1208
+ foreignKeys: foreignKeysObject,
1209
+ compositePrimaryKeys: primaryKeysObject,
1210
+ uniqueConstraints: uniqueConstraintObject,
1211
+ checkConstraints: checksObject
1212
+ };
1213
+ if (tableSchema && tableSchema !== "public") {
1214
+ schemas[tableSchema] = tableSchema;
1215
+ }
1216
+ }
1217
+ const enumsResult = await this.getEnums(schemaName);
1218
+ for (const enumInfo of enumsResult) {
1219
+ const key = `${enumInfo.schema}.${enumInfo.name}`;
1220
+ if (!enums[key]) {
1221
+ enums[key] = {
1222
+ name: enumInfo.name,
1223
+ schema: enumInfo.schema,
1224
+ values: []
1225
+ };
1226
+ }
1227
+ enums[key].values.push(enumInfo.value);
1228
+ }
1229
+ import_core4.logger.info({ src: "plugin:sql", tableCount: Object.keys(tables).length }, "Database introspection complete");
1230
+ return {
1231
+ version: "7",
1232
+ dialect: "postgresql",
1233
+ tables,
1234
+ schemas,
1235
+ enums,
1236
+ _meta: {
1237
+ schemas: {},
1238
+ tables: {},
1239
+ columns: {}
1240
+ }
1241
+ };
1242
+ }
1243
+ async getTables(schemaName) {
1244
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1245
+ table_schema,
1246
+ table_name
1247
+ FROM information_schema.tables
1248
+ WHERE table_schema = ${schemaName}
1249
+ AND table_type = 'BASE TABLE'
1250
+ ORDER BY table_name`);
1251
+ return getRows2(result);
1252
+ }
1253
+ async getColumns(schemaName, tableName) {
1254
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1255
+ a.attname AS column_name,
1256
+ CASE
1257
+ WHEN a.attnotnull THEN 'NO'
1258
+ ELSE 'YES'
1259
+ END AS is_nullable,
1260
+ CASE
1261
+ WHEN a.atttypid = ANY ('{int,int8,int2}'::regtype[])
1262
+ AND EXISTS (
1263
+ SELECT FROM pg_attrdef ad
1264
+ WHERE ad.adrelid = a.attrelid
1265
+ AND ad.adnum = a.attnum
1266
+ AND pg_get_expr(ad.adbin, ad.adrelid) = 'nextval('''
1267
+ || pg_get_serial_sequence(a.attrelid::regclass::text, a.attname)::regclass || '''::regclass)'
1268
+ )
1269
+ THEN CASE a.atttypid
1270
+ WHEN 'int'::regtype THEN 'serial'
1271
+ WHEN 'int8'::regtype THEN 'bigserial'
1272
+ WHEN 'int2'::regtype THEN 'smallserial'
1273
+ END
1274
+ ELSE format_type(a.atttypid, a.atttypmod)
1275
+ END AS data_type,
1276
+ pg_get_expr(ad.adbin, ad.adrelid) AS column_default,
1277
+ CASE
1278
+ WHEN con.contype = 'p' THEN true
1279
+ ELSE false
1280
+ END AS is_primary
1281
+ FROM pg_attribute a
1282
+ JOIN pg_class cls ON cls.oid = a.attrelid
1283
+ JOIN pg_namespace ns ON ns.oid = cls.relnamespace
1284
+ LEFT JOIN pg_attrdef ad ON ad.adrelid = a.attrelid AND ad.adnum = a.attnum
1285
+ LEFT JOIN pg_constraint con ON con.conrelid = a.attrelid
1286
+ AND a.attnum = ANY(con.conkey)
1287
+ AND con.contype = 'p'
1288
+ WHERE
1289
+ a.attnum > 0
1290
+ AND NOT a.attisdropped
1291
+ AND ns.nspname = ${schemaName}
1292
+ AND cls.relname = ${tableName}
1293
+ ORDER BY a.attnum`);
1294
+ return getRows2(result);
1295
+ }
1296
+ async getIndexes(schemaName, tableName) {
1297
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1298
+ i.relname AS name,
1299
+ idx.indisunique AS is_unique,
1300
+ idx.indisprimary AS is_primary,
1301
+ con.contype = 'u' AS is_unique_constraint,
1302
+ ARRAY(
1303
+ SELECT a.attname
1304
+ FROM pg_attribute a
1305
+ WHERE a.attrelid = idx.indrelid
1306
+ AND a.attnum = ANY(idx.indkey::int[])
1307
+ ORDER BY a.attnum
1308
+ ) AS columns,
1309
+ am.amname AS method
1310
+ FROM pg_index idx
1311
+ JOIN pg_class i ON i.oid = idx.indexrelid
1312
+ JOIN pg_class c ON c.oid = idx.indrelid
1313
+ JOIN pg_namespace n ON n.oid = c.relnamespace
1314
+ JOIN pg_am am ON am.oid = i.relam
1315
+ LEFT JOIN pg_constraint con ON con.conindid = idx.indexrelid
1316
+ WHERE n.nspname = ${schemaName}
1317
+ AND c.relname = ${tableName}`);
1318
+ return getRows2(result);
1319
+ }
1320
+ async getForeignKeys(schemaName, tableName) {
1321
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1322
+ con.conname AS name,
1323
+ att.attname AS column_name,
1324
+ fnsp.nspname AS foreign_table_schema,
1325
+ frel.relname AS foreign_table_name,
1326
+ fatt.attname AS foreign_column_name,
1327
+ CASE con.confupdtype
1328
+ WHEN 'a' THEN 'NO ACTION'
1329
+ WHEN 'r' THEN 'RESTRICT'
1330
+ WHEN 'n' THEN 'SET NULL'
1331
+ WHEN 'c' THEN 'CASCADE'
1332
+ WHEN 'd' THEN 'SET DEFAULT'
1333
+ END AS update_rule,
1334
+ CASE con.confdeltype
1335
+ WHEN 'a' THEN 'NO ACTION'
1336
+ WHEN 'r' THEN 'RESTRICT'
1337
+ WHEN 'n' THEN 'SET NULL'
1338
+ WHEN 'c' THEN 'CASCADE'
1339
+ WHEN 'd' THEN 'SET DEFAULT'
1340
+ END AS delete_rule
1341
+ FROM pg_catalog.pg_constraint con
1342
+ JOIN pg_catalog.pg_class rel ON rel.oid = con.conrelid
1343
+ JOIN pg_catalog.pg_namespace nsp ON nsp.oid = con.connamespace
1344
+ LEFT JOIN pg_catalog.pg_attribute att ON att.attnum = ANY (con.conkey)
1345
+ AND att.attrelid = con.conrelid
1346
+ LEFT JOIN pg_catalog.pg_class frel ON frel.oid = con.confrelid
1347
+ LEFT JOIN pg_catalog.pg_namespace fnsp ON fnsp.oid = frel.relnamespace
1348
+ LEFT JOIN pg_catalog.pg_attribute fatt ON fatt.attnum = ANY (con.confkey)
1349
+ AND fatt.attrelid = con.confrelid
1350
+ WHERE con.contype = 'f'
1351
+ AND nsp.nspname = ${schemaName}
1352
+ AND rel.relname = ${tableName}`);
1353
+ return getRows2(result);
1354
+ }
1355
+ async getPrimaryKeys(schemaName, tableName) {
1356
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1357
+ con.conname AS name,
1358
+ ARRAY(
1359
+ SELECT a.attname
1360
+ FROM pg_attribute a
1361
+ WHERE a.attrelid = con.conrelid
1362
+ AND a.attnum = ANY(con.conkey)
1363
+ ORDER BY a.attnum
1364
+ ) AS columns
1365
+ FROM pg_constraint con
1366
+ JOIN pg_class rel ON rel.oid = con.conrelid
1367
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1368
+ WHERE con.contype = 'p'
1369
+ AND nsp.nspname = ${schemaName}
1370
+ AND rel.relname = ${tableName}`);
1371
+ return getRows2(result);
1372
+ }
1373
+ async getUniqueConstraints(schemaName, tableName) {
1374
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1375
+ con.conname AS name,
1376
+ ARRAY(
1377
+ SELECT a.attname
1378
+ FROM pg_attribute a
1379
+ WHERE a.attrelid = con.conrelid
1380
+ AND a.attnum = ANY(con.conkey)
1381
+ ORDER BY a.attnum
1382
+ ) AS columns
1383
+ FROM pg_constraint con
1384
+ JOIN pg_class rel ON rel.oid = con.conrelid
1385
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1386
+ WHERE con.contype = 'u'
1387
+ AND nsp.nspname = ${schemaName}
1388
+ AND rel.relname = ${tableName}`);
1389
+ return getRows2(result);
1390
+ }
1391
+ async getCheckConstraints(schemaName, tableName) {
1392
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1393
+ con.conname AS name,
1394
+ pg_get_constraintdef(con.oid) AS definition
1395
+ FROM pg_constraint con
1396
+ JOIN pg_class rel ON rel.oid = con.conrelid
1397
+ JOIN pg_namespace nsp ON nsp.oid = con.connamespace
1398
+ WHERE con.contype = 'c'
1399
+ AND nsp.nspname = ${schemaName}
1400
+ AND rel.relname = ${tableName}`);
1401
+ return getRows2(result);
1402
+ }
1403
+ async getEnums(schemaName) {
1404
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT
1405
+ n.nspname AS schema,
1406
+ t.typname AS name,
1407
+ e.enumlabel AS value,
1408
+ e.enumsortorder AS sort_order
1409
+ FROM pg_type t
1410
+ JOIN pg_enum e ON t.oid = e.enumtypid
1411
+ JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
1412
+ WHERE n.nspname = ${schemaName}
1413
+ ORDER BY schema, name, sort_order`);
1414
+ return getRows2(result);
1415
+ }
1416
+ parseDefault(defaultValue, dataType) {
1417
+ if (!defaultValue)
1418
+ return;
1419
+ const match = defaultValue.match(/^'(.*)'::/);
1420
+ if (match) {
1421
+ return `'${match[1]}'`;
1422
+ }
1423
+ if (defaultValue.includes("nextval(")) {
1424
+ return;
1425
+ }
1426
+ if (dataType === "boolean") {
1427
+ if (defaultValue === "true")
1428
+ return "true";
1429
+ if (defaultValue === "false")
1430
+ return "false";
1431
+ }
1432
+ return defaultValue;
1433
+ }
1434
+ async hasExistingTables(pluginName) {
1435
+ const schemaName = pluginName === "@elizaos/plugin-sql" ? "public" : this.deriveSchemaName(pluginName);
1436
+ const result = await this.db.execute(import_drizzle_orm21.sql`SELECT COUNT(*) AS count
1437
+ FROM information_schema.tables
1438
+ WHERE table_schema = ${schemaName}
1439
+ AND table_type = 'BASE TABLE'`);
1440
+ const firstRow = result.rows?.[0];
1441
+ const count = parseInt(firstRow && firstRow.count || "0", 10);
1442
+ return count > 0;
1443
+ }
1444
+ deriveSchemaName(pluginName) {
1445
+ return pluginName.replace("@", "").replace("/", "_").replace(/-/g, "_").toLowerCase();
1446
+ }
1447
+ }
1448
+ var import_core4, import_drizzle_orm21;
1449
+ var init_database_introspector = __esm(() => {
1450
+ import_core4 = require("@elizaos/core");
1451
+ import_drizzle_orm21 = require("drizzle-orm");
1452
+ });
1453
+
1454
+ // runtime-migrator/drizzle-adapters/diff-calculator.ts
1455
+ var exports_diff_calculator = {};
1456
+ __export(exports_diff_calculator, {
1457
+ hasDiffChanges: () => hasDiffChanges,
1458
+ calculateDiff: () => calculateDiff
1459
+ });
1460
+ function normalizeType(type) {
1461
+ if (!type)
1462
+ return "";
1463
+ const normalized = type.toLowerCase().trim();
1464
+ if (normalized === "timestamp without time zone" || normalized === "timestamp with time zone") {
1465
+ return "timestamp";
1466
+ }
1467
+ if (normalized === "serial") {
1468
+ return "integer";
1469
+ }
1470
+ if (normalized === "bigserial") {
1471
+ return "bigint";
1472
+ }
1473
+ if (normalized === "smallserial") {
1474
+ return "smallint";
1475
+ }
1476
+ if (normalized.startsWith("numeric") || normalized.startsWith("decimal")) {
1477
+ const match = normalized.match(/\((\d+)(?:,\s*(\d+))?\)/);
1478
+ if (match) {
1479
+ return `numeric(${match[1]}${match[2] ? `,${match[2]}` : ""})`;
1480
+ }
1481
+ return "numeric";
1482
+ }
1483
+ if (normalized.startsWith("character varying")) {
1484
+ return normalized.replace("character varying", "varchar");
1485
+ }
1486
+ if (normalized === "text[]" || normalized === "_text") {
1487
+ return "text[]";
1488
+ }
1489
+ return normalized;
1490
+ }
1491
+ function isIndexChanged(prevIndex, currIndex) {
1492
+ if (prevIndex.isUnique !== currIndex.isUnique)
1493
+ return true;
1494
+ if (prevIndex.method !== currIndex.method)
1495
+ return true;
1496
+ if (prevIndex.where !== currIndex.where)
1497
+ return true;
1498
+ if (prevIndex.concurrently !== currIndex.concurrently)
1499
+ return true;
1500
+ const prevColumns = prevIndex.columns || [];
1501
+ const currColumns = currIndex.columns || [];
1502
+ if (prevColumns.length !== currColumns.length)
1503
+ return true;
1504
+ for (let i = 0;i < prevColumns.length; i++) {
1505
+ const prevCol = prevColumns[i];
1506
+ const currCol = currColumns[i];
1507
+ if (typeof prevCol === "string" && typeof currCol === "string") {
1508
+ if (prevCol !== currCol)
1509
+ return true;
1510
+ } else if (typeof prevCol === "object" && typeof currCol === "object") {
1511
+ if (prevCol.expression !== currCol.expression)
1512
+ return true;
1513
+ if (prevCol.isExpression !== currCol.isExpression)
1514
+ return true;
1515
+ if (prevCol.asc !== currCol.asc)
1516
+ return true;
1517
+ if (prevCol.nulls !== currCol.nulls)
1518
+ return true;
1519
+ } else {
1520
+ return true;
1521
+ }
1522
+ }
1523
+ return false;
1524
+ }
1525
+ async function calculateDiff(previousSnapshot, currentSnapshot) {
1526
+ const diff = {
1527
+ tables: {
1528
+ created: [],
1529
+ deleted: [],
1530
+ modified: []
1531
+ },
1532
+ columns: {
1533
+ added: [],
1534
+ deleted: [],
1535
+ modified: []
1536
+ },
1537
+ indexes: {
1538
+ created: [],
1539
+ deleted: [],
1540
+ altered: []
1541
+ },
1542
+ foreignKeys: {
1543
+ created: [],
1544
+ deleted: [],
1545
+ altered: []
1546
+ },
1547
+ uniqueConstraints: {
1548
+ created: [],
1549
+ deleted: []
1550
+ },
1551
+ checkConstraints: {
1552
+ created: [],
1553
+ deleted: []
1554
+ }
1555
+ };
1556
+ if (!previousSnapshot) {
1557
+ diff.tables.created = Object.keys(currentSnapshot.tables);
1558
+ for (const tableName in currentSnapshot.tables) {
1559
+ const table = currentSnapshot.tables[tableName];
1560
+ if (table.indexes) {
1561
+ for (const indexName in table.indexes) {
1562
+ diff.indexes.created.push({
1563
+ ...table.indexes[indexName],
1564
+ table: tableName
1565
+ });
1566
+ }
1567
+ }
1568
+ if (table.foreignKeys) {
1569
+ for (const fkName in table.foreignKeys) {
1570
+ diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1571
+ }
1572
+ }
1573
+ }
1574
+ return diff;
1575
+ }
1576
+ const prevTables = previousSnapshot.tables || {};
1577
+ const currTables = currentSnapshot.tables || {};
1578
+ for (const tableName in currTables) {
1579
+ if (!(tableName in prevTables)) {
1580
+ diff.tables.created.push(tableName);
1581
+ const table = currTables[tableName];
1582
+ if (table.indexes) {
1583
+ for (const indexName in table.indexes) {
1584
+ diff.indexes.created.push({
1585
+ ...table.indexes[indexName],
1586
+ table: tableName
1587
+ });
1588
+ }
1589
+ }
1590
+ if (table.uniqueConstraints) {
1591
+ for (const uqName in table.uniqueConstraints) {
1592
+ diff.uniqueConstraints.created.push({
1593
+ ...table.uniqueConstraints[uqName],
1594
+ table: tableName
1595
+ });
1596
+ }
1597
+ }
1598
+ if (table.checkConstraints) {
1599
+ for (const checkName in table.checkConstraints) {
1600
+ diff.checkConstraints.created.push({
1601
+ ...table.checkConstraints[checkName],
1602
+ table: tableName
1603
+ });
1604
+ }
1605
+ }
1606
+ if (table.foreignKeys) {
1607
+ for (const fkName in table.foreignKeys) {
1608
+ diff.foreignKeys.created.push(table.foreignKeys[fkName]);
1609
+ }
1610
+ }
1611
+ }
1612
+ }
1613
+ for (const tableName in prevTables) {
1614
+ if (!(tableName in currTables)) {
1615
+ diff.tables.deleted.push(tableName);
1616
+ }
1617
+ }
1618
+ for (const tableName in currTables) {
1619
+ if (tableName in prevTables) {
1255
1620
  const prevTable = prevTables[tableName];
1256
1621
  const currTable = currTables[tableName];
1257
1622
  const prevTableJson = JSON.stringify({
@@ -1417,32 +1782,6 @@ function hasDiffChanges(diff) {
1417
1782
  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;
1418
1783
  }
1419
1784
 
1420
- // runtime-migrator/crypto-utils.ts
1421
- function extendedHash(str) {
1422
- const h1 = hashWithSeed(str, 5381);
1423
- const h2 = hashWithSeed(str, 7919);
1424
- const h3 = hashWithSeed(str, 104729);
1425
- const h4 = hashWithSeed(str, 224737);
1426
- return h1 + h2 + h3 + h4;
1427
- }
1428
- function hashWithSeed(str, seed) {
1429
- let hash = seed;
1430
- for (let i = 0;i < str.length; i++) {
1431
- hash = hash * 33 ^ str.charCodeAt(i);
1432
- }
1433
- return (hash >>> 0).toString(16).padStart(8, "0");
1434
- }
1435
- function stringToBigInt(str) {
1436
- const hash = extendedHash(str);
1437
- let lockId = BigInt(`0x${hash.slice(0, 16)}`);
1438
- const mask63Bits = 0x7fffffffffffffffn;
1439
- lockId = lockId & mask63Bits;
1440
- if (lockId === 0n) {
1441
- lockId = 1n;
1442
- }
1443
- return lockId;
1444
- }
1445
-
1446
1785
  // runtime-migrator/drizzle-adapters/snapshot-generator.ts
1447
1786
  function escapeSingleQuotes(str) {
1448
1787
  return str.replace(/'/g, "''");
@@ -1478,7 +1817,7 @@ function extractTablesFromSchema(schema) {
1478
1817
  const tables = [];
1479
1818
  const exports2 = Object.values(schema);
1480
1819
  exports2.forEach((t) => {
1481
- if (import_drizzle_orm21.is(t, import_pg_core21.PgTable)) {
1820
+ if (import_drizzle_orm22.is(t, import_pg_core21.PgTable)) {
1482
1821
  tables.push(t);
1483
1822
  }
1484
1823
  });
@@ -1521,7 +1860,7 @@ async function generateSnapshot(schema) {
1521
1860
  notNull
1522
1861
  };
1523
1862
  if (column.default !== undefined) {
1524
- if (import_drizzle_orm21.is(column.default, import_drizzle_orm21.SQL)) {
1863
+ if (import_drizzle_orm22.is(column.default, import_drizzle_orm22.SQL)) {
1525
1864
  columnToSet.default = sqlToStr(column.default, undefined);
1526
1865
  } else {
1527
1866
  if (typeof column.default === "string") {
@@ -1595,7 +1934,7 @@ async function generateSnapshot(schema) {
1595
1934
  indexes.forEach((idx) => {
1596
1935
  const indexCols = idx.config.columns;
1597
1936
  const indexColumns = indexCols.map((col) => {
1598
- if (import_drizzle_orm21.is(col, import_drizzle_orm21.SQL)) {
1937
+ if (import_drizzle_orm22.is(col, import_drizzle_orm22.SQL)) {
1599
1938
  return {
1600
1939
  expression: dialect.sqlToQuery(col).sql,
1601
1940
  isExpression: true
@@ -1669,7 +2008,7 @@ function hasChanges(previousSnapshot, currentSnapshot) {
1669
2008
  const currHash = hashSnapshot(currentSnapshot);
1670
2009
  return prevHash !== currHash;
1671
2010
  }
1672
- var import_drizzle_orm21, import_pg_core21, sqlToStr = (sql21, _casing) => {
2011
+ var import_drizzle_orm22, import_pg_core21, sqlToStr = (sql22, _casing) => {
1673
2012
  const config = {
1674
2013
  escapeName: () => {
1675
2014
  throw new Error("we don't support params for `sql` default values");
@@ -1682,10 +2021,10 @@ var import_drizzle_orm21, import_pg_core21, sqlToStr = (sql21, _casing) => {
1682
2021
  },
1683
2022
  casing: undefined
1684
2023
  };
1685
- return sql21.toQuery(config).sql;
2024
+ return sql22.toQuery(config).sql;
1686
2025
  };
1687
2026
  var init_snapshot_generator = __esm(() => {
1688
- import_drizzle_orm21 = require("drizzle-orm");
2027
+ import_drizzle_orm22 = require("drizzle-orm");
1689
2028
  import_pg_core21 = require("drizzle-orm/pg-core");
1690
2029
  });
1691
2030
 
@@ -1819,7 +2158,7 @@ async function generateMigrationSQL(previousSnapshot, currentSnapshot, diff) {
1819
2158
  }
1820
2159
  const dataLossCheck = checkForDataLoss(diff);
1821
2160
  if (dataLossCheck.warnings.length > 0) {
1822
- import_core4.logger.warn({ src: "plugin:sql", warnings: dataLossCheck.warnings }, "Schema changes may cause data loss");
2161
+ import_core5.logger.warn({ src: "plugin:sql", warnings: dataLossCheck.warnings }, "Schema changes may cause data loss");
1823
2162
  }
1824
2163
  const schemasToCreate = new Set;
1825
2164
  for (const tableName of diff.tables.created) {
@@ -1972,24 +2311,29 @@ function generateCreateTableSQL(fullTableName, table) {
1972
2311
  const foreignKeys = table.foreignKeys || {};
1973
2312
  for (const [fkName, fkDef] of Object.entries(foreignKeys)) {
1974
2313
  const fk = fkDef;
1975
- 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}` : ""};`;
2314
+ const fkSQL = wrapConstraintCreationGuard(fkName, buildCreateForeignKeyBodySQL({
2315
+ ...fk,
2316
+ name: fkName,
2317
+ schemaFrom: schema,
2318
+ tableFrom: tableName
2319
+ }));
1976
2320
  fkSQLs.push(fkSQL);
1977
2321
  }
1978
2322
  return { tableSQL, fkSQLs };
1979
2323
  }
1980
2324
  function generateColumnDefinition(name, def) {
1981
- let sql21 = `"${name}" ${def.type}`;
2325
+ let sql22 = `"${name}" ${def.type}`;
1982
2326
  if (def.primaryKey && !def.type.includes("SERIAL")) {
1983
- sql21 += " PRIMARY KEY";
2327
+ sql22 += " PRIMARY KEY";
1984
2328
  }
1985
2329
  if (def.notNull) {
1986
- sql21 += " NOT NULL";
2330
+ sql22 += " NOT NULL";
1987
2331
  }
1988
2332
  if (def.default !== undefined) {
1989
2333
  const defaultValue = formatDefaultValue(def.default, def.type);
1990
- sql21 += ` DEFAULT ${defaultValue}`;
2334
+ sql22 += ` DEFAULT ${defaultValue}`;
1991
2335
  }
1992
- return sql21;
2336
+ return sql22;
1993
2337
  }
1994
2338
  function generateAddColumnSQL(table, column, definition) {
1995
2339
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
@@ -2009,537 +2353,205 @@ function generateAddColumnSQL(table, column, definition) {
2009
2353
  if (definitionWithGenerated.generated) {
2010
2354
  parts.push(`GENERATED ALWAYS AS (${definitionWithGenerated.generated}) STORED`);
2011
2355
  }
2012
- if (definition.notNull) {
2013
- parts.push("NOT NULL");
2014
- }
2015
- return `ALTER TABLE ${tableNameWithSchema} ADD COLUMN ${parts.join(" ")};`;
2016
- }
2017
- function generateDropColumnSQL(table, column) {
2018
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2019
- const tableNameWithSchema = `"${schema}"."${tableName}"`;
2020
- return `ALTER TABLE ${tableNameWithSchema} DROP COLUMN "${column}" CASCADE;`;
2021
- }
2022
- function generateAlterColumnSQL(table, column, changes) {
2023
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2024
- const tableNameWithSchema = `"${schema}"."${tableName}"`;
2025
- const statements = [];
2026
- const changesTo = changes.to;
2027
- const changesFrom = changes.from;
2028
- const changesToType = changesTo?.type;
2029
- const changesFromType = changesFrom?.type;
2030
- if (changesToType !== changesFromType) {
2031
- const newType = changesToType || "TEXT";
2032
- const needsUsing = checkIfNeedsUsingClause(changesFromType || "", newType);
2033
- if (needsUsing) {
2034
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" TYPE ${newType} USING "${column}"::text::${newType};`);
2035
- } else {
2036
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DATA TYPE ${newType};`);
2037
- }
2038
- }
2039
- const changesToNotNull = changesTo?.notNull;
2040
- const changesFromNotNull = changesFrom?.notNull;
2041
- if (changesToNotNull !== changesFromNotNull) {
2042
- if (changesToNotNull) {
2043
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET NOT NULL;`);
2044
- } else {
2045
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP NOT NULL;`);
2046
- }
2047
- }
2048
- const changesToDefault = changesTo?.default;
2049
- const changesFromDefault = changesFrom?.default;
2050
- if (changesToDefault !== changesFromDefault) {
2051
- if (changesToDefault !== undefined) {
2052
- const defaultValue = formatDefaultValue(changesToDefault, changesToType || "");
2053
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DEFAULT ${defaultValue};`);
2054
- } else {
2055
- statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP DEFAULT;`);
2056
- }
2057
- }
2058
- return statements;
2059
- }
2060
- function checkIfNeedsUsingClause(fromType, toType) {
2061
- if (!fromType || !toType)
2062
- return false;
2063
- if (fromType.includes("enum") || toType.includes("enum")) {
2064
- return true;
2065
- }
2066
- const fromBase = fromType.split("(")[0].toLowerCase();
2067
- const toBase = toType.split("(")[0].toLowerCase();
2068
- if ((fromBase === "text" || fromBase === "varchar" || fromBase === "character varying") && (toBase === "jsonb" || toBase === "json")) {
2069
- return true;
2070
- }
2071
- const needsUsingPairs = [
2072
- ["integer", "boolean"],
2073
- ["boolean", "integer"],
2074
- ["text", "integer"],
2075
- ["text", "numeric"],
2076
- ["text", "boolean"],
2077
- ["text", "uuid"],
2078
- ["text", "jsonb"],
2079
- ["text", "json"],
2080
- ["varchar", "integer"],
2081
- ["varchar", "numeric"],
2082
- ["varchar", "boolean"],
2083
- ["varchar", "uuid"],
2084
- ["varchar", "jsonb"],
2085
- ["varchar", "json"],
2086
- ["character varying", "jsonb"],
2087
- ["character varying", "json"]
2088
- ];
2089
- for (const [from, to] of needsUsingPairs) {
2090
- if (fromBase === from && toBase === to || fromBase === to && toBase === from) {
2091
- return true;
2092
- }
2093
- }
2094
- return false;
2095
- }
2096
- function formatDefaultValue(value, type) {
2097
- if (value === null || value === "NULL") {
2098
- return "NULL";
2099
- }
2100
- if (type && (type.toLowerCase().includes("boolean") || type.toLowerCase() === "bool")) {
2101
- if (value === true || value === "true" || value === "t" || value === 1) {
2102
- return "true";
2103
- }
2104
- if (value === false || value === "false" || value === "f" || value === 0) {
2105
- return "false";
2106
- }
2107
- }
2108
- if (type?.match(/^(integer|bigint|smallint|numeric|decimal|real|double)/i)) {
2109
- return String(value);
2110
- }
2111
- if (typeof value === "string") {
2112
- if (value.includes("::")) {
2113
- return value;
2114
- }
2115
- if (value.startsWith("'") && value.endsWith("'")) {
2116
- return value;
2117
- }
2118
- if (value.match(/^\w+\(\)/i) || value.includes("(") && value.includes(")")) {
2119
- return value;
2120
- }
2121
- if (value.toUpperCase().startsWith("CURRENT_")) {
2122
- return value;
2123
- }
2124
- return `'${value.replace(/'/g, "''")}'`;
2125
- }
2126
- return String(value);
2127
- }
2128
- function generateCreateIndexSQL(index7) {
2129
- const unique3 = index7.isUnique ? "UNIQUE " : "";
2130
- const method = index7.method || "btree";
2131
- const columns = index7.columns.map((c) => {
2132
- if (c.isExpression) {
2133
- return c.expression;
2134
- }
2135
- return `"${c.expression}"${c.asc === false ? " DESC" : ""}`;
2136
- }).join(", ");
2137
- const indexName = index7.name.includes(".") ? index7.name.split(".")[1] : index7.name;
2138
- let tableRef;
2139
- const indexTable = index7.table;
2140
- if (indexTable?.includes(".")) {
2141
- const [schema, table] = indexTable.split(".");
2142
- tableRef = `"${schema}"."${table}"`;
2143
- } else {
2144
- tableRef = `"${indexTable || ""}"`;
2145
- }
2146
- return `CREATE ${unique3}INDEX "${indexName}" ON ${tableRef} USING ${method} (${columns});`;
2147
- }
2148
- function generateDropIndexSQL(index7) {
2149
- const indexNameFull = typeof index7 === "string" ? index7 : index7.name;
2150
- const indexName = indexNameFull.includes(".") ? indexNameFull.split(".")[1] : indexNameFull;
2151
- return `DROP INDEX IF EXISTS "${indexName}";`;
2152
- }
2153
- function generateCreateForeignKeySQL(fk) {
2154
- const schemaFrom = fk.schemaFrom || "public";
2155
- const schemaTo = fk.schemaTo || "public";
2156
- const tableFrom = fk.tableFrom;
2157
- const columnsFrom = fk.columnsFrom.map((c) => `"${c}"`).join(", ");
2158
- const columnsTo = fk.columnsTo.map((c) => `"${c}"`).join(", ");
2159
- let sql21 = `ALTER TABLE "${schemaFrom}"."${tableFrom}" ADD CONSTRAINT "${fk.name}" FOREIGN KEY (${columnsFrom}) REFERENCES "${schemaTo}"."${fk.tableTo}" (${columnsTo})`;
2160
- if (fk.onDelete) {
2161
- sql21 += ` ON DELETE ${fk.onDelete}`;
2162
- }
2163
- if (fk.onUpdate) {
2164
- sql21 += ` ON UPDATE ${fk.onUpdate}`;
2165
- }
2166
- return `${sql21};`;
2167
- }
2168
- function generateDropForeignKeySQL(fk) {
2169
- const [schema, tableName] = fk.tableFrom ? fk.tableFrom.includes(".") ? fk.tableFrom.split(".") : ["public", fk.tableFrom] : ["public", ""];
2170
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${fk.name}";`;
2171
- }
2172
- function generateCreateUniqueConstraintSQL(constraint) {
2173
- const table = constraint.table || "";
2174
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2175
- const name = constraint.name;
2176
- const columns = constraint.columns.map((c) => `"${c}"`).join(", ");
2177
- let sql21 = `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" UNIQUE`;
2178
- if (constraint.nullsNotDistinct) {
2179
- sql21 += ` NULLS NOT DISTINCT`;
2180
- }
2181
- sql21 += ` (${columns});`;
2182
- return sql21;
2183
- }
2184
- function generateDropUniqueConstraintSQL(constraint) {
2185
- const table = constraint.table || "";
2186
- const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2187
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2356
+ if (definition.notNull) {
2357
+ parts.push("NOT NULL");
2358
+ }
2359
+ return `ALTER TABLE ${tableNameWithSchema} ADD COLUMN ${parts.join(" ")};`;
2188
2360
  }
2189
- function generateCreateCheckConstraintSQL(constraint) {
2190
- const table = constraint.table || "";
2361
+ function generateDropColumnSQL(table, column) {
2191
2362
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2192
- const name = constraint.name;
2193
- const value = constraint.value;
2194
- return `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" CHECK (${value});`;
2363
+ const tableNameWithSchema = `"${schema}"."${tableName}"`;
2364
+ return `ALTER TABLE ${tableNameWithSchema} DROP COLUMN "${column}" CASCADE;`;
2195
2365
  }
2196
- function generateDropCheckConstraintSQL(constraint) {
2197
- const table = constraint.table || "";
2366
+ function generateAlterColumnSQL(table, column, changes) {
2198
2367
  const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2199
- return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2200
- }
2201
- var import_core4;
2202
- var init_sql_generator = __esm(() => {
2203
- import_core4 = require("@elizaos/core");
2204
- });
2205
-
2206
- // runtime-migrator/drizzle-adapters/database-introspector.ts
2207
- function getRows2(result) {
2208
- return result.rows;
2209
- }
2210
-
2211
- class DatabaseIntrospector {
2212
- db;
2213
- constructor(db) {
2214
- this.db = db;
2215
- }
2216
- async introspectSchema(schemaName = "public") {
2217
- import_core5.logger.info({ src: "plugin:sql", schemaName }, "Starting database introspection");
2218
- const tables = {};
2219
- const schemas = {};
2220
- const enums = {};
2221
- const allTables = await this.getTables(schemaName);
2222
- for (const tableInfo of allTables) {
2223
- const tableName = tableInfo.table_name;
2224
- const tableSchema = tableInfo.table_schema || "public";
2225
- import_core5.logger.debug({ src: "plugin:sql", tableSchema, tableName }, "Introspecting table");
2226
- const columns = await this.getColumns(tableSchema, tableName);
2227
- const columnsObject = {};
2228
- const uniqueConstraintObject = {};
2229
- for (const col of columns) {
2230
- columnsObject[col.column_name] = {
2231
- name: col.column_name,
2232
- type: col.data_type,
2233
- primaryKey: col.is_primary || false,
2234
- notNull: col.is_nullable === "NO",
2235
- default: col.column_default ? this.parseDefault(col.column_default, col.data_type) : undefined
2236
- };
2237
- }
2238
- const indexes = await this.getIndexes(tableSchema, tableName);
2239
- const indexesObject = {};
2240
- for (const idx of indexes) {
2241
- if (!idx.is_primary && !idx.is_unique_constraint) {
2242
- if (idx.columns && Array.isArray(idx.columns) && idx.columns.length > 0) {
2243
- indexesObject[idx.name] = {
2244
- name: idx.name,
2245
- columns: idx.columns.map((col) => ({
2246
- expression: col,
2247
- isExpression: false
2248
- })),
2249
- isUnique: idx.is_unique,
2250
- method: idx.method || "btree"
2251
- };
2252
- }
2253
- }
2254
- }
2255
- const foreignKeys = await this.getForeignKeys(tableSchema, tableName);
2256
- const foreignKeysObject = {};
2257
- for (const fk of foreignKeys) {
2258
- foreignKeysObject[fk.name] = {
2259
- name: fk.name,
2260
- tableFrom: tableName,
2261
- schemaFrom: tableSchema,
2262
- tableTo: fk.foreign_table_name,
2263
- schemaTo: fk.foreign_table_schema || "public",
2264
- columnsFrom: [fk.column_name],
2265
- columnsTo: [fk.foreign_column_name],
2266
- onDelete: fk.delete_rule?.toLowerCase() || "no action",
2267
- onUpdate: fk.update_rule?.toLowerCase() || "no action"
2268
- };
2269
- }
2270
- const primaryKeys = await this.getPrimaryKeys(tableSchema, tableName);
2271
- const primaryKeysObject = {};
2272
- for (const pk of primaryKeys) {
2273
- primaryKeysObject[pk.name] = {
2274
- name: pk.name,
2275
- columns: pk.columns
2276
- };
2277
- }
2278
- const uniqueConstraints = await this.getUniqueConstraints(tableSchema, tableName);
2279
- for (const unq of uniqueConstraints) {
2280
- uniqueConstraintObject[unq.name] = {
2281
- name: unq.name,
2282
- columns: unq.columns,
2283
- nullsNotDistinct: false
2284
- };
2285
- }
2286
- const checkConstraints = await this.getCheckConstraints(tableSchema, tableName);
2287
- const checksObject = {};
2288
- for (const check3 of checkConstraints) {
2289
- checksObject[check3.name] = {
2290
- name: check3.name,
2291
- value: check3.definition
2292
- };
2293
- }
2294
- tables[`${tableSchema}.${tableName}`] = {
2295
- name: tableName,
2296
- schema: tableSchema,
2297
- columns: columnsObject,
2298
- indexes: indexesObject,
2299
- foreignKeys: foreignKeysObject,
2300
- compositePrimaryKeys: primaryKeysObject,
2301
- uniqueConstraints: uniqueConstraintObject,
2302
- checkConstraints: checksObject
2303
- };
2304
- if (tableSchema && tableSchema !== "public") {
2305
- schemas[tableSchema] = tableSchema;
2306
- }
2307
- }
2308
- const enumsResult = await this.getEnums(schemaName);
2309
- for (const enumInfo of enumsResult) {
2310
- const key = `${enumInfo.schema}.${enumInfo.name}`;
2311
- if (!enums[key]) {
2312
- enums[key] = {
2313
- name: enumInfo.name,
2314
- schema: enumInfo.schema,
2315
- values: []
2316
- };
2317
- }
2318
- enums[key].values.push(enumInfo.value);
2368
+ const tableNameWithSchema = `"${schema}"."${tableName}"`;
2369
+ const statements = [];
2370
+ const changesTo = changes.to;
2371
+ const changesFrom = changes.from;
2372
+ const changesToType = changesTo?.type;
2373
+ const changesFromType = changesFrom?.type;
2374
+ if (changesToType !== changesFromType) {
2375
+ const newType = changesToType || "TEXT";
2376
+ const needsUsing = checkIfNeedsUsingClause(changesFromType || "", newType);
2377
+ if (needsUsing) {
2378
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" TYPE ${newType} USING "${column}"::text::${newType};`);
2379
+ } else {
2380
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DATA TYPE ${newType};`);
2319
2381
  }
2320
- import_core5.logger.info({ src: "plugin:sql", tableCount: Object.keys(tables).length }, "Database introspection complete");
2321
- return {
2322
- version: "7",
2323
- dialect: "postgresql",
2324
- tables,
2325
- schemas,
2326
- enums,
2327
- _meta: {
2328
- schemas: {},
2329
- tables: {},
2330
- columns: {}
2331
- }
2332
- };
2333
2382
  }
2334
- async getTables(schemaName) {
2335
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2336
- table_schema,
2337
- table_name
2338
- FROM information_schema.tables
2339
- WHERE table_schema = ${schemaName}
2340
- AND table_type = 'BASE TABLE'
2341
- ORDER BY table_name`);
2342
- return getRows2(result);
2383
+ const changesToNotNull = changesTo?.notNull;
2384
+ const changesFromNotNull = changesFrom?.notNull;
2385
+ if (changesToNotNull !== changesFromNotNull) {
2386
+ if (changesToNotNull) {
2387
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET NOT NULL;`);
2388
+ } else {
2389
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP NOT NULL;`);
2390
+ }
2343
2391
  }
2344
- async getColumns(schemaName, tableName) {
2345
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2346
- a.attname AS column_name,
2347
- CASE
2348
- WHEN a.attnotnull THEN 'NO'
2349
- ELSE 'YES'
2350
- END AS is_nullable,
2351
- CASE
2352
- WHEN a.atttypid = ANY ('{int,int8,int2}'::regtype[])
2353
- AND EXISTS (
2354
- SELECT FROM pg_attrdef ad
2355
- WHERE ad.adrelid = a.attrelid
2356
- AND ad.adnum = a.attnum
2357
- AND pg_get_expr(ad.adbin, ad.adrelid) = 'nextval('''
2358
- || pg_get_serial_sequence(a.attrelid::regclass::text, a.attname)::regclass || '''::regclass)'
2359
- )
2360
- THEN CASE a.atttypid
2361
- WHEN 'int'::regtype THEN 'serial'
2362
- WHEN 'int8'::regtype THEN 'bigserial'
2363
- WHEN 'int2'::regtype THEN 'smallserial'
2364
- END
2365
- ELSE format_type(a.atttypid, a.atttypmod)
2366
- END AS data_type,
2367
- pg_get_expr(ad.adbin, ad.adrelid) AS column_default,
2368
- CASE
2369
- WHEN con.contype = 'p' THEN true
2370
- ELSE false
2371
- END AS is_primary
2372
- FROM pg_attribute a
2373
- JOIN pg_class cls ON cls.oid = a.attrelid
2374
- JOIN pg_namespace ns ON ns.oid = cls.relnamespace
2375
- LEFT JOIN pg_attrdef ad ON ad.adrelid = a.attrelid AND ad.adnum = a.attnum
2376
- LEFT JOIN pg_constraint con ON con.conrelid = a.attrelid
2377
- AND a.attnum = ANY(con.conkey)
2378
- AND con.contype = 'p'
2379
- WHERE
2380
- a.attnum > 0
2381
- AND NOT a.attisdropped
2382
- AND ns.nspname = ${schemaName}
2383
- AND cls.relname = ${tableName}
2384
- ORDER BY a.attnum`);
2385
- return getRows2(result);
2392
+ const changesToDefault = changesTo?.default;
2393
+ const changesFromDefault = changesFrom?.default;
2394
+ if (changesToDefault !== changesFromDefault) {
2395
+ if (changesToDefault !== undefined) {
2396
+ const defaultValue = formatDefaultValue(changesToDefault, changesToType || "");
2397
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" SET DEFAULT ${defaultValue};`);
2398
+ } else {
2399
+ statements.push(`ALTER TABLE ${tableNameWithSchema} ALTER COLUMN "${column}" DROP DEFAULT;`);
2400
+ }
2386
2401
  }
2387
- async getIndexes(schemaName, tableName) {
2388
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2389
- i.relname AS name,
2390
- idx.indisunique AS is_unique,
2391
- idx.indisprimary AS is_primary,
2392
- con.contype = 'u' AS is_unique_constraint,
2393
- ARRAY(
2394
- SELECT a.attname
2395
- FROM pg_attribute a
2396
- WHERE a.attrelid = idx.indrelid
2397
- AND a.attnum = ANY(idx.indkey::int[])
2398
- ORDER BY a.attnum
2399
- ) AS columns,
2400
- am.amname AS method
2401
- FROM pg_index idx
2402
- JOIN pg_class i ON i.oid = idx.indexrelid
2403
- JOIN pg_class c ON c.oid = idx.indrelid
2404
- JOIN pg_namespace n ON n.oid = c.relnamespace
2405
- JOIN pg_am am ON am.oid = i.relam
2406
- LEFT JOIN pg_constraint con ON con.conindid = idx.indexrelid
2407
- WHERE n.nspname = ${schemaName}
2408
- AND c.relname = ${tableName}`);
2409
- return getRows2(result);
2402
+ return statements;
2403
+ }
2404
+ function checkIfNeedsUsingClause(fromType, toType) {
2405
+ if (!fromType || !toType)
2406
+ return false;
2407
+ if (fromType.includes("enum") || toType.includes("enum")) {
2408
+ return true;
2410
2409
  }
2411
- async getForeignKeys(schemaName, tableName) {
2412
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2413
- con.conname AS name,
2414
- att.attname AS column_name,
2415
- fnsp.nspname AS foreign_table_schema,
2416
- frel.relname AS foreign_table_name,
2417
- fatt.attname AS foreign_column_name,
2418
- CASE con.confupdtype
2419
- WHEN 'a' THEN 'NO ACTION'
2420
- WHEN 'r' THEN 'RESTRICT'
2421
- WHEN 'n' THEN 'SET NULL'
2422
- WHEN 'c' THEN 'CASCADE'
2423
- WHEN 'd' THEN 'SET DEFAULT'
2424
- END AS update_rule,
2425
- CASE con.confdeltype
2426
- WHEN 'a' THEN 'NO ACTION'
2427
- WHEN 'r' THEN 'RESTRICT'
2428
- WHEN 'n' THEN 'SET NULL'
2429
- WHEN 'c' THEN 'CASCADE'
2430
- WHEN 'd' THEN 'SET DEFAULT'
2431
- END AS delete_rule
2432
- FROM pg_catalog.pg_constraint con
2433
- JOIN pg_catalog.pg_class rel ON rel.oid = con.conrelid
2434
- JOIN pg_catalog.pg_namespace nsp ON nsp.oid = con.connamespace
2435
- LEFT JOIN pg_catalog.pg_attribute att ON att.attnum = ANY (con.conkey)
2436
- AND att.attrelid = con.conrelid
2437
- LEFT JOIN pg_catalog.pg_class frel ON frel.oid = con.confrelid
2438
- LEFT JOIN pg_catalog.pg_namespace fnsp ON fnsp.oid = frel.relnamespace
2439
- LEFT JOIN pg_catalog.pg_attribute fatt ON fatt.attnum = ANY (con.confkey)
2440
- AND fatt.attrelid = con.confrelid
2441
- WHERE con.contype = 'f'
2442
- AND nsp.nspname = ${schemaName}
2443
- AND rel.relname = ${tableName}`);
2444
- return getRows2(result);
2410
+ const fromBase = fromType.split("(")[0].toLowerCase();
2411
+ const toBase = toType.split("(")[0].toLowerCase();
2412
+ if ((fromBase === "text" || fromBase === "varchar" || fromBase === "character varying") && (toBase === "jsonb" || toBase === "json")) {
2413
+ return true;
2445
2414
  }
2446
- async getPrimaryKeys(schemaName, tableName) {
2447
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2448
- con.conname AS name,
2449
- ARRAY(
2450
- SELECT a.attname
2451
- FROM pg_attribute a
2452
- WHERE a.attrelid = con.conrelid
2453
- AND a.attnum = ANY(con.conkey)
2454
- ORDER BY a.attnum
2455
- ) AS columns
2456
- FROM pg_constraint con
2457
- JOIN pg_class rel ON rel.oid = con.conrelid
2458
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2459
- WHERE con.contype = 'p'
2460
- AND nsp.nspname = ${schemaName}
2461
- AND rel.relname = ${tableName}`);
2462
- return getRows2(result);
2415
+ const needsUsingPairs = [
2416
+ ["integer", "boolean"],
2417
+ ["boolean", "integer"],
2418
+ ["text", "integer"],
2419
+ ["text", "numeric"],
2420
+ ["text", "boolean"],
2421
+ ["text", "uuid"],
2422
+ ["text", "jsonb"],
2423
+ ["text", "json"],
2424
+ ["varchar", "integer"],
2425
+ ["varchar", "numeric"],
2426
+ ["varchar", "boolean"],
2427
+ ["varchar", "uuid"],
2428
+ ["varchar", "jsonb"],
2429
+ ["varchar", "json"],
2430
+ ["character varying", "jsonb"],
2431
+ ["character varying", "json"]
2432
+ ];
2433
+ for (const [from, to] of needsUsingPairs) {
2434
+ if (fromBase === from && toBase === to || fromBase === to && toBase === from) {
2435
+ return true;
2436
+ }
2463
2437
  }
2464
- async getUniqueConstraints(schemaName, tableName) {
2465
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2466
- con.conname AS name,
2467
- ARRAY(
2468
- SELECT a.attname
2469
- FROM pg_attribute a
2470
- WHERE a.attrelid = con.conrelid
2471
- AND a.attnum = ANY(con.conkey)
2472
- ORDER BY a.attnum
2473
- ) AS columns
2474
- FROM pg_constraint con
2475
- JOIN pg_class rel ON rel.oid = con.conrelid
2476
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2477
- WHERE con.contype = 'u'
2478
- AND nsp.nspname = ${schemaName}
2479
- AND rel.relname = ${tableName}`);
2480
- return getRows2(result);
2438
+ return false;
2439
+ }
2440
+ function formatDefaultValue(value, type) {
2441
+ if (value === null || value === "NULL") {
2442
+ return "NULL";
2481
2443
  }
2482
- async getCheckConstraints(schemaName, tableName) {
2483
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2484
- con.conname AS name,
2485
- pg_get_constraintdef(con.oid) AS definition
2486
- FROM pg_constraint con
2487
- JOIN pg_class rel ON rel.oid = con.conrelid
2488
- JOIN pg_namespace nsp ON nsp.oid = con.connamespace
2489
- WHERE con.contype = 'c'
2490
- AND nsp.nspname = ${schemaName}
2491
- AND rel.relname = ${tableName}`);
2492
- return getRows2(result);
2444
+ if (type && (type.toLowerCase().includes("boolean") || type.toLowerCase() === "bool")) {
2445
+ if (value === true || value === "true" || value === "t" || value === 1) {
2446
+ return "true";
2447
+ }
2448
+ if (value === false || value === "false" || value === "f" || value === 0) {
2449
+ return "false";
2450
+ }
2493
2451
  }
2494
- async getEnums(schemaName) {
2495
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT
2496
- n.nspname AS schema,
2497
- t.typname AS name,
2498
- e.enumlabel AS value,
2499
- e.enumsortorder AS sort_order
2500
- FROM pg_type t
2501
- JOIN pg_enum e ON t.oid = e.enumtypid
2502
- JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
2503
- WHERE n.nspname = ${schemaName}
2504
- ORDER BY schema, name, sort_order`);
2505
- return getRows2(result);
2452
+ if (type?.match(/^(integer|bigint|smallint|numeric|decimal|real|double)/i)) {
2453
+ return String(value);
2506
2454
  }
2507
- parseDefault(defaultValue, dataType) {
2508
- if (!defaultValue)
2509
- return;
2510
- const match = defaultValue.match(/^'(.*)'::/);
2511
- if (match) {
2512
- return `'${match[1]}'`;
2455
+ if (typeof value === "string") {
2456
+ if (value.includes("::")) {
2457
+ return value;
2513
2458
  }
2514
- if (defaultValue.includes("nextval(")) {
2515
- return;
2459
+ if (value.startsWith("'") && value.endsWith("'")) {
2460
+ return value;
2516
2461
  }
2517
- if (dataType === "boolean") {
2518
- if (defaultValue === "true")
2519
- return "true";
2520
- if (defaultValue === "false")
2521
- return "false";
2462
+ if (value.match(/^\w+\(\)/i) || value.includes("(") && value.includes(")")) {
2463
+ return value;
2522
2464
  }
2523
- return defaultValue;
2465
+ if (value.toUpperCase().startsWith("CURRENT_")) {
2466
+ return value;
2467
+ }
2468
+ return `'${value.replace(/'/g, "''")}'`;
2524
2469
  }
2525
- async hasExistingTables(pluginName) {
2526
- const schemaName = pluginName === "@elizaos/plugin-sql" ? "public" : this.deriveSchemaName(pluginName);
2527
- const result = await this.db.execute(import_drizzle_orm22.sql`SELECT COUNT(*) AS count
2528
- FROM information_schema.tables
2529
- WHERE table_schema = ${schemaName}
2530
- AND table_type = 'BASE TABLE'`);
2531
- const firstRow = result.rows?.[0];
2532
- const count = parseInt(firstRow && firstRow.count || "0", 10);
2533
- return count > 0;
2470
+ return String(value);
2471
+ }
2472
+ function generateCreateIndexSQL(index7) {
2473
+ const unique3 = index7.isUnique ? "UNIQUE " : "";
2474
+ const method = index7.method || "btree";
2475
+ const columns = index7.columns.map((c) => {
2476
+ if (c.isExpression) {
2477
+ return c.expression;
2478
+ }
2479
+ return `"${c.expression}"${c.asc === false ? " DESC" : ""}`;
2480
+ }).join(", ");
2481
+ const indexName = index7.name.includes(".") ? index7.name.split(".")[1] : index7.name;
2482
+ let tableRef;
2483
+ const indexTable = index7.table;
2484
+ if (indexTable?.includes(".")) {
2485
+ const [schema, table] = indexTable.split(".");
2486
+ tableRef = `"${schema}"."${table}"`;
2487
+ } else {
2488
+ tableRef = `"${indexTable || ""}"`;
2534
2489
  }
2535
- deriveSchemaName(pluginName) {
2536
- return pluginName.replace("@", "").replace("/", "_").replace(/-/g, "_").toLowerCase();
2490
+ return `CREATE ${unique3}INDEX "${indexName}" ON ${tableRef} USING ${method} (${columns});`;
2491
+ }
2492
+ function generateDropIndexSQL(index7) {
2493
+ const indexNameFull = typeof index7 === "string" ? index7 : index7.name;
2494
+ const indexName = indexNameFull.includes(".") ? indexNameFull.split(".")[1] : indexNameFull;
2495
+ return `DROP INDEX IF EXISTS "${indexName}";`;
2496
+ }
2497
+ function generateCreateForeignKeySQL(fk) {
2498
+ return wrapConstraintCreationGuard(fk.name, buildCreateForeignKeyBodySQL(fk));
2499
+ }
2500
+ function generateDropForeignKeySQL(fk) {
2501
+ const [schema, tableName] = fk.tableFrom ? fk.tableFrom.includes(".") ? fk.tableFrom.split(".") : ["public", fk.tableFrom] : ["public", ""];
2502
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${fk.name}";`;
2503
+ }
2504
+ function generateCreateUniqueConstraintSQL(constraint) {
2505
+ const table = constraint.table || "";
2506
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2507
+ const name = constraint.name;
2508
+ const columns = constraint.columns.map((c) => `"${c}"`).join(", ");
2509
+ let sql22 = `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" UNIQUE`;
2510
+ if (constraint.nullsNotDistinct) {
2511
+ sql22 += ` NULLS NOT DISTINCT`;
2537
2512
  }
2513
+ sql22 += ` (${columns});`;
2514
+ return sql22;
2538
2515
  }
2539
- var import_core5, import_drizzle_orm22;
2540
- var init_database_introspector = __esm(() => {
2516
+ function generateDropUniqueConstraintSQL(constraint) {
2517
+ const table = constraint.table || "";
2518
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2519
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2520
+ }
2521
+ function generateCreateCheckConstraintSQL(constraint) {
2522
+ const table = constraint.table || "";
2523
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2524
+ const name = constraint.name;
2525
+ const value = constraint.value;
2526
+ return `ALTER TABLE "${schema}"."${tableName}" ADD CONSTRAINT "${name}" CHECK (${value});`;
2527
+ }
2528
+ function generateDropCheckConstraintSQL(constraint) {
2529
+ const table = constraint.table || "";
2530
+ const [schema, tableName] = table.includes(".") ? table.split(".") : ["public", table];
2531
+ return `ALTER TABLE "${schema}"."${tableName}" DROP CONSTRAINT "${constraint.name}";`;
2532
+ }
2533
+ function buildCreateForeignKeyBodySQL(fk) {
2534
+ const schemaFrom = fk.schemaFrom || "public";
2535
+ const schemaTo = fk.schemaTo || "public";
2536
+ const tableFrom = fk.tableFrom;
2537
+ const columnsFrom = fk.columnsFrom.map((c) => `"${c}"`).join(", ");
2538
+ const columnsTo = fk.columnsTo.map((c) => `"${c}"`).join(", ");
2539
+ let sql22 = `ALTER TABLE "${schemaFrom}"."${tableFrom}" ADD CONSTRAINT "${fk.name}" FOREIGN KEY (${columnsFrom}) REFERENCES "${schemaTo}"."${fk.tableTo}" (${columnsTo})`;
2540
+ if (fk.onDelete) {
2541
+ sql22 += ` ON DELETE ${fk.onDelete}`;
2542
+ }
2543
+ if (fk.onUpdate) {
2544
+ sql22 += ` ON UPDATE ${fk.onUpdate}`;
2545
+ }
2546
+ return sql22;
2547
+ }
2548
+ function wrapConstraintCreationGuard(constraintName, statement) {
2549
+ const escapedConstraintName = constraintName.replace(/'/g, "''");
2550
+ return `DO $$ BEGIN IF NOT EXISTS (SELECT 1 FROM pg_constraint WHERE conname = '${escapedConstraintName}') THEN ${statement}; END IF; END $$;`;
2551
+ }
2552
+ var import_core5;
2553
+ var init_sql_generator = __esm(() => {
2541
2554
  import_core5 = require("@elizaos/core");
2542
- import_drizzle_orm22 = require("drizzle-orm");
2543
2555
  });
2544
2556
 
2545
2557
  // runtime-migrator/extension-manager.ts
@@ -3222,14 +3234,10 @@ var init_runtime_migrator = __esm(() => {
3222
3234
  import_core8 = require("@elizaos/core");
3223
3235
  import_drizzle_orm27 = require("drizzle-orm");
3224
3236
  });
3237
+
3225
3238
  // runtime-migrator/index.ts
3226
3239
  var init_runtime_migrator2 = __esm(() => {
3227
- init_snapshot_generator();
3228
- init_sql_generator();
3229
3240
  init_runtime_migrator();
3230
- init_journal_storage();
3231
- init_migration_tracker();
3232
- init_snapshot_storage();
3233
3241
  });
3234
3242
 
3235
3243
  // migration-service.ts
@@ -3822,7 +3830,7 @@ class BaseDrizzleAdapter extends import_core10.DatabaseAdapter {
3822
3830
  return [String(names)];
3823
3831
  }
3824
3832
  isValidUUID(value) {
3825
- 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);
3833
+ return /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(value);
3826
3834
  }
3827
3835
  normalizeWorldData(world) {
3828
3836
  const worldData = {
@@ -5209,11 +5217,14 @@ class BaseDrizzleAdapter extends import_core10.DatabaseAdapter {
5209
5217
  async addParticipant(entityId, roomId) {
5210
5218
  return this.withDatabase(async () => {
5211
5219
  try {
5212
- await this.db.insert(participantTable).values({
5213
- entityId,
5214
- roomId,
5215
- agentId: this.agentId
5216
- }).onConflictDoNothing();
5220
+ const existing = await this.db.select({ id: participantTable.id }).from(participantTable).where(import_drizzle_orm28.and(import_drizzle_orm28.eq(participantTable.entityId, entityId), import_drizzle_orm28.eq(participantTable.roomId, roomId), import_drizzle_orm28.eq(participantTable.agentId, this.agentId))).limit(1);
5221
+ if (existing.length === 0) {
5222
+ await this.db.insert(participantTable).values({
5223
+ entityId,
5224
+ roomId,
5225
+ agentId: this.agentId
5226
+ });
5227
+ }
5217
5228
  return true;
5218
5229
  } catch (error) {
5219
5230
  import_core10.logger.error({
@@ -5230,12 +5241,16 @@ class BaseDrizzleAdapter extends import_core10.DatabaseAdapter {
5230
5241
  async addParticipantsRoom(entityIds, roomId) {
5231
5242
  return this.withDatabase(async () => {
5232
5243
  try {
5233
- const values = entityIds.map((id) => ({
5234
- entityId: id,
5235
- roomId,
5236
- agentId: this.agentId
5237
- }));
5238
- await this.db.insert(participantTable).values(values).onConflictDoNothing().execute();
5244
+ for (const id of entityIds) {
5245
+ const existing = await this.db.select({ id: participantTable.id }).from(participantTable).where(import_drizzle_orm28.and(import_drizzle_orm28.eq(participantTable.entityId, id), import_drizzle_orm28.eq(participantTable.roomId, roomId), import_drizzle_orm28.eq(participantTable.agentId, this.agentId))).limit(1);
5246
+ if (existing.length === 0) {
5247
+ await this.db.insert(participantTable).values({
5248
+ entityId: id,
5249
+ roomId,
5250
+ agentId: this.agentId
5251
+ });
5252
+ }
5253
+ }
5239
5254
  return true;
5240
5255
  } catch (error) {
5241
5256
  import_core10.logger.error({
@@ -5385,19 +5400,27 @@ class BaseDrizzleAdapter extends import_core10.DatabaseAdapter {
5385
5400
  }
5386
5401
  async getRelationships(params) {
5387
5402
  return this.withDatabase(async () => {
5388
- const { entityId, tags } = params;
5389
- let query;
5403
+ const { entityIds: rawEntityIds, entityId, tags, limit, offset } = params;
5404
+ const entityIds = (rawEntityIds && rawEntityIds.length > 0 ? rawEntityIds : entityId ? [entityId] : []).filter((id) => typeof id === "string" && id.trim().length > 0);
5405
+ if (entityIds.length === 0) {
5406
+ return [];
5407
+ }
5408
+ const entityFilter = import_drizzle_orm28.sql.join(entityIds.map((id) => import_drizzle_orm28.sql`(${relationshipTable.sourceEntityId} = ${id} OR ${relationshipTable.targetEntityId} = ${id})`), import_drizzle_orm28.sql` OR `);
5409
+ let query = import_drizzle_orm28.sql`
5410
+ SELECT * FROM ${relationshipTable}
5411
+ WHERE (${entityFilter})
5412
+ `;
5390
5413
  if (tags && tags.length > 0) {
5391
5414
  query = import_drizzle_orm28.sql`
5392
- SELECT * FROM ${relationshipTable}
5393
- WHERE (${relationshipTable.sourceEntityId} = ${entityId} OR ${relationshipTable.targetEntityId} = ${entityId})
5415
+ ${query}
5394
5416
  AND ${relationshipTable.tags} && CAST(ARRAY[${import_drizzle_orm28.sql.join(tags, import_drizzle_orm28.sql`, `)}] AS text[])
5395
5417
  `;
5396
- } else {
5397
- query = import_drizzle_orm28.sql`
5398
- SELECT * FROM ${relationshipTable}
5399
- WHERE ${relationshipTable.sourceEntityId} = ${entityId} OR ${relationshipTable.targetEntityId} = ${entityId}
5400
- `;
5418
+ }
5419
+ if (typeof limit === "number") {
5420
+ query = import_drizzle_orm28.sql`${query} LIMIT ${limit}`;
5421
+ }
5422
+ if (typeof offset === "number" && offset > 0) {
5423
+ query = import_drizzle_orm28.sql`${query} OFFSET ${offset}`;
5401
5424
  }
5402
5425
  const result = await this.db.execute(query);
5403
5426
  return result.rows.map((relationship) => ({
@@ -7122,5 +7145,5 @@ var plugin = {
7122
7145
  };
7123
7146
  var typescript_default = plugin;
7124
7147
 
7125
- //# debugId=13D17A8DF9243CD764756E2164756E21
7148
+ //# debugId=B2FA58A515BC4FB464756E2164756E21
7126
7149
  //# sourceMappingURL=index.node.cjs.map