@dbcube/core 5.1.15 → 5.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -392,7 +392,7 @@ var Downloader = class {
392
392
  }
393
393
  this.mainSpinner.text = import_chalk.default.blue(`Updating ${binariesToDownload.length} binary(ies)...`);
394
394
  try {
395
- await Promise.all(binariesToDownload.map(async (binary) => {
395
+ const results = await Promise.allSettled(binariesToDownload.map(async (binary) => {
396
396
  const maxRetries = 3;
397
397
  let attempt = 0;
398
398
  while (attempt <= maxRetries) {
@@ -420,6 +420,11 @@ var Downloader = class {
420
420
  }
421
421
  }
422
422
  }));
423
+ const failures = results.filter((r) => r.status === "rejected");
424
+ if (failures.length > 0) {
425
+ const messages = failures.map((f) => f.reason instanceof Error ? f.reason.message : String(f.reason));
426
+ throw new Error(messages.join(" | "));
427
+ }
423
428
  this.mainSpinner.succeed(import_chalk.default.green("Binaries updated successfully"));
424
429
  } catch (error) {
425
430
  const errorMessage = error instanceof Error ? error.message : "Unknown error";
@@ -484,8 +489,7 @@ var Downloader = class {
484
489
  }
485
490
  });
486
491
  response.on("end", () => {
487
- file.end();
488
- resolve5();
492
+ file.end(() => resolve5());
489
493
  });
490
494
  response.on("error", (err) => {
491
495
  file.close();
@@ -712,7 +716,6 @@ var Config = class {
712
716
  /**
713
717
  * Obtiene un valor de configuración
714
718
  * @param key - Clave de configuración
715
- * @returns Valor de configuración
716
719
  */
717
720
  get(key) {
718
721
  return this.data[key];
@@ -720,14 +723,12 @@ var Config = class {
720
723
  /**
721
724
  * Obtiene la configuración de una base de datos específica
722
725
  * @param dbName - Nombre de la base de datos
723
- * @returns Configuración de la base de datos o null
724
726
  */
725
727
  getDatabase(dbName) {
726
728
  return this.databases[dbName] || null;
727
729
  }
728
730
  /**
729
731
  * Obtiene todas las bases de datos configuradas
730
- * @returns Todas las configuraciones de bases de datos
731
732
  */
732
733
  getAllDatabases() {
733
734
  return this.databases;
@@ -775,6 +776,39 @@ var DaemonClient = class _DaemonClient {
775
776
  portfilePath() {
776
777
  return import_path3.default.join(process.cwd(), ".dbcube", "daemon", `${this.name}.json`);
777
778
  }
779
+ lockfilePath() {
780
+ return import_path3.default.join(process.cwd(), ".dbcube", "daemon", `${this.name}.lock`);
781
+ }
782
+ /**
783
+ * Exclusive-create lock so two processes never spawn two daemons for the
784
+ * same database at once. Stale locks (crashed starter) expire after 15s.
785
+ */
786
+ acquireSpawnLock() {
787
+ const lockPath = this.lockfilePath();
788
+ try {
789
+ import_fs.default.mkdirSync(import_path3.default.dirname(lockPath), { recursive: true });
790
+ const fd = import_fs.default.openSync(lockPath, "wx");
791
+ import_fs.default.writeSync(fd, String(process.pid));
792
+ import_fs.default.closeSync(fd);
793
+ return true;
794
+ } catch {
795
+ try {
796
+ const age = Date.now() - import_fs.default.statSync(lockPath).mtimeMs;
797
+ if (age > 15e3) {
798
+ import_fs.default.unlinkSync(lockPath);
799
+ return this.acquireSpawnLock();
800
+ }
801
+ } catch {
802
+ }
803
+ return false;
804
+ }
805
+ }
806
+ releaseSpawnLock() {
807
+ try {
808
+ import_fs.default.unlinkSync(this.lockfilePath());
809
+ } catch {
810
+ }
811
+ }
778
812
  /**
779
813
  * Ensures a usable daemon connection. Returns false when the daemon
780
814
  * can't be used (old binary, startup failure) so callers fall back
@@ -791,24 +825,32 @@ var DaemonClient = class _DaemonClient {
791
825
  async connectOrStart() {
792
826
  const port = this.readPortfile();
793
827
  if (port && await this.tryConnect(port)) return true;
828
+ const gotLock = this.acquireSpawnLock();
794
829
  try {
795
- import_fs.default.unlinkSync(this.portfilePath());
796
- } catch {
797
- }
798
- this.spawnDaemon();
799
- const deadline = Date.now() + 1e4;
800
- while (Date.now() < deadline) {
801
- await new Promise((r) => setTimeout(r, 150));
802
- const newPort = this.readPortfile();
803
- if (newPort && await this.tryConnect(newPort)) return true;
830
+ if (gotLock) {
831
+ try {
832
+ import_fs.default.unlinkSync(this.portfilePath());
833
+ } catch {
834
+ }
835
+ this.spawnDaemon();
836
+ }
837
+ const deadline = Date.now() + 1e4;
838
+ while (Date.now() < deadline) {
839
+ await new Promise((r) => setTimeout(r, 150));
840
+ const newPort = this.readPortfile();
841
+ if (newPort && await this.tryConnect(newPort)) return true;
842
+ }
843
+ return false;
844
+ } finally {
845
+ if (gotLock) this.releaseSpawnLock();
804
846
  }
805
- return false;
806
847
  }
807
848
  readPortfile() {
808
849
  try {
809
850
  const raw = import_fs.default.readFileSync(this.portfilePath(), "utf8");
810
851
  const info = JSON.parse(raw);
811
- return typeof info.port === "number" ? info.port : null;
852
+ const port = info?.port;
853
+ return Number.isInteger(port) && port > 0 && port <= 65535 ? port : null;
812
854
  } catch {
813
855
  return null;
814
856
  }
@@ -827,7 +869,7 @@ var DaemonClient = class _DaemonClient {
827
869
  socket.setNoDelay(true);
828
870
  this.attach(socket);
829
871
  try {
830
- const pong = await this.send({ action: "ping" });
872
+ const pong = await this.send({ action: "ping" }, 2e3);
831
873
  resolve5(pong.status === 200);
832
874
  } catch {
833
875
  this.detach();
@@ -884,7 +926,7 @@ var DaemonClient = class _DaemonClient {
884
926
  * Sends a request to the daemon. Responses arrive in FIFO order on the
885
927
  * single socket, so pending requests resolve in send order.
886
928
  */
887
- send(payload) {
929
+ send(payload, timeoutMs) {
888
930
  return new Promise((resolve5, reject) => {
889
931
  if (!this.socket || this.socket.destroyed) {
890
932
  reject(new Error("Daemon not connected"));
@@ -894,7 +936,8 @@ var DaemonClient = class _DaemonClient {
894
936
  const i = this.pending.findIndex((p) => p.timer === timer);
895
937
  if (i !== -1) this.pending.splice(i, 1);
896
938
  reject(new Error("Daemon request timeout"));
897
- }, this.requestTimeout);
939
+ this.detach();
940
+ }, timeoutMs ?? this.requestTimeout);
898
941
  this.pending.push({ resolve: resolve5, reject, timer });
899
942
  this.socket.write(JSON.stringify(payload) + "\n");
900
943
  });
@@ -1051,14 +1094,16 @@ var Engine = class {
1051
1094
  "--host",
1052
1095
  this.config.config.HOST,
1053
1096
  "--port",
1054
- this.config.config.PORT,
1055
- "--user",
1056
- this.config.config.USER,
1057
- "--password",
1058
- this.config.config.PASSWORD,
1097
+ String(this.config.config.PORT),
1059
1098
  "--motor",
1060
1099
  this.config.type
1061
1100
  ];
1101
+ if (this.config.config.USER != null && this.config.config.USER !== "") {
1102
+ args.push("--user", this.config.config.USER);
1103
+ }
1104
+ if (this.config.config.PASSWORD != null && this.config.config.PASSWORD !== "") {
1105
+ args.push("--password", this.config.config.PASSWORD);
1106
+ }
1062
1107
  }
1063
1108
  return args;
1064
1109
  }
@@ -1116,13 +1161,15 @@ var Engine = class {
1116
1161
  resolve5(response);
1117
1162
  }
1118
1163
  };
1119
- child.stdout.on("data", (data) => {
1120
- stdoutBuffer += data.toString();
1121
- console.log(stdoutBuffer);
1122
- const match = stdoutBuffer.match(/PROCESS_RESPONSE:(\{.*\})/);
1123
- if (match) {
1164
+ const tryParseLines = (buffer) => {
1165
+ let idx;
1166
+ while ((idx = buffer.indexOf("\n")) !== -1) {
1167
+ const line = buffer.slice(0, idx);
1168
+ buffer = buffer.slice(idx + 1);
1169
+ const marker = line.indexOf("PROCESS_RESPONSE:");
1170
+ if (marker === -1) continue;
1124
1171
  try {
1125
- const response = JSON.parse(match[1]);
1172
+ const response = JSON.parse(line.slice(marker + "PROCESS_RESPONSE:".length));
1126
1173
  resolveOnce({
1127
1174
  status: response.status,
1128
1175
  message: response.message,
@@ -1136,27 +1183,19 @@ var Engine = class {
1136
1183
  });
1137
1184
  }
1138
1185
  }
1186
+ return buffer;
1187
+ };
1188
+ child.stdout.on("data", (data) => {
1189
+ const text = data.toString();
1190
+ const visible = text.split("\n").filter((l) => l.trim() && !l.includes("PROCESS_RESPONSE:")).join("\n");
1191
+ if (visible) console.log(visible);
1192
+ stdoutBuffer = tryParseLines(stdoutBuffer + text);
1139
1193
  });
1140
1194
  child.stderr.on("data", (data) => {
1141
- stderrBuffer += data.toString();
1142
- console.log(stderrBuffer);
1143
- const match = stderrBuffer.match(/PROCESS_RESPONSE:(\{.*\})/);
1144
- if (match) {
1145
- try {
1146
- const response = JSON.parse(match[1]);
1147
- resolveOnce({
1148
- status: response.status,
1149
- message: response.message,
1150
- data: response.data
1151
- });
1152
- } catch (error) {
1153
- resolveOnce({
1154
- status: 500,
1155
- message: "Failed to parse response JSON",
1156
- data: null
1157
- });
1158
- }
1159
- }
1195
+ const text = data.toString();
1196
+ const visible = text.split("\n").filter((l) => l.trim() && !l.includes("PROCESS_RESPONSE:")).join("\n");
1197
+ if (visible) console.log(visible);
1198
+ stderrBuffer = tryParseLines(stderrBuffer + text);
1160
1199
  });
1161
1200
  child.on("close", (code) => {
1162
1201
  clearTimeout(timeoutId);
@@ -1193,7 +1232,6 @@ var globalTcpConnections = /* @__PURE__ */ new Map();
1193
1232
  var connectionQueues = /* @__PURE__ */ new Map();
1194
1233
  var connectionProcessing = /* @__PURE__ */ new Map();
1195
1234
  var queryCache = /* @__PURE__ */ new Map();
1196
- var cacheSize = 0;
1197
1235
  var MAX_CACHE_SIZE = 500;
1198
1236
  var QueryEngine = class {
1199
1237
  name;
@@ -1207,7 +1245,7 @@ var QueryEngine = class {
1207
1245
  this.name = name;
1208
1246
  this.config = this.setConfig(name);
1209
1247
  this.arguments = this.setArguments();
1210
- this.timeout = timeout;
1248
+ this.timeout = this.config?.daemon?.requestTimeoutMs ?? timeout;
1211
1249
  this.connectionId = `${name}_query_engine_${this.config.type}_${this.config.config.DATABASE}_${this.config.config.HOST || "localhost"}`;
1212
1250
  this.tcpPort = this.generatePort();
1213
1251
  }
@@ -1262,17 +1300,30 @@ var QueryEngine = class {
1262
1300
  "--host",
1263
1301
  this.config.config.HOST,
1264
1302
  "--port",
1265
- this.config.config.PORT,
1266
- "--user",
1267
- this.config.config.USER,
1268
- "--password",
1269
- this.config.config.PASSWORD,
1303
+ String(this.config.config.PORT),
1270
1304
  "--motor",
1271
1305
  this.config.type
1272
1306
  ];
1307
+ if (this.config.config.USER != null && this.config.config.USER !== "") {
1308
+ args.push("--user", this.config.config.USER);
1309
+ }
1310
+ if (this.config.config.PASSWORD != null && this.config.config.PASSWORD !== "") {
1311
+ args.push("--password", this.config.config.PASSWORD);
1312
+ }
1273
1313
  }
1314
+ const pool = this.config.pool ?? {};
1315
+ if (pool.maxConnections != null) args.push("--max-connections", String(pool.maxConnections));
1316
+ if (pool.minConnections != null) args.push("--min-connections", String(pool.minConnections));
1317
+ if (pool.acquireTimeoutMs != null) args.push("--acquire-timeout-ms", String(pool.acquireTimeoutMs));
1318
+ if (pool.idleTimeoutMs != null) args.push("--idle-timeout-ms", String(pool.idleTimeoutMs));
1274
1319
  return args;
1275
1320
  }
1321
+ /** El daemon puede desactivarse por config (daemon.enabled=false) o por env (DBCUBE_DAEMON=0). */
1322
+ daemonEnabled() {
1323
+ const flag = process.env.DBCUBE_DAEMON;
1324
+ if (flag === "0" || flag === "false") return false;
1325
+ return this.config?.daemon?.enabled !== false;
1326
+ }
1276
1327
  setConfig(name) {
1277
1328
  const configInstance = new Config();
1278
1329
  try {
@@ -1308,18 +1359,71 @@ var QueryEngine = class {
1308
1359
  const isExecuteAction = actionIndex !== -1 && args[actionIndex + 1] === "execute";
1309
1360
  const isQueryEngine = binary === "query_engine";
1310
1361
  if (isQueryEngine && isExecuteAction) {
1311
- return this.executeWithTcpServer(args);
1362
+ return this.executeWithTcpServer(this.argsToCommand(args));
1312
1363
  } else {
1313
1364
  return this.createProcess(binary, args);
1314
1365
  }
1315
1366
  }
1316
- async executeWithTcpServer(args) {
1367
+ argsToCommand(args) {
1368
+ const command = {};
1369
+ for (let i = 0; i < args.length; i += 2) {
1370
+ if (args[i].startsWith("--")) {
1371
+ command[args[i].substring(2)] = args[i + 1];
1372
+ }
1373
+ }
1374
+ return command;
1375
+ }
1376
+ /**
1377
+ * Executes a DML plan over the persistent TCP server.
1378
+ * Pass txId to run it inside an active transaction.
1379
+ */
1380
+ async executeDml(dml, txId) {
1381
+ const command = { action: "execute", dml: JSON.stringify(dml) };
1382
+ if (txId) command.tx_id = txId;
1383
+ return this.executeWithTcpServer(command);
1384
+ }
1385
+ /**
1386
+ * Executes raw SQL (or a MongoDB command document) with bound parameters
1387
+ * over the persistent TCP server.
1388
+ */
1389
+ async rawQuery(query, params = [], txId) {
1390
+ const command = { action: "raw", query, params };
1391
+ if (txId) command.tx_id = txId;
1392
+ return this.executeWithTcpServer(command);
1393
+ }
1394
+ /** Starts a server-side transaction and returns its id. */
1395
+ async beginTransaction() {
1396
+ const res = await this.executeWithTcpServer({ action: "begin" });
1397
+ if (res.status !== 200 || !res.data?.tx_id) {
1398
+ throw new Error(String(res.message || "Failed to begin transaction (update the query-engine binary: npx dbcube update)"));
1399
+ }
1400
+ return res.data.tx_id;
1401
+ }
1402
+ async commitTransaction(txId) {
1403
+ const res = await this.executeWithTcpServer({ action: "commit", tx_id: txId });
1404
+ if (res.status !== 200) throw new Error(String(res.message || "Failed to commit transaction"));
1405
+ }
1406
+ async rollbackTransaction(txId) {
1407
+ const res = await this.executeWithTcpServer({ action: "rollback", tx_id: txId });
1408
+ if (res.status !== 200) throw new Error(String(res.message || "Failed to rollback transaction"));
1409
+ }
1410
+ async executeWithTcpServer(command) {
1411
+ if (!this.daemonEnabled()) {
1412
+ if (command.tx_id || ["begin", "commit", "rollback"].includes(command.action)) {
1413
+ throw new Error("Transactions require daemon mode. Remove daemon.enabled=false from dbcube.config.js (or unset DBCUBE_DAEMON=0).");
1414
+ }
1415
+ const args = [];
1416
+ for (const [key, value] of Object.entries(command)) {
1417
+ args.push(`--${key.replace(/_/g, "-")}`, typeof value === "string" ? value : JSON.stringify(value));
1418
+ }
1419
+ return this.createProcess("query_engine", args);
1420
+ }
1317
1421
  const serverInfo = globalTcpServers.get(this.connectionId);
1318
1422
  if (!serverInfo || !serverInfo.process || serverInfo.process.killed) {
1319
1423
  await this.startTcpServer();
1320
1424
  await this.waitForServerReady();
1321
1425
  }
1322
- return this.sendTcpRequestFast(args);
1426
+ return this.sendTcpRequestFast(command);
1323
1427
  }
1324
1428
  async waitForServerReady() {
1325
1429
  const maxRetries = 10;
@@ -1362,10 +1466,11 @@ var QueryEngine = class {
1362
1466
  return queryCache.get(dmlJson);
1363
1467
  }
1364
1468
  const parsed = JSON.parse(dmlJson);
1365
- if (cacheSize < MAX_CACHE_SIZE) {
1366
- queryCache.set(dmlJson, parsed);
1367
- cacheSize++;
1469
+ if (queryCache.size >= MAX_CACHE_SIZE) {
1470
+ const oldest = queryCache.keys().next().value;
1471
+ if (oldest !== void 0) queryCache.delete(oldest);
1368
1472
  }
1473
+ queryCache.set(dmlJson, parsed);
1369
1474
  return parsed;
1370
1475
  }
1371
1476
  async startTcpServer() {
@@ -1412,14 +1517,14 @@ var QueryEngine = class {
1412
1517
  });
1413
1518
  });
1414
1519
  }
1415
- async sendTcpRequestFast(args) {
1520
+ async sendTcpRequestFast(command) {
1416
1521
  return new Promise((resolve5, reject) => {
1417
1522
  let queue = connectionQueues.get(this.connectionId);
1418
1523
  if (!queue) {
1419
1524
  queue = [];
1420
1525
  connectionQueues.set(this.connectionId, queue);
1421
1526
  }
1422
- queue.push({ args, resolve: resolve5, reject });
1527
+ queue.push({ command, resolve: resolve5, reject });
1423
1528
  this.processQueue();
1424
1529
  });
1425
1530
  }
@@ -1446,9 +1551,16 @@ var QueryEngine = class {
1446
1551
  connection = await this.createNewConnection(serverInfo.port);
1447
1552
  globalTcpConnections.set(this.connectionId, connection);
1448
1553
  }
1449
- const result = await this.executeOnConnection(connection, request.args);
1554
+ const result = await this.executeOnConnection(connection, request.command);
1450
1555
  request.resolve(result);
1451
1556
  } catch (error) {
1557
+ const staleConnection = globalTcpConnections.get(this.connectionId);
1558
+ if (staleConnection) {
1559
+ try {
1560
+ staleConnection.destroy();
1561
+ } catch {
1562
+ }
1563
+ }
1452
1564
  globalTcpConnections.delete(this.connectionId);
1453
1565
  request.reject(error);
1454
1566
  }
@@ -1476,16 +1588,8 @@ var QueryEngine = class {
1476
1588
  });
1477
1589
  });
1478
1590
  }
1479
- async executeOnConnection(connection, args) {
1591
+ async executeOnConnection(connection, command) {
1480
1592
  return new Promise((resolve5, reject) => {
1481
- const command = {};
1482
- for (let i = 0; i < args.length; i += 2) {
1483
- if (args[i].startsWith("--")) {
1484
- const key = args[i].substring(2);
1485
- const value = args[i + 1];
1486
- command[key] = value;
1487
- }
1488
- }
1489
1593
  let responseBuffer = "";
1490
1594
  let isResolved = false;
1491
1595
  const timeout = setTimeout(() => {
@@ -1498,14 +1602,18 @@ var QueryEngine = class {
1498
1602
  }, this.timeout);
1499
1603
  const onData = (data) => {
1500
1604
  responseBuffer += data.toString();
1501
- const match = responseBuffer.match(/PROCESS_RESPONSE:(\{.*\})/);
1502
- if (match && !isResolved) {
1605
+ let idx;
1606
+ while ((idx = responseBuffer.indexOf("\n")) !== -1 && !isResolved) {
1607
+ const line = responseBuffer.slice(0, idx);
1608
+ responseBuffer = responseBuffer.slice(idx + 1);
1609
+ const marker = line.indexOf("PROCESS_RESPONSE:");
1610
+ if (marker === -1) continue;
1503
1611
  isResolved = true;
1504
1612
  clearTimeout(timeout);
1505
1613
  connection.removeListener("data", onData);
1506
1614
  connection.removeListener("error", onError);
1507
1615
  try {
1508
- const response = JSON.parse(match[1]);
1616
+ const response = JSON.parse(line.slice(marker + "PROCESS_RESPONSE:".length));
1509
1617
  resolve5({
1510
1618
  status: response.status,
1511
1619
  message: response.message,
@@ -1527,7 +1635,7 @@ var QueryEngine = class {
1527
1635
  };
1528
1636
  connection.on("data", onData);
1529
1637
  connection.on("error", onError);
1530
- connection.write(JSON.stringify(command));
1638
+ connection.write(JSON.stringify(command) + "\n");
1531
1639
  });
1532
1640
  }
1533
1641
  async createProcess(binary, args) {
@@ -1554,12 +1662,15 @@ var QueryEngine = class {
1554
1662
  resolve5(response);
1555
1663
  }
1556
1664
  };
1557
- child.stdout.on("data", (data) => {
1558
- stdoutBuffer += data.toString();
1559
- const match = stdoutBuffer.match(/PROCESS_RESPONSE:(\{.*\})/);
1560
- if (match) {
1665
+ const tryParseLines = (buffer) => {
1666
+ let idx;
1667
+ while ((idx = buffer.indexOf("\n")) !== -1) {
1668
+ const line = buffer.slice(0, idx);
1669
+ buffer = buffer.slice(idx + 1);
1670
+ const marker = line.indexOf("PROCESS_RESPONSE:");
1671
+ if (marker === -1) continue;
1561
1672
  try {
1562
- const response = JSON.parse(match[1]);
1673
+ const response = JSON.parse(line.slice(marker + "PROCESS_RESPONSE:".length));
1563
1674
  resolveOnce({
1564
1675
  status: response.status,
1565
1676
  message: response.message,
@@ -1573,26 +1684,13 @@ var QueryEngine = class {
1573
1684
  });
1574
1685
  }
1575
1686
  }
1687
+ return buffer;
1688
+ };
1689
+ child.stdout.on("data", (data) => {
1690
+ stdoutBuffer = tryParseLines(stdoutBuffer + data.toString());
1576
1691
  });
1577
1692
  child.stderr.on("data", (data) => {
1578
- stderrBuffer += data.toString();
1579
- const match = stderrBuffer.match(/PROCESS_RESPONSE:(\{.*\})/);
1580
- if (match) {
1581
- try {
1582
- const response = JSON.parse(match[1]);
1583
- resolveOnce({
1584
- status: response.status,
1585
- message: response.message,
1586
- data: response.data
1587
- });
1588
- } catch (error) {
1589
- resolveOnce({
1590
- status: 500,
1591
- message: "Failed to parse response JSON",
1592
- data: null
1593
- });
1594
- }
1595
- }
1693
+ stderrBuffer = tryParseLines(stderrBuffer + data.toString());
1596
1694
  });
1597
1695
  child.on("close", (code) => {
1598
1696
  clearTimeout(timeoutId);
@@ -2452,7 +2550,7 @@ var ComputedFieldProcessor = class {
2452
2550
  const tableExistsQuery = `SELECT name FROM sqlite_master WHERE type='table' AND name='dbcube_computes_config'`;
2453
2551
  const tableExistsResult = await DbConfig_default.query(tableExistsQuery);
2454
2552
  if (tableExistsResult.status === "success" && tableExistsResult.data && tableExistsResult.data.length > 0) {
2455
- const queryComputes = await DbConfig_default.query(`SELECT * FROM dbcube_computes_config WHERE database_ref='${name}'`);
2553
+ const queryComputes = await DbConfig_default.queryWithParameters(`SELECT * FROM dbcube_computes_config WHERE database_ref=?`, [name]);
2456
2554
  computedFields = queryComputes.data;
2457
2555
  } else {
2458
2556
  computedFields = [];
@@ -2483,21 +2581,10 @@ var ComputedFieldProcessor = class {
2483
2581
  }
2484
2582
  functionBody = functionBody.replace(/@column\(([^)]+)\)/g, (_match, columnName) => {
2485
2583
  const cleanColumnName = columnName.trim().replace(/['"]/g, "");
2486
- const value = rowData[cleanColumnName];
2487
- if (value === null || value === void 0) {
2488
- return "null";
2489
- } else if (typeof value === "string") {
2490
- return `"${value.replace(/"/g, '\\"')}"`;
2491
- } else if (typeof value === "number" || typeof value === "boolean") {
2492
- return value.toString();
2493
- } else if (value instanceof Date) {
2494
- return `new Date("${value.toISOString()}")`;
2495
- } else {
2496
- return JSON.stringify(value);
2497
- }
2584
+ return `__row[${JSON.stringify(cleanColumnName)}]`;
2498
2585
  });
2499
- const computeFunction = new Function(functionBody);
2500
- return computeFunction();
2586
+ const computeFunction = new Function("__row", functionBody);
2587
+ return computeFunction(rowData);
2501
2588
  } catch (error) {
2502
2589
  console.error("Error processing computed field:", error);
2503
2590
  return null;
@@ -2540,14 +2627,7 @@ var ComputedFieldProcessor = class {
2540
2627
  /@column\(([^)]+)\)/g,
2541
2628
  (match, columnName) => {
2542
2629
  const cleanColumnName = columnName.replace(/['"]/g, "");
2543
- const value = processedItem[cleanColumnName];
2544
- if (typeof value === "string") {
2545
- return `"${value}"`;
2546
- } else if (value === null || value === void 0) {
2547
- return "null";
2548
- } else {
2549
- return String(value);
2550
- }
2630
+ return `__row[${JSON.stringify(cleanColumnName)}]`;
2551
2631
  }
2552
2632
  );
2553
2633
  const computeMatch = processedExpression.match(/@compute\s*\(\s*\(\s*\)\s*=>\s*\{(.*)\}\s*\)/s);
@@ -2555,8 +2635,8 @@ var ComputedFieldProcessor = class {
2555
2635
  throw new Error(`Formato de @compute inv\xE1lido para campo ${fieldName}`);
2556
2636
  }
2557
2637
  const functionBody = computeMatch[1];
2558
- const computeFunction = new Function(functionBody);
2559
- let result = computeFunction();
2638
+ const computeFunction = new Function("__row", functionBody);
2639
+ let result = computeFunction(processedItem);
2560
2640
  result = convertToType(result, type2);
2561
2641
  processedItem[fieldName] = result;
2562
2642
  } catch (error) {
@@ -2748,14 +2828,14 @@ var TableProcessor = class {
2748
2828
  if (await DbConfig_default.ifExist()) {
2749
2829
  await DbConfig_default.connect();
2750
2830
  try {
2751
- const tableExistsQuery = `SELECT name FROM sqlite_master WHERE type='table' AND name='dbcube_computes_config'`;
2831
+ const tableExistsQuery = `SELECT name FROM sqlite_master WHERE type='table' AND name='dbcube_schemas_config'`;
2752
2832
  const tableExistsResult = await DbConfig_default.query(tableExistsQuery);
2753
2833
  if (tableExistsResult.status === "success" && tableExistsResult.data && tableExistsResult.data.length > 0) {
2754
- const queryComputes = await DbConfig_default.query(`SELECT * FROM dbcube_schemas_config WHERE table_ref='${tableName}' AND database_ref='${database_ref}'`);
2834
+ const queryComputes = await DbConfig_default.queryWithParameters(`SELECT * FROM dbcube_schemas_config WHERE table_ref=? AND database_ref=?`, [tableName, database_ref]);
2755
2835
  const oldQuery = queryComputes.data[0];
2756
2836
  if (!oldQuery || !oldQuery.struct) {
2757
- console.error("No exist a previus schema please execute the refresh first...", oldQuery);
2758
- return [];
2837
+ await DbConfig_default.disconnect();
2838
+ return [nowQuery];
2759
2839
  }
2760
2840
  const nowSchema = parseCreateTableQuery(nowQuery, dbType);
2761
2841
  const oldSchema = parseCreateTableQuery(oldQuery.struct, dbType);
@@ -2790,7 +2870,7 @@ var TableProcessor = class {
2790
2870
  if (await DbConfig_default.ifExist()) {
2791
2871
  await DbConfig_default.connect();
2792
2872
  try {
2793
- await DbConfig_default.query(`DELETE FROM dbcube_schemas_config WHERE table_ref='${table_ref}' AND database_ref='${database_ref}'`);
2873
+ await DbConfig_default.queryWithParameters(`DELETE FROM dbcube_schemas_config WHERE table_ref=? AND database_ref=?`, [table_ref, database_ref]);
2794
2874
  const tableExistsQuery = `INSERT INTO dbcube_schemas_config (table_ref, database_ref, struct) VALUES (?, ?, ?)`;
2795
2875
  await DbConfig_default.queryWithParameters(tableExistsQuery, [table_ref, database_ref, struct]);
2796
2876
  } catch (error) {
@@ -2809,7 +2889,7 @@ var TriggerProcessor = class {
2809
2889
  const tableExistsQuery = `SELECT name FROM sqlite_master WHERE type='table' AND name='dbcube_triggers_config'`;
2810
2890
  const tableExistsResult = await DbConfig_default.query(tableExistsQuery);
2811
2891
  if (tableExistsResult.status === "success" && tableExistsResult.data && tableExistsResult.data.length > 0) {
2812
- const queryComputes = await DbConfig_default.query(`SELECT * FROM dbcube_triggers_config WHERE database_ref='${name}'`);
2892
+ const queryComputes = await DbConfig_default.queryWithParameters(`SELECT * FROM dbcube_triggers_config WHERE database_ref=?`, [name]);
2813
2893
  triggers = queryComputes.data;
2814
2894
  } else {
2815
2895
  triggers = [];