@utilix-tech/sdk 0.79.0 → 0.81.0

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
@@ -43,13 +43,16 @@ var __export = (target, all) => {
43
43
  var json_exports = {};
44
44
  __export(json_exports, {
45
45
  applyJsonMergePatch: () => applyJsonMergePatch,
46
+ applyJsonPatch: () => applyJsonPatch,
46
47
  csvToJson: () => csvToJson,
47
48
  detectFormat: () => detectFormat,
48
49
  diffJson: () => diffJson,
50
+ diffJsonPatch: () => diffJsonPatch,
49
51
  evaluateJsonPath: () => evaluateJsonPath,
50
52
  formatDiffLine: () => formatDiffLine,
51
53
  formatJson: () => formatJson,
52
54
  generateExample: () => generateExample,
55
+ generateJsonPatch: () => generateJsonPatch,
53
56
  getJsonStats: () => getJsonStats,
54
57
  inferGoType: () => inferGoType,
55
58
  inferPythonType: () => inferPythonType,
@@ -1473,6 +1476,219 @@ function applyJsonMergePatch(targetJson, patchJson) {
1473
1476
  }
1474
1477
  return { result: mergeJsonPatch(target, patch) };
1475
1478
  }
1479
+ function _escapeJsonPointerToken(token) {
1480
+ return token.replace(/~/g, "~0").replace(/\//g, "~1");
1481
+ }
1482
+ function _unescapeJsonPointerToken(token) {
1483
+ return token.replace(/~1/g, "/").replace(/~0/g, "~");
1484
+ }
1485
+ function _parseJsonPointer(pointer) {
1486
+ if (pointer === "") return [];
1487
+ if (!pointer.startsWith("/")) throw new Error(`Invalid JSON Pointer "${pointer}": must start with "/"`);
1488
+ return pointer.slice(1).split("/").map(_unescapeJsonPointerToken);
1489
+ }
1490
+ function _isPlainObject(value) {
1491
+ return typeof value === "object" && value !== null && !Array.isArray(value);
1492
+ }
1493
+ function _deepEqual(a, b) {
1494
+ if (a === b) return true;
1495
+ if (typeof a !== typeof b) return false;
1496
+ if (Array.isArray(a) || Array.isArray(b)) {
1497
+ if (!Array.isArray(a) || !Array.isArray(b) || a.length !== b.length) return false;
1498
+ return a.every((v, i) => _deepEqual(v, b[i]));
1499
+ }
1500
+ if (_isPlainObject(a) && _isPlainObject(b)) {
1501
+ const aKeys = Object.keys(a);
1502
+ const bKeys = Object.keys(b);
1503
+ if (aKeys.length !== bKeys.length) return false;
1504
+ return aKeys.every((k) => k in b && _deepEqual(a[k], b[k]));
1505
+ }
1506
+ return false;
1507
+ }
1508
+ function _getByTokens(doc, tokens) {
1509
+ let current = doc;
1510
+ for (const token of tokens) {
1511
+ if (Array.isArray(current)) {
1512
+ const index = token === "-" ? current.length - 1 : parseInt(token, 10);
1513
+ if (!Number.isInteger(index) || index < 0 || index >= current.length) return { found: false, value: void 0 };
1514
+ current = current[index];
1515
+ } else if (_isPlainObject(current)) {
1516
+ if (!(token in current)) return { found: false, value: void 0 };
1517
+ current = current[token];
1518
+ } else {
1519
+ return { found: false, value: void 0 };
1520
+ }
1521
+ }
1522
+ return { found: true, value: current };
1523
+ }
1524
+ function diffJsonPatch(a, b) {
1525
+ const ops = [];
1526
+ _diffValue(a, b, "", ops);
1527
+ return ops;
1528
+ }
1529
+ function _diffValue(a, b, path, ops) {
1530
+ if (_deepEqual(a, b)) return;
1531
+ if (_isPlainObject(a) && _isPlainObject(b)) {
1532
+ for (const key of Object.keys(a)) {
1533
+ if (!(key in b)) ops.push({ op: "remove", path: `${path}/${_escapeJsonPointerToken(key)}` });
1534
+ }
1535
+ for (const key of Object.keys(b)) {
1536
+ const childPath = `${path}/${_escapeJsonPointerToken(key)}`;
1537
+ if (!(key in a)) {
1538
+ ops.push({ op: "add", path: childPath, value: b[key] });
1539
+ } else {
1540
+ _diffValue(a[key], b[key], childPath, ops);
1541
+ }
1542
+ }
1543
+ return;
1544
+ }
1545
+ if (Array.isArray(a) && Array.isArray(b)) {
1546
+ const minLen = Math.min(a.length, b.length);
1547
+ for (let i = 0; i < minLen; i++) {
1548
+ _diffValue(a[i], b[i], `${path}/${i}`, ops);
1549
+ }
1550
+ if (b.length > a.length) {
1551
+ for (let i = a.length; i < b.length; i++) ops.push({ op: "add", path: `${path}/${i}`, value: b[i] });
1552
+ } else if (a.length > b.length) {
1553
+ for (let i = a.length - 1; i >= b.length; i--) ops.push({ op: "remove", path: `${path}/${i}` });
1554
+ }
1555
+ return;
1556
+ }
1557
+ ops.push({ op: "replace", path, value: b });
1558
+ }
1559
+ function applyJsonPatch(target, operations) {
1560
+ let doc = JSON.parse(JSON.stringify(target ?? null));
1561
+ const applyOne = (op, index) => {
1562
+ if (op.path === void 0 || op.op === void 0) return `Operation ${index}: missing "op" or "path"`;
1563
+ let tokens;
1564
+ try {
1565
+ tokens = _parseJsonPointer(op.path);
1566
+ } catch (e) {
1567
+ return `Operation ${index}: ${e.message}`;
1568
+ }
1569
+ const setAt = (tgtTokens, value) => {
1570
+ if (tgtTokens.length === 0) {
1571
+ doc = value;
1572
+ return null;
1573
+ }
1574
+ const parentTokens = tgtTokens.slice(0, -1);
1575
+ const lastToken = tgtTokens[tgtTokens.length - 1];
1576
+ const { found, value: parent } = _getByTokens(doc, parentTokens);
1577
+ if (!found) return `Operation ${index}: path "${op.path}" has no parent`;
1578
+ if (Array.isArray(parent)) {
1579
+ const idx = lastToken === "-" ? parent.length : parseInt(lastToken, 10);
1580
+ if (!Number.isInteger(idx) || idx < 0 || idx > parent.length) return `Operation ${index}: array index "${lastToken}" out of bounds`;
1581
+ parent.splice(idx, 0, value);
1582
+ } else if (_isPlainObject(parent)) {
1583
+ parent[lastToken] = value;
1584
+ } else {
1585
+ return `Operation ${index}: cannot add into a non-object, non-array value at "${op.path}"`;
1586
+ }
1587
+ return null;
1588
+ };
1589
+ const replaceAt = (tgtTokens, value) => {
1590
+ if (tgtTokens.length === 0) {
1591
+ doc = value;
1592
+ return null;
1593
+ }
1594
+ const parentTokens = tgtTokens.slice(0, -1);
1595
+ const lastToken = tgtTokens[tgtTokens.length - 1];
1596
+ const { found, value: parent } = _getByTokens(doc, parentTokens);
1597
+ if (!found) return `Operation ${index}: path "${op.path}" has no parent`;
1598
+ if (Array.isArray(parent)) {
1599
+ const idx = lastToken === "-" ? parent.length - 1 : parseInt(lastToken, 10);
1600
+ if (!Number.isInteger(idx) || idx < 0 || idx >= parent.length) return `Operation ${index}: array index "${lastToken}" out of bounds`;
1601
+ parent[idx] = value;
1602
+ } else if (_isPlainObject(parent)) {
1603
+ if (!(lastToken in parent)) return `Operation ${index}: path "${op.path}" does not exist`;
1604
+ parent[lastToken] = value;
1605
+ } else {
1606
+ return `Operation ${index}: cannot replace into a non-object, non-array value at "${op.path}"`;
1607
+ }
1608
+ return null;
1609
+ };
1610
+ const removeAt = (tgtTokens) => {
1611
+ if (tgtTokens.length === 0) return { error: `Operation ${index}: cannot remove the whole document (path "")` };
1612
+ const parentTokens = tgtTokens.slice(0, -1);
1613
+ const lastToken = tgtTokens[tgtTokens.length - 1];
1614
+ const { found, value: parent } = _getByTokens(doc, parentTokens);
1615
+ if (!found) return { error: `Operation ${index}: path "${op.path}" has no parent` };
1616
+ if (Array.isArray(parent)) {
1617
+ const idx = lastToken === "-" ? parent.length - 1 : parseInt(lastToken, 10);
1618
+ if (!Number.isInteger(idx) || idx < 0 || idx >= parent.length) return { error: `Operation ${index}: array index "${lastToken}" out of bounds` };
1619
+ const [removed] = parent.splice(idx, 1);
1620
+ return { error: null, removed };
1621
+ }
1622
+ if (_isPlainObject(parent)) {
1623
+ if (!(lastToken in parent)) return { error: `Operation ${index}: path "${op.path}" does not exist` };
1624
+ const removed = parent[lastToken];
1625
+ delete parent[lastToken];
1626
+ return { error: null, removed };
1627
+ }
1628
+ return { error: `Operation ${index}: cannot remove from a non-object, non-array value at "${op.path}"` };
1629
+ };
1630
+ switch (op.op) {
1631
+ case "add":
1632
+ return setAt(tokens, op.value);
1633
+ case "replace":
1634
+ return replaceAt(tokens, op.value);
1635
+ case "remove":
1636
+ return removeAt(tokens).error;
1637
+ case "test": {
1638
+ const { found, value } = _getByTokens(doc, tokens);
1639
+ if (!found) return `Operation ${index}: path "${op.path}" does not exist`;
1640
+ if (!_deepEqual(value, op.value)) return `Operation ${index}: test failed at "${op.path}"`;
1641
+ return null;
1642
+ }
1643
+ case "move": {
1644
+ if (!op.from) return `Operation ${index}: "move" requires "from"`;
1645
+ let fromTokens;
1646
+ try {
1647
+ fromTokens = _parseJsonPointer(op.from);
1648
+ } catch (e) {
1649
+ return `Operation ${index}: ${e.message}`;
1650
+ }
1651
+ const removal = removeAt(fromTokens);
1652
+ if (removal.error) return removal.error;
1653
+ return setAt(tokens, removal.removed);
1654
+ }
1655
+ case "copy": {
1656
+ if (!op.from) return `Operation ${index}: "copy" requires "from"`;
1657
+ let fromTokens;
1658
+ try {
1659
+ fromTokens = _parseJsonPointer(op.from);
1660
+ } catch (e) {
1661
+ return `Operation ${index}: ${e.message}`;
1662
+ }
1663
+ const { found, value } = _getByTokens(doc, fromTokens);
1664
+ if (!found) return `Operation ${index}: "from" path "${op.from}" does not exist`;
1665
+ return setAt(tokens, JSON.parse(JSON.stringify(value)));
1666
+ }
1667
+ default:
1668
+ return `Operation ${index}: unknown op "${op.op}"`;
1669
+ }
1670
+ };
1671
+ for (let i = 0; i < operations.length; i++) {
1672
+ const err = applyOne(operations[i], i);
1673
+ if (err) return { error: err };
1674
+ }
1675
+ return { result: doc };
1676
+ }
1677
+ function generateJsonPatch(aJson, bJson) {
1678
+ let a;
1679
+ try {
1680
+ a = JSON.parse(aJson);
1681
+ } catch {
1682
+ return { error: "First document is not valid JSON" };
1683
+ }
1684
+ let b;
1685
+ try {
1686
+ b = JSON.parse(bJson);
1687
+ } catch {
1688
+ return { error: "Second document is not valid JSON" };
1689
+ }
1690
+ return { patch: diffJsonPatch(a, b) };
1691
+ }
1476
1692
 
1477
1693
  // src/tools/encoding.ts
1478
1694
  var encoding_exports = {};
@@ -16520,6 +16736,7 @@ __export(code_exports, {
16520
16736
  ALL_FLAGS: () => ALL_FLAGS,
16521
16737
  CHEATSHEET: () => CHEATSHEET,
16522
16738
  DEFAULT_COMMIT_TYPES: () => DEFAULT_COMMIT_TYPES,
16739
+ KNOWN_LANGUAGE_TAGS: () => KNOWN_LANGUAGE_TAGS,
16523
16740
  MIME_TABLE: () => MIME_TABLE,
16524
16741
  OPERATIONS: () => OPERATIONS,
16525
16742
  SQL_DEFAULT_OPTIONS: () => SQL_DEFAULT_OPTIONS,
@@ -16532,6 +16749,7 @@ __export(code_exports, {
16532
16749
  collapseJsWhitespace: () => collapseJsWhitespace,
16533
16750
  countProperties: () => countProperties,
16534
16751
  countRules: () => countRules,
16752
+ countSqlPlaceholders: () => countSqlPlaceholders,
16535
16753
  detectDialect: () => detectDialect,
16536
16754
  detectOperationType: () => detectOperationType,
16537
16755
  detectRedos: () => detectRedos,
@@ -16557,6 +16775,7 @@ __export(code_exports, {
16557
16775
  minifySql: () => minifySql,
16558
16776
  normalizeRef: () => normalizeRef,
16559
16777
  parseCommitTrailers: () => parseCommitTrailers,
16778
+ parseConnectionString: () => parseConnectionString,
16560
16779
  parseDockerImage: () => parseDockerImage,
16561
16780
  parseEnv: () => parseEnv2,
16562
16781
  parseGitCommand: () => parseGitCommand,
@@ -16576,6 +16795,7 @@ __export(code_exports, {
16576
16795
  validateAria: () => validateAria,
16577
16796
  validateEditorConfig: () => validateEditorConfig,
16578
16797
  validateEnvKey: () => validateEnvKey2,
16798
+ validateFenceLanguageTags: () => validateFenceLanguageTags,
16579
16799
  validatePackageExports: () => validatePackageExports,
16580
16800
  validateTsconfig: () => validateTsconfig
16581
16801
  });
@@ -20389,6 +20609,394 @@ function validateAria(html) {
20389
20609
  valid: issues.every((i) => i.severity !== "error")
20390
20610
  };
20391
20611
  }
20612
+ var CONNECTION_STRING_RE = /^([a-zA-Z][a-zA-Z0-9+.-]*):\/\/(?:([^@/?#]*)@)?([^/?#]*)(?:\/([^?#]*))?(?:\?([^#]*))?$/;
20613
+ function _parseConnectionHost(segment) {
20614
+ const ipv6Match = segment.match(/^\[([^\]]+)\](?::(\d+))?$/);
20615
+ if (ipv6Match) {
20616
+ return { host: ipv6Match[1], port: ipv6Match[2] ? parseInt(ipv6Match[2], 10) : null };
20617
+ }
20618
+ const lastColon = segment.lastIndexOf(":");
20619
+ if (lastColon === -1) return { host: segment, port: null };
20620
+ const portPart = segment.slice(lastColon + 1);
20621
+ if (!/^\d+$/.test(portPart)) return { host: segment, port: null };
20622
+ return { host: segment.slice(0, lastColon), port: parseInt(portPart, 10) };
20623
+ }
20624
+ function parseConnectionString(input) {
20625
+ if (!input || typeof input !== "string" || !input.trim()) {
20626
+ return { error: "Connection string is empty" };
20627
+ }
20628
+ const trimmed = input.trim();
20629
+ const match = trimmed.match(CONNECTION_STRING_RE);
20630
+ if (!match) {
20631
+ return { error: "Not a valid scheme://[user[:password]@]host[,host2][/database][?params] connection string" };
20632
+ }
20633
+ const [, scheme, userinfo, hostPart, databasePart, queryPart] = match;
20634
+ let user = null;
20635
+ let password = null;
20636
+ if (userinfo) {
20637
+ const sepIndex = userinfo.indexOf(":");
20638
+ if (sepIndex === -1) {
20639
+ user = decodeURIComponent(userinfo);
20640
+ } else {
20641
+ user = decodeURIComponent(userinfo.slice(0, sepIndex));
20642
+ password = decodeURIComponent(userinfo.slice(sepIndex + 1));
20643
+ }
20644
+ }
20645
+ const hosts = hostPart ? hostPart.split(",").filter(Boolean).map(_parseConnectionHost) : [];
20646
+ const database = databasePart ? decodeURIComponent(databasePart) : null;
20647
+ const params = {};
20648
+ if (queryPart) {
20649
+ for (const pair of queryPart.split("&")) {
20650
+ if (!pair) continue;
20651
+ const eqIndex = pair.indexOf("=");
20652
+ const key = eqIndex === -1 ? pair : pair.slice(0, eqIndex);
20653
+ const value = eqIndex === -1 ? "" : pair.slice(eqIndex + 1);
20654
+ params[decodeURIComponent(key)] = decodeURIComponent(value);
20655
+ }
20656
+ }
20657
+ return { scheme, user, password, hosts, database, params };
20658
+ }
20659
+ var KNOWN_LANGUAGE_TAGS = /* @__PURE__ */ new Set([
20660
+ "js",
20661
+ "jsx",
20662
+ "mjs",
20663
+ "cjs",
20664
+ "javascript",
20665
+ "ts",
20666
+ "tsx",
20667
+ "typescript",
20668
+ "json",
20669
+ "json5",
20670
+ "jsonc",
20671
+ "jsonl",
20672
+ "ndjson",
20673
+ "yaml",
20674
+ "yml",
20675
+ "toml",
20676
+ "ini",
20677
+ "cfg",
20678
+ "conf",
20679
+ "properties",
20680
+ "env",
20681
+ "dotenv",
20682
+ "html",
20683
+ "htm",
20684
+ "xml",
20685
+ "svg",
20686
+ "xhtml",
20687
+ "css",
20688
+ "scss",
20689
+ "sass",
20690
+ "less",
20691
+ "stylus",
20692
+ "styl",
20693
+ "markdown",
20694
+ "md",
20695
+ "mdx",
20696
+ "bash",
20697
+ "sh",
20698
+ "shell",
20699
+ "zsh",
20700
+ "fish",
20701
+ "console",
20702
+ "powershell",
20703
+ "ps1",
20704
+ "bat",
20705
+ "cmd",
20706
+ "python",
20707
+ "py",
20708
+ "py3",
20709
+ "ipynb",
20710
+ "ruby",
20711
+ "rb",
20712
+ "erb",
20713
+ "php",
20714
+ "java",
20715
+ "kotlin",
20716
+ "kt",
20717
+ "kts",
20718
+ "groovy",
20719
+ "gradle",
20720
+ "swift",
20721
+ "objectivec",
20722
+ "objc",
20723
+ "go",
20724
+ "golang",
20725
+ "rust",
20726
+ "rs",
20727
+ "c",
20728
+ "h",
20729
+ "cpp",
20730
+ "cc",
20731
+ "cxx",
20732
+ "hpp",
20733
+ "c++",
20734
+ "csharp",
20735
+ "cs",
20736
+ "fsharp",
20737
+ "fs",
20738
+ "perl",
20739
+ "pl",
20740
+ "lua",
20741
+ "r",
20742
+ "matlab",
20743
+ "m",
20744
+ "scala",
20745
+ "nim",
20746
+ "zig",
20747
+ "julia",
20748
+ "jl",
20749
+ "haskell",
20750
+ "hs",
20751
+ "elixir",
20752
+ "ex",
20753
+ "exs",
20754
+ "erlang",
20755
+ "erl",
20756
+ "clojure",
20757
+ "clj",
20758
+ "cljs",
20759
+ "dart",
20760
+ "ocaml",
20761
+ "ml",
20762
+ "sql",
20763
+ "mysql",
20764
+ "postgresql",
20765
+ "plsql",
20766
+ "sqlite",
20767
+ "graphql",
20768
+ "gql",
20769
+ "dockerfile",
20770
+ "docker",
20771
+ "makefile",
20772
+ "make",
20773
+ "cmake",
20774
+ "nginx",
20775
+ "apache",
20776
+ "diff",
20777
+ "patch",
20778
+ "git",
20779
+ "http",
20780
+ "proto",
20781
+ "protobuf",
20782
+ "csv",
20783
+ "tsv",
20784
+ "vim",
20785
+ "viml",
20786
+ "tex",
20787
+ "latex",
20788
+ "bibtex",
20789
+ "plaintext",
20790
+ "text",
20791
+ "txt",
20792
+ "nohighlight",
20793
+ "none",
20794
+ "asciidoc",
20795
+ "adoc",
20796
+ "rst",
20797
+ "vue",
20798
+ "svelte",
20799
+ "astro",
20800
+ "wasm",
20801
+ "wat",
20802
+ "handlebars",
20803
+ "hbs",
20804
+ "pug",
20805
+ "jade",
20806
+ "coffee",
20807
+ "coffeescript",
20808
+ "actionscript",
20809
+ "terraform",
20810
+ "tf",
20811
+ "hcl",
20812
+ "puppet",
20813
+ "ansible"
20814
+ ]);
20815
+ function _parseFenceLine(line) {
20816
+ const match = line.match(/^( {0,3})(`{3,}|~{3,})(.*)$/);
20817
+ if (!match) return null;
20818
+ const [, indent, marker, rest] = match;
20819
+ const char = marker[0];
20820
+ if (char === "`" && rest.includes("`")) return null;
20821
+ return { indent: indent.length, char, length: marker.length, infoString: rest.trim() };
20822
+ }
20823
+ function _isClosingFence(line, fenceChar, fenceLength) {
20824
+ const match = line.match(/^ {0,3}(`+|~+)\s*$/);
20825
+ if (!match) return false;
20826
+ const marker = match[1];
20827
+ return marker[0] === fenceChar && marker.length >= fenceLength;
20828
+ }
20829
+ function validateFenceLanguageTags(markdown) {
20830
+ const lines = markdown.split("\n");
20831
+ const issues = [];
20832
+ let totalFences = 0;
20833
+ let open = null;
20834
+ for (let i = 0; i < lines.length; i++) {
20835
+ const lineNumber = i + 1;
20836
+ const line = lines[i];
20837
+ if (open) {
20838
+ if (_isClosingFence(line, open.char, open.length)) open = null;
20839
+ continue;
20840
+ }
20841
+ const fence = _parseFenceLine(line);
20842
+ if (!fence) continue;
20843
+ totalFences++;
20844
+ const tag = fence.infoString.split(/\s+/)[0] ?? "";
20845
+ open = { char: fence.char, length: fence.length };
20846
+ if (tag === "") {
20847
+ issues.push({ line: lineNumber, tag, issue: "missing" });
20848
+ continue;
20849
+ }
20850
+ const lower = tag.toLowerCase();
20851
+ if (!KNOWN_LANGUAGE_TAGS.has(lower)) {
20852
+ issues.push({ line: lineNumber, tag, issue: "unknown" });
20853
+ continue;
20854
+ }
20855
+ if (tag !== lower) {
20856
+ issues.push({ line: lineNumber, tag, issue: "inconsistent-case", suggestion: lower });
20857
+ }
20858
+ }
20859
+ return { totalFences, issues };
20860
+ }
20861
+ var _IDENT_START = /[A-Za-z_]/;
20862
+ var _IDENT_CHAR = /[A-Za-z0-9_]/;
20863
+ function _readIdentifier(sql, start) {
20864
+ let end = start;
20865
+ while (end < sql.length && _IDENT_CHAR.test(sql[end])) end++;
20866
+ return sql.slice(start, end);
20867
+ }
20868
+ function countSqlPlaceholders(sql) {
20869
+ const placeholders = [];
20870
+ let state = "normal";
20871
+ let i = 0;
20872
+ while (i < sql.length) {
20873
+ const ch = sql[i];
20874
+ const next = sql[i + 1];
20875
+ if (state === "single") {
20876
+ if (ch === "'" && next === "'") {
20877
+ i += 2;
20878
+ continue;
20879
+ }
20880
+ if (ch === "'") {
20881
+ state = "normal";
20882
+ i++;
20883
+ continue;
20884
+ }
20885
+ i++;
20886
+ continue;
20887
+ }
20888
+ if (state === "double") {
20889
+ if (ch === '"' && next === '"') {
20890
+ i += 2;
20891
+ continue;
20892
+ }
20893
+ if (ch === '"') {
20894
+ state = "normal";
20895
+ i++;
20896
+ continue;
20897
+ }
20898
+ i++;
20899
+ continue;
20900
+ }
20901
+ if (state === "line-comment") {
20902
+ if (ch === "\n") state = "normal";
20903
+ i++;
20904
+ continue;
20905
+ }
20906
+ if (state === "block-comment") {
20907
+ if (ch === "*" && next === "/") {
20908
+ state = "normal";
20909
+ i += 2;
20910
+ continue;
20911
+ }
20912
+ i++;
20913
+ continue;
20914
+ }
20915
+ if (ch === "'") {
20916
+ state = "single";
20917
+ i++;
20918
+ continue;
20919
+ }
20920
+ if (ch === '"') {
20921
+ state = "double";
20922
+ i++;
20923
+ continue;
20924
+ }
20925
+ if (ch === "-" && next === "-") {
20926
+ state = "line-comment";
20927
+ i += 2;
20928
+ continue;
20929
+ }
20930
+ if (ch === "/" && next === "*") {
20931
+ state = "block-comment";
20932
+ i += 2;
20933
+ continue;
20934
+ }
20935
+ if (ch === "?") {
20936
+ placeholders.push({ style: "anonymous", raw: "?", index: i });
20937
+ i++;
20938
+ continue;
20939
+ }
20940
+ if (ch === "$" && /[0-9]/.test(next ?? "")) {
20941
+ let end = i + 1;
20942
+ while (end < sql.length && /[0-9]/.test(sql[end])) end++;
20943
+ const raw = sql.slice(i, end);
20944
+ placeholders.push({ style: "numbered", raw, index: i, number: parseInt(raw.slice(1), 10) });
20945
+ i = end;
20946
+ continue;
20947
+ }
20948
+ if (ch === ":") {
20949
+ if (next === ":") {
20950
+ i += 2;
20951
+ continue;
20952
+ }
20953
+ if (next && _IDENT_START.test(next)) {
20954
+ const name = _readIdentifier(sql, i + 1);
20955
+ placeholders.push({ style: "named-colon", raw: `:${name}`, index: i, name });
20956
+ i += 1 + name.length;
20957
+ continue;
20958
+ }
20959
+ i++;
20960
+ continue;
20961
+ }
20962
+ if (ch === "@") {
20963
+ if (next === "@") {
20964
+ i += 2;
20965
+ continue;
20966
+ }
20967
+ if (next && _IDENT_START.test(next)) {
20968
+ const name = _readIdentifier(sql, i + 1);
20969
+ placeholders.push({ style: "named-at", raw: `@${name}`, index: i, name });
20970
+ i += 1 + name.length;
20971
+ continue;
20972
+ }
20973
+ i++;
20974
+ continue;
20975
+ }
20976
+ i++;
20977
+ }
20978
+ const counts = { anonymous: 0, numbered: 0, "named-colon": 0, "named-at": 0 };
20979
+ for (const p of placeholders) counts[p.style]++;
20980
+ const stylesUsed = ["anonymous", "numbered", "named-colon", "named-at"].filter((s) => counts[s] > 0);
20981
+ const numbers = placeholders.filter((p) => p.style === "numbered").map((p) => p.number);
20982
+ const maxNumber = numbers.length > 0 ? Math.max(...numbers) : 0;
20983
+ const seen = new Set(numbers);
20984
+ const numberedGaps = [];
20985
+ for (let n = 1; n < maxNumber; n++) {
20986
+ if (!seen.has(n)) numberedGaps.push(n);
20987
+ }
20988
+ const countedMap = /* @__PURE__ */ new Map();
20989
+ for (const n of numbers) countedMap.set(n, (countedMap.get(n) ?? 0) + 1);
20990
+ const numberedDuplicates = [...countedMap.entries()].filter(([, c]) => c > 1).map(([n]) => n).sort((a, b) => a - b);
20991
+ return {
20992
+ placeholders,
20993
+ counts,
20994
+ stylesUsed,
20995
+ mixedStyles: stylesUsed.length > 1,
20996
+ numberedGaps,
20997
+ numberedDuplicates
20998
+ };
20999
+ }
20392
21000
 
20393
21001
  // src/tools/color.ts
20394
21002
  var color_exports = {};
package/dist/index.d.cts CHANGED
@@ -1,4 +1,4 @@
1
- export { j as json } from './json-CaiYsGDQ.cjs';
1
+ export { j as json } from './json-Ca6gZCNB.cjs';
2
2
  export { e as encoding } from './encoding-Dk3wpmb3.cjs';
3
3
  export { h as hashing } from './hashing-CJjlvqS_.cjs';
4
4
  export { t as text } from './text-CNn3whZA.cjs';
@@ -8,7 +8,7 @@ export { t as time } from './time-KqJjdqII.cjs';
8
8
  export { u as units } from './units-D7YRRwei.cjs';
9
9
  export { n as network } from './network-BskZe1n2.cjs';
10
10
  export { a as api } from './api-CQnIUrVB.cjs';
11
- export { c as code } from './code-46xO9xFf.cjs';
11
+ export { c as code } from './code-B8yHwP3m.cjs';
12
12
  export { c as color } from './color-tPwZCr9H.cjs';
13
13
  export { c as css } from './css-Cf7AMGM-.cjs';
14
14
  export { m as misc } from './misc-CA3N198T.cjs';
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- export { j as json } from './json-CaiYsGDQ.js';
1
+ export { j as json } from './json-Ca6gZCNB.js';
2
2
  export { e as encoding } from './encoding-Dk3wpmb3.js';
3
3
  export { h as hashing } from './hashing-CJjlvqS_.js';
4
4
  export { t as text } from './text-CNn3whZA.js';
@@ -8,7 +8,7 @@ export { t as time } from './time-KqJjdqII.js';
8
8
  export { u as units } from './units-D7YRRwei.js';
9
9
  export { n as network } from './network-BskZe1n2.js';
10
10
  export { a as api } from './api-CQnIUrVB.js';
11
- export { c as code } from './code-46xO9xFf.js';
11
+ export { c as code } from './code-B8yHwP3m.js';
12
12
  export { c as color } from './color-tPwZCr9H.js';
13
13
  export { c as css } from './css-Cf7AMGM-.js';
14
14
  export { m as misc } from './misc-CA3N198T.js';
package/dist/index.js CHANGED
@@ -2,12 +2,12 @@ export { media_exports as media } from './chunk-ZWFZRDQ4.js';
2
2
  export { units_exports as units } from './chunk-OFLNVDNX.js';
3
3
  export { network_exports as network } from './chunk-KWS4ZCYG.js';
4
4
  export { api_exports as api } from './chunk-U2HREMZU.js';
5
- export { code_exports as code } from './chunk-XT2BQWXT.js';
5
+ export { code_exports as code } from './chunk-FPFA4ZHC.js';
6
6
  export { color_exports as color } from './chunk-BPVAB4P2.js';
7
7
  export { css_exports as css } from './chunk-6YPV2AB5.js';
8
8
  export { misc_exports as misc } from './chunk-GX7H6TAX.js';
9
9
  export { ai_agent_exports as ai_agent } from './chunk-HJLGUNSO.js';
10
- export { json_exports as json } from './chunk-34C6GXCC.js';
10
+ export { json_exports as json } from './chunk-WUOZHCIC.js';
11
11
  export { encoding_exports as encoding } from './chunk-DOWQZUTP.js';
12
12
  export { hashing_exports as hashing } from './chunk-PET2CGTH.js';
13
13
  export { text_exports as text } from './chunk-QVOK3BXM.js';