@carbonorm/carbonnode 6.1.0 → 6.1.1

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.
Files changed (65) hide show
  1. package/README.md +509 -292
  2. package/dist/index.cjs.js +209 -37
  3. package/dist/index.cjs.js.map +1 -1
  4. package/dist/index.esm.js +208 -38
  5. package/dist/index.esm.js.map +1 -1
  6. package/dist/orm/utils/sqlUtils.d.ts +1 -0
  7. package/dist/types/ormInterfaces.d.ts +1 -0
  8. package/dist/utils/sqlAllowList.d.ts +5 -3
  9. package/package.json +1 -1
  10. package/src/__tests__/fixtures/c6.fixture.ts +33 -0
  11. package/src/__tests__/sakila-db/C6.js +1 -1
  12. package/src/__tests__/sakila-db/C6.mysqldump.json +1 -1
  13. package/src/__tests__/sakila-db/C6.mysqldump.sql +1 -1
  14. package/src/__tests__/sakila-db/C6.ts +1 -1
  15. package/src/__tests__/sakila-db/sqlResponses/C6.actor.post.json +6 -6
  16. package/src/__tests__/sakila-db/sqlResponses/C6.actor.post.latest.json +3 -3
  17. package/src/__tests__/sakila-db/sqlResponses/C6.actor.put.json +1 -1
  18. package/src/__tests__/sakila-db/sqlResponses/C6.actor.put.lookup.json +3 -3
  19. package/src/__tests__/sakila-db/sqlResponses/C6.address.post.json +10 -10
  20. package/src/__tests__/sakila-db/sqlResponses/C6.address.post.latest.json +5 -5
  21. package/src/__tests__/sakila-db/sqlResponses/C6.address.put.json +1 -1
  22. package/src/__tests__/sakila-db/sqlResponses/C6.address.put.lookup.json +5 -5
  23. package/src/__tests__/sakila-db/sqlResponses/C6.category.post.json +4 -4
  24. package/src/__tests__/sakila-db/sqlResponses/C6.category.post.latest.json +2 -2
  25. package/src/__tests__/sakila-db/sqlResponses/C6.category.put.json +1 -1
  26. package/src/__tests__/sakila-db/sqlResponses/C6.category.put.lookup.json +2 -2
  27. package/src/__tests__/sakila-db/sqlResponses/C6.city.post.json +4 -4
  28. package/src/__tests__/sakila-db/sqlResponses/C6.city.post.latest.json +2 -2
  29. package/src/__tests__/sakila-db/sqlResponses/C6.city.put.json +1 -1
  30. package/src/__tests__/sakila-db/sqlResponses/C6.city.put.lookup.json +2 -2
  31. package/src/__tests__/sakila-db/sqlResponses/C6.country.post.json +4 -4
  32. package/src/__tests__/sakila-db/sqlResponses/C6.country.post.latest.json +2 -2
  33. package/src/__tests__/sakila-db/sqlResponses/C6.country.put.json +1 -1
  34. package/src/__tests__/sakila-db/sqlResponses/C6.country.put.lookup.json +2 -2
  35. package/src/__tests__/sakila-db/sqlResponses/C6.customer.post.json +10 -10
  36. package/src/__tests__/sakila-db/sqlResponses/C6.customer.post.latest.json +5 -5
  37. package/src/__tests__/sakila-db/sqlResponses/C6.customer.put.json +1 -1
  38. package/src/__tests__/sakila-db/sqlResponses/C6.customer.put.lookup.json +5 -5
  39. package/src/__tests__/sakila-db/sqlResponses/C6.film.post.json +4 -4
  40. package/src/__tests__/sakila-db/sqlResponses/C6.film.post.latest.json +2 -2
  41. package/src/__tests__/sakila-db/sqlResponses/C6.film.put.json +1 -1
  42. package/src/__tests__/sakila-db/sqlResponses/C6.film.put.lookup.json +2 -2
  43. package/src/__tests__/sakila-db/sqlResponses/C6.inventory.post.json +2 -2
  44. package/src/__tests__/sakila-db/sqlResponses/C6.inventory.post.latest.json +1 -1
  45. package/src/__tests__/sakila-db/sqlResponses/C6.inventory.put.json +1 -1
  46. package/src/__tests__/sakila-db/sqlResponses/C6.inventory.put.lookup.json +1 -1
  47. package/src/__tests__/sakila-db/sqlResponses/C6.language.post.json +4 -4
  48. package/src/__tests__/sakila-db/sqlResponses/C6.language.post.latest.json +2 -2
  49. package/src/__tests__/sakila-db/sqlResponses/C6.language.put.json +1 -1
  50. package/src/__tests__/sakila-db/sqlResponses/C6.language.put.lookup.json +2 -2
  51. package/src/__tests__/sakila-db/sqlResponses/C6.payment.post.json +4 -4
  52. package/src/__tests__/sakila-db/sqlResponses/C6.payment.post.latest.json +2 -2
  53. package/src/__tests__/sakila-db/sqlResponses/C6.payment.put.lookup.json +2 -2
  54. package/src/__tests__/sakila-db/sqlResponses/C6.rental.join.json +10 -10
  55. package/src/__tests__/sakila-db/sqlResponses/C6.rental.post.json +6 -6
  56. package/src/__tests__/sakila-db/sqlResponses/C6.rental.post.latest.json +3 -3
  57. package/src/__tests__/sakila-db/sqlResponses/C6.rental.put.json +1 -1
  58. package/src/__tests__/sakila-db/sqlResponses/C6.rental.put.lookup.json +3 -3
  59. package/src/__tests__/sqlAllowList.test.ts +56 -1
  60. package/src/__tests__/sqlBuilders.test.ts +38 -1
  61. package/src/executors/SqlExecutor.ts +4 -3
  62. package/src/orm/builders/ConditionBuilder.ts +3 -10
  63. package/src/orm/utils/sqlUtils.ts +172 -4
  64. package/src/types/ormInterfaces.ts +1 -0
  65. package/src/utils/sqlAllowList.ts +44 -11
package/dist/index.cjs.js CHANGED
@@ -956,7 +956,7 @@ function colorSql(sql) {
956
956
  return s;
957
957
  }
958
958
 
959
- var version = "6.1.0";
959
+ var version = "6.1.1";
960
960
 
961
961
  var DEFAULT_STEP = 8;
962
962
  function parseSemver(version) {
@@ -1801,14 +1801,176 @@ var HttpExecutor$1 = /*#__PURE__*/Object.freeze({
1801
1801
  });
1802
1802
 
1803
1803
  function convertHexIfBinary(_col, val, columnDef) {
1804
+ var _a;
1804
1805
  if (typeof val === 'string' &&
1805
1806
  /^[0-9a-fA-F]{32}$/.test(val) &&
1806
1807
  typeof columnDef === 'object' &&
1807
- columnDef.MYSQL_TYPE.toUpperCase().includes('BINARY')) {
1808
+ String((_a = columnDef.MYSQL_TYPE) !== null && _a !== void 0 ? _a : '').toUpperCase().includes('BINARY')) {
1808
1809
  return Buffer.from(val, 'hex');
1809
1810
  }
1810
1811
  return val;
1811
1812
  }
1813
+ var TEMPORAL_TYPES = new Set([
1814
+ 'date',
1815
+ 'datetime',
1816
+ 'timestamp',
1817
+ 'time',
1818
+ 'year',
1819
+ ]);
1820
+ var MYSQL_DATE_REGEX = /^\d{4}-\d{2}-\d{2}$/;
1821
+ var MYSQL_DATETIME_REGEX = /^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}(?:\.\d{1,6})?$/;
1822
+ var MYSQL_TIME_REGEX = /^-?\d{2,3}:\d{2}:\d{2}(?:\.\d{1,6})?$/;
1823
+ var ISO_DATETIME_REGEX = /^(\d{4}-\d{2}-\d{2})[Tt](\d{2}:\d{2}:\d{2})(\.\d{1,6})?([zZ]|[+-]\d{2}:\d{2})?$/;
1824
+ var pad2 = function (value) { return value.toString().padStart(2, '0'); };
1825
+ function trimFraction(value, precision) {
1826
+ var _a = value.split('.', 2), base = _a[0], fractionRaw = _a[1];
1827
+ if (precision <= 0 || !fractionRaw)
1828
+ return base;
1829
+ return "".concat(base, ".").concat(fractionRaw.slice(0, precision).padEnd(precision, '0'));
1830
+ }
1831
+ function normalizeFraction(raw, precision) {
1832
+ if (precision <= 0)
1833
+ return '';
1834
+ if (!raw)
1835
+ return '';
1836
+ var digits = raw.startsWith('.') ? raw.slice(1) : raw;
1837
+ return ".".concat(digits.slice(0, precision).padEnd(precision, '0'));
1838
+ }
1839
+ function formatDateUtc(value) {
1840
+ return "".concat(value.getUTCFullYear(), "-").concat(pad2(value.getUTCMonth() + 1), "-").concat(pad2(value.getUTCDate()));
1841
+ }
1842
+ function formatTimeUtc(value, precision) {
1843
+ var base = "".concat(pad2(value.getUTCHours()), ":").concat(pad2(value.getUTCMinutes()), ":").concat(pad2(value.getUTCSeconds()));
1844
+ if (precision <= 0)
1845
+ return base;
1846
+ var millis = value.getUTCMilliseconds().toString().padStart(3, '0');
1847
+ var fraction = millis.slice(0, Math.min(precision, 3)).padEnd(precision, '0');
1848
+ return "".concat(base, ".").concat(fraction);
1849
+ }
1850
+ function formatDateTimeUtc(value, precision) {
1851
+ return "".concat(formatDateUtc(value), " ").concat(formatTimeUtc(value, precision));
1852
+ }
1853
+ function parseEpochNumber(value) {
1854
+ if (!Number.isFinite(value))
1855
+ return undefined;
1856
+ var abs = Math.abs(value);
1857
+ if (abs >= 1e12) {
1858
+ var date = new Date(value);
1859
+ return Number.isNaN(date.getTime()) ? undefined : date;
1860
+ }
1861
+ if (abs >= 1e9) {
1862
+ var date = new Date(value * 1000);
1863
+ return Number.isNaN(date.getTime()) ? undefined : date;
1864
+ }
1865
+ return undefined;
1866
+ }
1867
+ function parseTemporalType(columnDef) {
1868
+ var _a;
1869
+ var raw = String((_a = columnDef === null || columnDef === void 0 ? void 0 : columnDef.MYSQL_TYPE) !== null && _a !== void 0 ? _a : '').trim().toLowerCase();
1870
+ if (!raw)
1871
+ return { baseType: undefined, precision: 0 };
1872
+ var base = raw.split(/[\s(]/, 1)[0];
1873
+ if (!TEMPORAL_TYPES.has(base))
1874
+ return { baseType: undefined, precision: 0 };
1875
+ var precisionMatch = raw.match(/^(?:datetime|timestamp|time)\((\d+)\)/);
1876
+ if (!precisionMatch)
1877
+ return { baseType: base, precision: 0 };
1878
+ var parsed = Number.parseInt(precisionMatch[1], 10);
1879
+ if (!Number.isFinite(parsed))
1880
+ return { baseType: base, precision: 0 };
1881
+ return { baseType: base, precision: Math.max(0, Math.min(6, parsed)) };
1882
+ }
1883
+ function normalizeTemporalString(value, baseType, precision) {
1884
+ var trimmed = value.trim();
1885
+ if (!trimmed)
1886
+ return value;
1887
+ if (baseType === 'date') {
1888
+ if (MYSQL_DATE_REGEX.test(trimmed))
1889
+ return trimmed;
1890
+ var iso_1 = trimmed.match(ISO_DATETIME_REGEX);
1891
+ if (iso_1) {
1892
+ var datePart = iso_1[1], timezonePart = iso_1[4];
1893
+ if (!timezonePart)
1894
+ return datePart;
1895
+ var parsed_1 = new Date(trimmed);
1896
+ return Number.isNaN(parsed_1.getTime()) ? value : formatDateUtc(parsed_1);
1897
+ }
1898
+ var parsed_2 = new Date(trimmed);
1899
+ return Number.isNaN(parsed_2.getTime()) ? value : formatDateUtc(parsed_2);
1900
+ }
1901
+ if (baseType === 'time') {
1902
+ if (MYSQL_TIME_REGEX.test(trimmed))
1903
+ return trimFraction(trimmed, precision);
1904
+ var iso_2 = trimmed.match(ISO_DATETIME_REGEX);
1905
+ if (iso_2) {
1906
+ var timePart = iso_2[2], fractionPart = iso_2[3], timezonePart = iso_2[4];
1907
+ if (!timezonePart) {
1908
+ return "".concat(timePart).concat(normalizeFraction(fractionPart, precision));
1909
+ }
1910
+ var parsed_3 = new Date(trimmed);
1911
+ return Number.isNaN(parsed_3.getTime()) ? value : formatTimeUtc(parsed_3, precision);
1912
+ }
1913
+ var parsed_4 = new Date(trimmed);
1914
+ return Number.isNaN(parsed_4.getTime()) ? value : formatTimeUtc(parsed_4, precision);
1915
+ }
1916
+ if (baseType === 'year') {
1917
+ if (/^\d{2,4}$/.test(trimmed))
1918
+ return trimmed;
1919
+ var parsed_5 = new Date(trimmed);
1920
+ return Number.isNaN(parsed_5.getTime()) ? value : String(parsed_5.getUTCFullYear());
1921
+ }
1922
+ if (MYSQL_DATETIME_REGEX.test(trimmed))
1923
+ return trimFraction(trimmed, precision);
1924
+ var iso = trimmed.match(ISO_DATETIME_REGEX);
1925
+ if (iso) {
1926
+ var datePart = iso[1], timePart = iso[2], fractionPart = iso[3], timezonePart = iso[4];
1927
+ if (!timezonePart) {
1928
+ return "".concat(datePart, " ").concat(timePart).concat(normalizeFraction(fractionPart, precision));
1929
+ }
1930
+ var parsed_6 = new Date(trimmed);
1931
+ return Number.isNaN(parsed_6.getTime()) ? value : formatDateTimeUtc(parsed_6, precision);
1932
+ }
1933
+ var parsed = new Date(trimmed);
1934
+ return Number.isNaN(parsed.getTime()) ? value : formatDateTimeUtc(parsed, precision);
1935
+ }
1936
+ function convertTemporalIfNeeded(value, columnDef) {
1937
+ var _a = parseTemporalType(columnDef), baseType = _a.baseType, precision = _a.precision;
1938
+ if (!baseType)
1939
+ return value;
1940
+ if (value === null || value === undefined)
1941
+ return value;
1942
+ if (typeof Buffer !== 'undefined' && Buffer.isBuffer && Buffer.isBuffer(value))
1943
+ return value;
1944
+ if (value instanceof Date) {
1945
+ if (baseType === 'date')
1946
+ return formatDateUtc(value);
1947
+ if (baseType === 'time')
1948
+ return formatTimeUtc(value, precision);
1949
+ if (baseType === 'year')
1950
+ return String(value.getUTCFullYear());
1951
+ return formatDateTimeUtc(value, precision);
1952
+ }
1953
+ if (typeof value === 'number') {
1954
+ var parsed = parseEpochNumber(value);
1955
+ if (!parsed)
1956
+ return value;
1957
+ if (baseType === 'date')
1958
+ return formatDateUtc(parsed);
1959
+ if (baseType === 'time')
1960
+ return formatTimeUtc(parsed, precision);
1961
+ if (baseType === 'year')
1962
+ return String(parsed.getUTCFullYear());
1963
+ return formatDateTimeUtc(parsed, precision);
1964
+ }
1965
+ if (typeof value === 'string') {
1966
+ return normalizeTemporalString(value, baseType, precision);
1967
+ }
1968
+ return value;
1969
+ }
1970
+ function convertSqlValueForColumn(col, val, columnDef) {
1971
+ var binaryConverted = convertHexIfBinary(col, val, columnDef);
1972
+ return convertTemporalIfNeeded(binaryConverted, columnDef);
1973
+ }
1812
1974
 
1813
1975
  // ========================
1814
1976
  // SQL Operators & Expressions
@@ -2454,16 +2616,8 @@ var ConditionBuilder = /** @class */ (function (_super) {
2454
2616
  Object.values(table.COLUMNS).includes(column));
2455
2617
  };
2456
2618
  ConditionBuilder.prototype.addParam = function (params, column, value) {
2457
- var _a, _b, _c, _d, _e;
2458
- // Determine column definition from C6.TABLES to support type-aware conversions (e.g., BINARY hex -> Buffer)
2459
- var columnDef;
2460
- if (typeof column === 'string' && column.includes('.')) {
2461
- var _f = column.split('.', 2), tableName = _f[0], colName = _f[1];
2462
- var table = (_b = (_a = this.config.C6) === null || _a === void 0 ? void 0 : _a.TABLES) === null || _b === void 0 ? void 0 : _b[tableName];
2463
- // Support both short-keyed and fully-qualified TYPE_VALIDATION entries
2464
- columnDef = (_d = (_c = table === null || table === void 0 ? void 0 : table.TYPE_VALIDATION) === null || _c === void 0 ? void 0 : _c[colName]) !== null && _d !== void 0 ? _d : (_e = table === null || table === void 0 ? void 0 : table.TYPE_VALIDATION) === null || _e === void 0 ? void 0 : _e["".concat(tableName, ".").concat(colName)];
2465
- }
2466
- var val = convertHexIfBinary(column, value, columnDef);
2619
+ var columnDef = this.resolveColumnDefinition(column);
2620
+ var val = convertSqlValueForColumn(column, value, columnDef);
2467
2621
  if (this.useNamedParams) {
2468
2622
  var key = "param".concat(Object.keys(params).length);
2469
2623
  params[key] = val;
@@ -3777,6 +3931,7 @@ function normalizeSingularRequest(requestMethod, request, restModel, removedPrim
3777
3931
  return tslib.__assign(tslib.__assign({}, normalized), { dataInsertMultipleRows: dataInsertMultipleRows, cacheResults: cacheResults, skipReactBootstrap: skipReactBootstrap, fetchDependencies: fetchDependencies, debug: debug, success: success, error: error });
3778
3932
  }
3779
3933
 
3934
+ var DEFAULT_NORMALIZER_CACHE_KEY = "__default__";
3780
3935
  var allowListCache = new Map();
3781
3936
  var ANSI_ESCAPE_REGEX = /\x1b\[[0-9;]*m/g;
3782
3937
  var COLLAPSED_BIND_ROW_REGEX = /\(\?\s*×\d+\)/g;
@@ -3828,7 +3983,17 @@ var normalizeSql = function (sql) {
3828
3983
  normalized = normalized.replace(/;\s*$/, "");
3829
3984
  return normalized.replace(/\s+/g, " ").trim();
3830
3985
  };
3831
- var parseAllowList = function (raw, sourcePath) {
3986
+ var normalizeSqlWith = function (sql, sqlQueryNormalizer) {
3987
+ var normalized = normalizeSql(sql);
3988
+ if (!sqlQueryNormalizer)
3989
+ return normalized;
3990
+ var customized = sqlQueryNormalizer(normalized);
3991
+ if (typeof customized !== "string") {
3992
+ throw new Error("sqlQueryNormalizer must return a string.");
3993
+ }
3994
+ return customized.replace(/\s+/g, " ").trim();
3995
+ };
3996
+ var parseAllowList = function (raw, sourcePath, sqlQueryNormalizer) {
3832
3997
  var parsed;
3833
3998
  try {
3834
3999
  parsed = JSON.parse(raw);
@@ -3841,59 +4006,63 @@ var parseAllowList = function (raw, sourcePath) {
3841
4006
  }
3842
4007
  var sqlEntries = parsed
3843
4008
  .filter(function (entry) { return typeof entry === "string"; })
3844
- .map(normalizeSql)
4009
+ .map(function (entry) { return normalizeSqlWith(entry, sqlQueryNormalizer); })
3845
4010
  .filter(function (entry) { return entry.length > 0; });
3846
4011
  if (sqlEntries.length !== parsed.length) {
3847
4012
  throw new Error("SQL allowlist at ".concat(sourcePath, " must contain only string entries."));
3848
4013
  }
3849
4014
  return sqlEntries;
3850
4015
  };
3851
- var loadSqlAllowList = function (allowListPath) { return tslib.__awaiter(void 0, void 0, void 0, function () {
3852
- var _a, readFile, stat, fileStat, cached, raw, sqlEntries, allowList;
3853
- return tslib.__generator(this, function (_b) {
3854
- switch (_b.label) {
4016
+ var loadSqlAllowList = function (allowListPath, sqlQueryNormalizer) { return tslib.__awaiter(void 0, void 0, void 0, function () {
4017
+ var _a, readFile, stat, fileStat, pathCache, cacheKey, cached, raw, sqlEntries, allowList;
4018
+ var _b;
4019
+ return tslib.__generator(this, function (_c) {
4020
+ switch (_c.label) {
3855
4021
  case 0:
3856
4022
  if (!isNode()) {
3857
4023
  throw new Error("SQL allowlist validation requires a Node runtime.");
3858
4024
  }
3859
4025
  return [4 /*yield*/, import('node:fs/promises')];
3860
4026
  case 1:
3861
- _a = _b.sent(), readFile = _a.readFile, stat = _a.stat;
3862
- _b.label = 2;
4027
+ _a = _c.sent(), readFile = _a.readFile, stat = _a.stat;
4028
+ _c.label = 2;
3863
4029
  case 2:
3864
- _b.trys.push([2, 4, , 5]);
4030
+ _c.trys.push([2, 4, , 5]);
3865
4031
  return [4 /*yield*/, stat(allowListPath)];
3866
4032
  case 3:
3867
- fileStat = _b.sent();
4033
+ fileStat = _c.sent();
3868
4034
  return [3 /*break*/, 5];
3869
4035
  case 4:
3870
- _b.sent();
4036
+ _c.sent();
3871
4037
  throw new Error("SQL allowlist file not found at ".concat(allowListPath, "."));
3872
4038
  case 5:
3873
- cached = allowListCache.get(allowListPath);
4039
+ pathCache = (_b = allowListCache.get(allowListPath)) !== null && _b !== void 0 ? _b : new Map();
4040
+ cacheKey = sqlQueryNormalizer !== null && sqlQueryNormalizer !== void 0 ? sqlQueryNormalizer : DEFAULT_NORMALIZER_CACHE_KEY;
4041
+ cached = pathCache.get(cacheKey);
3874
4042
  if (cached &&
3875
4043
  cached.mtimeMs === fileStat.mtimeMs &&
3876
4044
  cached.size === fileStat.size) {
3877
4045
  return [2 /*return*/, cached.allowList];
3878
4046
  }
3879
- _b.label = 6;
4047
+ _c.label = 6;
3880
4048
  case 6:
3881
- _b.trys.push([6, 8, , 9]);
4049
+ _c.trys.push([6, 8, , 9]);
3882
4050
  return [4 /*yield*/, readFile(allowListPath, "utf-8")];
3883
4051
  case 7:
3884
- raw = _b.sent();
4052
+ raw = _c.sent();
3885
4053
  return [3 /*break*/, 9];
3886
4054
  case 8:
3887
- _b.sent();
4055
+ _c.sent();
3888
4056
  throw new Error("SQL allowlist file not found at ".concat(allowListPath, "."));
3889
4057
  case 9:
3890
- sqlEntries = parseAllowList(raw, allowListPath);
4058
+ sqlEntries = parseAllowList(raw, allowListPath, sqlQueryNormalizer);
3891
4059
  allowList = new Set(sqlEntries);
3892
- allowListCache.set(allowListPath, {
4060
+ pathCache.set(cacheKey, {
3893
4061
  allowList: allowList,
3894
4062
  mtimeMs: fileStat.mtimeMs,
3895
4063
  size: fileStat.size,
3896
4064
  });
4065
+ allowListCache.set(allowListPath, pathCache);
3897
4066
  return [2 /*return*/, allowList];
3898
4067
  }
3899
4068
  });
@@ -3920,15 +4089,15 @@ var extractSqlEntries = function (payload) {
3920
4089
  }
3921
4090
  return [];
3922
4091
  };
3923
- var collectSqlAllowListEntries = function (payload, entries) {
4092
+ var collectSqlAllowListEntries = function (payload, entries, sqlQueryNormalizer) {
3924
4093
  if (entries === void 0) { entries = new Set(); }
3925
4094
  var sqlEntries = extractSqlEntries(payload)
3926
- .map(normalizeSql)
4095
+ .map(function (entry) { return normalizeSqlWith(entry, sqlQueryNormalizer); })
3927
4096
  .filter(function (entry) { return entry.length > 0; });
3928
4097
  sqlEntries.forEach(function (entry) { return entries.add(entry); });
3929
4098
  return entries;
3930
4099
  };
3931
- var compileSqlAllowList = function (allowListPath, entries) { return tslib.__awaiter(void 0, void 0, void 0, function () {
4100
+ var compileSqlAllowList = function (allowListPath, entries, sqlQueryNormalizer) { return tslib.__awaiter(void 0, void 0, void 0, function () {
3932
4101
  var _a, writeFile, mkdir, path, compiled;
3933
4102
  return tslib.__generator(this, function (_b) {
3934
4103
  switch (_b.label) {
@@ -3946,7 +4115,7 @@ var compileSqlAllowList = function (allowListPath, entries) { return tslib.__awa
3946
4115
  case 3:
3947
4116
  _b.sent();
3948
4117
  compiled = Array.from(new Set(Array.from(entries)
3949
- .map(normalizeSql)
4118
+ .map(function (entry) { return normalizeSqlWith(entry, sqlQueryNormalizer); })
3950
4119
  .filter(function (entry) { return entry.length > 0; }))).sort();
3951
4120
  return [4 /*yield*/, writeFile(allowListPath, JSON.stringify(compiled, null, 2))];
3952
4121
  case 4:
@@ -4799,7 +4968,7 @@ var SqlExecutor = /** @class */ (function (_super) {
4799
4968
  };
4800
4969
  SqlExecutor.prototype.validateSqlAllowList = function (sql) {
4801
4970
  return tslib.__awaiter(this, void 0, void 0, function () {
4802
- var allowListPath, allowList, normalized;
4971
+ var allowListPath, sqlQueryNormalizer, allowList, normalized;
4803
4972
  var _a;
4804
4973
  return tslib.__generator(this, function (_b) {
4805
4974
  switch (_b.label) {
@@ -4808,10 +4977,11 @@ var SqlExecutor = /** @class */ (function (_super) {
4808
4977
  if (!allowListPath) {
4809
4978
  return [2 /*return*/, "not verified"];
4810
4979
  }
4811
- return [4 /*yield*/, loadSqlAllowList(allowListPath)];
4980
+ sqlQueryNormalizer = this.config.sqlQueryNormalizer;
4981
+ return [4 /*yield*/, loadSqlAllowList(allowListPath, sqlQueryNormalizer)];
4812
4982
  case 1:
4813
4983
  allowList = _b.sent();
4814
- normalized = normalizeSql(sql);
4984
+ normalized = normalizeSqlWith(sql, sqlQueryNormalizer);
4815
4985
  if (!allowList.has(normalized)) {
4816
4986
  throw createSqlAllowListBlockedError({
4817
4987
  tableName: typeof ((_a = this.config.restModel) === null || _a === void 0 ? void 0 : _a.TABLE_NAME) === "string"
@@ -5096,6 +5266,7 @@ exports.colorSql = colorSql;
5096
5266
  exports.compileSqlAllowList = compileSqlAllowList;
5097
5267
  exports.convertForRequestBody = convertForRequestBody;
5098
5268
  exports.convertHexIfBinary = convertHexIfBinary;
5269
+ exports.convertSqlValueForColumn = convertSqlValueForColumn;
5099
5270
  exports.derivedTable = derivedTable;
5100
5271
  exports.determineRuntimeJsType = determineRuntimeJsType;
5101
5272
  exports.distSphere = distSphere;
@@ -5124,6 +5295,7 @@ exports.logSql = logSql;
5124
5295
  exports.logWithLevel = logWithLevel;
5125
5296
  exports.normalizeSingularRequest = normalizeSingularRequest;
5126
5297
  exports.normalizeSql = normalizeSql;
5298
+ exports.normalizeSqlWith = normalizeSqlWith;
5127
5299
  exports.notifyToast = notifyToast;
5128
5300
  exports.onError = onError;
5129
5301
  exports.onSuccess = onSuccess;