@pushary/agent-hooks 1.9.30 → 1.9.31

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 (104) hide show
  1. package/CHANGELOG.md +11 -0
  2. package/data/SKILL.md +46 -12
  3. package/data/cursor-plugin/skills/pushary/SKILL.md +46 -12
  4. package/data/vscode-plugin/skills/pushary/SKILL.md +46 -12
  5. package/dist/bin/pushary-bell-hook.js +26 -26
  6. package/dist/bin/pushary-bell.js +9 -9
  7. package/dist/bin/pushary-claude.js +25 -25
  8. package/dist/bin/pushary-clean.js +29 -29
  9. package/dist/bin/pushary-codex-bridge.js +17 -17
  10. package/dist/bin/pushary-codex-hook.js +31 -31
  11. package/dist/bin/pushary-codex.js +12 -12
  12. package/dist/bin/pushary-connect.js +24 -24
  13. package/dist/bin/pushary-cowork.js +5 -5
  14. package/dist/bin/pushary-daemon.js +33 -33
  15. package/dist/bin/pushary-disconnect.js +24 -24
  16. package/dist/bin/pushary-doctor.js +33 -33
  17. package/dist/bin/pushary-elicitation-hook.js +26 -26
  18. package/dist/bin/pushary-gemini-bridge.js +13 -13
  19. package/dist/bin/pushary-gemini-hook.js +28 -28
  20. package/dist/bin/pushary-hook.js +30 -30
  21. package/dist/bin/pushary-login.js +12 -12
  22. package/dist/bin/pushary-logout.js +24 -24
  23. package/dist/bin/pushary-mcp.js +9 -9
  24. package/dist/bin/pushary-mode.js +12 -12
  25. package/dist/bin/pushary-notification-hook.js +25 -25
  26. package/dist/bin/pushary-opencode-hook.js +27 -27
  27. package/dist/bin/pushary-permission-denied-hook.js +30 -30
  28. package/dist/bin/pushary-permission-hook.js +29 -29
  29. package/dist/bin/pushary-post-hook.js +25 -25
  30. package/dist/bin/pushary-prompt-hook.js +25 -25
  31. package/dist/bin/pushary-session-end-hook.js +25 -25
  32. package/dist/bin/pushary-session-start-hook.js +29 -29
  33. package/dist/bin/pushary-setup.js +35 -35
  34. package/dist/bin/pushary-stats.js +5 -5
  35. package/dist/bin/pushary-status.js +26 -26
  36. package/dist/bin/pushary-stop-hook.js +25 -25
  37. package/dist/bin/pushary-stopfailure-hook.js +25 -25
  38. package/dist/bin/pushary-suggestions.js +12 -12
  39. package/dist/bin/pushary-transcript-register.js +18 -18
  40. package/dist/bin/pushary-transcripts.js +8 -8
  41. package/dist/bin/pushary-upgrade.js +30 -30
  42. package/dist/bin/pushary-wait.js +12 -12
  43. package/dist/bin/pushary.js +6 -6
  44. package/dist/{chunk-SMA7LUCS.js → chunk-2ROXUEZV.js} +1 -1
  45. package/dist/{chunk-DP6FJABB.js → chunk-35RJKPIC.js} +1 -1
  46. package/dist/{chunk-PWQN4D6R.js → chunk-3EIJDBVB.js} +5 -5
  47. package/dist/{chunk-OQ5K6QHU.js → chunk-464FX6W5.js} +5 -5
  48. package/dist/{chunk-Q6HJD6SH.js → chunk-4JOWKPUF.js} +1 -1
  49. package/dist/{chunk-3QKX22ZA.js → chunk-4WGKAGIU.js} +3 -3
  50. package/dist/{chunk-XNKFK27C.js → chunk-5EX2SD5N.js} +1 -1
  51. package/dist/{chunk-VTTHXOCR.js → chunk-5F32ZTWD.js} +2 -2
  52. package/dist/{chunk-DU6UZXGV.js → chunk-5FNE6ZVV.js} +2 -2
  53. package/dist/{chunk-RZTWWE26.js → chunk-5GDNIEL5.js} +1 -1
  54. package/dist/{chunk-E2WJLU5U.js → chunk-7447DYNW.js} +1 -1
  55. package/dist/{chunk-SAGO6JNL.js → chunk-75UCMLT5.js} +1 -1
  56. package/dist/{chunk-NKDK3H3I.js → chunk-77J4RVB2.js} +4 -4
  57. package/dist/{chunk-AO75FKBR.js → chunk-7S4Z36H7.js} +3 -3
  58. package/dist/{chunk-HMA7QQ3P.js → chunk-ALSIMOFS.js} +4 -4
  59. package/dist/{chunk-CI2H3U7O.js → chunk-AXANUGOV.js} +2 -2
  60. package/dist/{chunk-3FIKV3PW.js → chunk-BMUTA66M.js} +11 -11
  61. package/dist/{chunk-6R22H57A.js → chunk-CJCVPCOB.js} +2 -2
  62. package/dist/{chunk-CS5JKDWW.js → chunk-D3TVRNZC.js} +2 -2
  63. package/dist/{chunk-3HTCA4SQ.js → chunk-DP2FAIW6.js} +1 -1
  64. package/dist/{chunk-VTR4VRL2.js → chunk-DWQYCOPI.js} +2 -4
  65. package/dist/{chunk-IMUCTAM2.js → chunk-EPVY3JU3.js} +1 -1
  66. package/dist/{chunk-7JO33ODX.js → chunk-FEICGRNI.js} +3 -3
  67. package/dist/{chunk-OARF7TWF.js → chunk-FGFFUCEL.js} +6 -6
  68. package/dist/{chunk-GFY6XONT.js → chunk-FXJ5SEQT.js} +5 -5
  69. package/dist/{chunk-XZRRYMY2.js → chunk-GROYT52D.js} +4 -4
  70. package/dist/{chunk-JHVSVVHB.js → chunk-GSBOLJZ4.js} +177 -56
  71. package/dist/{chunk-2VQULZ4L.js → chunk-H2PQXK26.js} +2 -2
  72. package/dist/{chunk-S6J3A4DF.js → chunk-IDGESFKZ.js} +1 -1
  73. package/dist/{chunk-GSMB7FWI.js → chunk-IIP4LEO3.js} +7 -7
  74. package/dist/{chunk-LD3A63IE.js → chunk-IKJJB4QG.js} +3 -3
  75. package/dist/{chunk-KRZECDHA.js → chunk-KBRKQMCI.js} +2 -2
  76. package/dist/{chunk-J3HI2SRD.js → chunk-MG523AVN.js} +1 -1
  77. package/dist/{chunk-434NFCK2.js → chunk-MRR4NQ3H.js} +1 -1
  78. package/dist/{chunk-V2FRBKMP.js → chunk-N4LLBUU2.js} +2 -2
  79. package/dist/{chunk-6DJBVMTR.js → chunk-NTWTU6FA.js} +1 -1
  80. package/dist/{chunk-2OIGS4P2.js → chunk-OS6AE2MR.js} +3 -3
  81. package/dist/{chunk-MTPE6BW7.js → chunk-OSUAY4SA.js} +1 -1
  82. package/dist/{chunk-SM4P6VIY.js → chunk-OTDRNEED.js} +1 -1
  83. package/dist/{chunk-EDEEITT3.js → chunk-OULHOX5C.js} +5 -5
  84. package/dist/{chunk-PGFLQXW5.js → chunk-Q2GSTQ3R.js} +2 -2
  85. package/dist/{chunk-SMAY3CGD.js → chunk-Q7H2IMJQ.js} +2 -2
  86. package/dist/{chunk-ZLKJHXSC.js → chunk-QCOE42GO.js} +4 -4
  87. package/dist/{chunk-H7HRHS3M.js → chunk-QGCEQGH6.js} +4 -4
  88. package/dist/{chunk-KHYUAZPL.js → chunk-RN3KZDWP.js} +2 -2
  89. package/dist/{chunk-KT4SP73I.js → chunk-SAHD5DYW.js} +4 -4
  90. package/dist/{chunk-4GIGQIRN.js → chunk-SJJA2GPD.js} +2 -2
  91. package/dist/{chunk-T4KXYKDL.js → chunk-SQIZGUAN.js} +5 -5
  92. package/dist/{chunk-2QEW5FJK.js → chunk-SRRJLA24.js} +4 -4
  93. package/dist/{chunk-XKSAXKRY.js → chunk-SYUHM6V3.js} +3 -3
  94. package/dist/{chunk-JBVKA3UR.js → chunk-TDLEFGAM.js} +707 -101
  95. package/dist/{chunk-QYD5TN2J.js → chunk-VFNYTVTJ.js} +5 -5
  96. package/dist/{chunk-XLNSQLTV.js → chunk-X427XA76.js} +8 -8
  97. package/dist/{chunk-YZPCDR32.js → chunk-X5HK4XUN.js} +4 -4
  98. package/dist/{chunk-MYTWZ33A.js → chunk-ZYDSHR5P.js} +3 -3
  99. package/dist/{global-upgrade-JDZPAQ6B.js → global-upgrade-YMBTZHDP.js} +6 -6
  100. package/dist/{paths-4QBYMQHK.js → paths-BPFRUWMB.js} +2 -2
  101. package/dist/{reapply-26GMHUWI.js → reapply-ZC2LSUVZ.js} +20 -20
  102. package/dist/src/index.js +19 -19
  103. package/dist/{upgrade-lock-DIRCINDI.js → upgrade-lock-TTZMLZPB.js} +3 -3
  104. package/package.json +1 -1
@@ -1750,6 +1750,428 @@ var powerShellCommandHasAVisibleConsequence = (command, judge) => {
1750
1750
  return powerShellReadingIsDestructive(reading, judge) || stages.some((stage) => stageHasAVisibleConsequence(stage, judge)) || reading.statements.some(listsRecursivelyIntoARemoval) || runsFetchedPowerShellCode(stages, judge) || runsADownloadedFile(stages, judge) || reading.posixCommands.some((words) => judge.commandShowsAConsequence(words));
1751
1751
  };
1752
1752
 
1753
+ // ../contracts/src/command-analysis/sql-text.ts
1754
+ var UNCERTAIN_SQL = { kind: "uncertain" };
1755
+ var STRING_PLACEHOLDER = "''";
1756
+ var TOKEN_GAP = " ";
1757
+ var STATEMENT_SEPARATOR2 = ";";
1758
+ var SINGLE_QUOTE = "'";
1759
+ var DOUBLE_QUOTE = '"';
1760
+ var BACKTICK = "`";
1761
+ var BACKSLASH = "\\";
1762
+ var DOLLAR = "$";
1763
+ var DASH_DASH = "--";
1764
+ var HASH = "#";
1765
+ var BLOCK_COMMENT_OPEN2 = "/*";
1766
+ var BLOCK_COMMENT_CLOSE2 = "*/";
1767
+ var NEWLINE2 = "\n";
1768
+ var CARRIAGE_RETURN2 = "\r";
1769
+ var TRIPLE_QUOTE_LENGTH = 3;
1770
+ var CLIENT_COMMAND_LENGTH = 2;
1771
+ var UNICODE_ESCAPE_PREFIX = /^[uU]&$/;
1772
+ var ESCAPE_STRING_PREFIX = /^[eE]$/;
1773
+ var EXECUTABLE_COMMENT_OPENER = /^\/\*M?!/;
1774
+ var ASCII_LETTER_OR_UNDERSCORE = /^[A-Za-z_]$/;
1775
+ var DECIMAL_DIGIT = /^[0-9]$/;
1776
+ var DECIMAL_DIGITS = /^[0-9]+$/;
1777
+ var ANY_WHITESPACE = /^\s$/;
1778
+ var STATEMENT_TERMINATOR_CLIENT_COMMAND = /^\\[gG]$/;
1779
+ var SQL_MODE_SETTING = /\bsql_mode\b/i;
1780
+ var FIRST_NON_ASCII = "\x80";
1781
+ var FIRST_NON_ASCII_CODE = 128;
1782
+ var LAST_ASCII_CONTROL_OR_SPACE = 32;
1783
+ var ASCII_DELETE = 127;
1784
+ var MYSQL_WHITESPACE = /* @__PURE__ */ new Set([" ", " ", "\n", "\v", "\f", "\r"]);
1785
+ var ESCAPE_STRING_SYNTAX = { backslashes: "escape", content: "hidden" };
1786
+ var isIdentifierStart = (character) => ASCII_LETTER_OR_UNDERSCORE.test(character) || character >= FIRST_NON_ASCII;
1787
+ var isDecimalDigit = (character) => DECIMAL_DIGIT.test(character);
1788
+ var isWordCharacter = (character) => isIdentifierStart(character) || isDecimalDigit(character);
1789
+ var isIdentifierPart = (character) => isWordCharacter(character) || character === DOLLAR;
1790
+ var isQuote = (character) => character === SINGLE_QUOTE || character === DOUBLE_QUOTE || character === BACKTICK;
1791
+ var isLineCommentTerminator = (character) => character === NEWLINE2 || character === CARRIAGE_RETURN2;
1792
+ var isControlOrSpace = (character) => {
1793
+ const code = character.charCodeAt(0);
1794
+ return code <= LAST_ASCII_CONTROL_OR_SPACE || code === ASCII_DELETE;
1795
+ };
1796
+ var followsNonAsciiText = (source, index) => source.charCodeAt(index - 1) >= FIRST_NON_ASCII_CODE;
1797
+ var mayBeAMultibyteTrailByte = (source, index, lexicon) => lexicon.clientCharsets === "may-be-multibyte" && followsNonAsciiText(source, index);
1798
+ var endOfRun = (source, start, belongs) => {
1799
+ let index = start;
1800
+ while (index < source.length && belongs(source.charAt(index))) index += 1;
1801
+ return index;
1802
+ };
1803
+ var dollarQuoteDelimiterAt = (source, start) => {
1804
+ if (source.charAt(start) !== DOLLAR) return void 0;
1805
+ const tagStart = start + 1;
1806
+ const tagEnd = isIdentifierStart(source.charAt(tagStart)) ? endOfRun(source, tagStart, isWordCharacter) : tagStart;
1807
+ return source.charAt(tagEnd) === DOLLAR ? source.slice(start, tagEnd + 1) : void 0;
1808
+ };
1809
+ var doubledQuoteEnd = (source, from, quote, backslashBeforeTheQuote) => {
1810
+ for (let index = from; index < source.length; index += 1) {
1811
+ if (backslashBeforeTheQuote === "uncertain" && source[index] === BACKSLASH && source[index + 1] === quote) return "uncertain";
1812
+ if (source[index] !== quote) continue;
1813
+ if (source[index + 1] === quote) index += 1;
1814
+ else return index + 1;
1815
+ }
1816
+ return "unterminated";
1817
+ };
1818
+ var escapedQuoteEnd = (source, from, closing, lexicon) => {
1819
+ for (let index = from; index < source.length; ) {
1820
+ if (source[index] === BACKSLASH) {
1821
+ if (mayBeAMultibyteTrailByte(source, index, lexicon)) return "uncertain";
1822
+ index += 2;
1823
+ } else if (!source.startsWith(closing, index)) {
1824
+ index += 1;
1825
+ } else if (closing.length === 1 && source[index + 1] === closing) {
1826
+ index += 2;
1827
+ } else {
1828
+ return index + closing.length;
1829
+ }
1830
+ }
1831
+ return "unterminated";
1832
+ };
1833
+ var blockCommentEnd = (source, start, lexicon) => {
1834
+ let depth = 0;
1835
+ let index = start + BLOCK_COMMENT_OPEN2.length;
1836
+ while (index < source.length) {
1837
+ if (source.startsWith(BLOCK_COMMENT_OPEN2, index)) {
1838
+ if (lexicon.nestedBlockComments === "uncertain") return "uncertain";
1839
+ depth += 1;
1840
+ index += BLOCK_COMMENT_OPEN2.length;
1841
+ } else if (!source.startsWith(BLOCK_COMMENT_CLOSE2, index)) {
1842
+ index += 1;
1843
+ } else if (depth === 0) {
1844
+ return index + BLOCK_COMMENT_CLOSE2.length;
1845
+ } else {
1846
+ depth -= 1;
1847
+ index += BLOCK_COMMENT_CLOSE2.length;
1848
+ }
1849
+ }
1850
+ return "uncertain";
1851
+ };
1852
+ var opensAnEscapeString = (source, start, lexicon) => lexicon.escapeStringPrefix === "backslash-escapes" && source.charAt(start) === SINGLE_QUOTE && ESCAPE_STRING_PREFIX.test(source.charAt(start - 1)) && !isIdentifierPart(source.charAt(start - 2));
1853
+ var quotedTextSyntaxOf = (quote, lexicon) => {
1854
+ if (quote === SINGLE_QUOTE) return lexicon.singleQuotes;
1855
+ if (quote === DOUBLE_QUOTE) return lexicon.doubleQuotes;
1856
+ return lexicon.backticks;
1857
+ };
1858
+ var syntaxOfQuoteAt = (source, start, lexicon) => opensAnEscapeString(source, start, lexicon) ? ESCAPE_STRING_SYNTAX : quotedTextSyntaxOf(source.charAt(start), lexicon);
1859
+ var openerOfQuoteAt = (source, start, lexicon) => {
1860
+ const triple = source.charAt(start).repeat(TRIPLE_QUOTE_LENGTH);
1861
+ return lexicon.tripleQuotes === "quote" && source.startsWith(triple, start) ? triple : source.charAt(start);
1862
+ };
1863
+ var readsBackslashesLiterally = (syntax, reading) => syntax.backslashes === "escape-unless-the-sql-mode-disables-it" && reading.backslashMode === "literal";
1864
+ var quotedTextEnd = (source, start, opener, syntax, reading) => {
1865
+ const from = start + opener.length;
1866
+ if (opener.length > 1) return escapedQuoteEnd(source, from, opener, reading.lexicon);
1867
+ const end = doubledQuoteEnd(source, from, opener, "uncertain");
1868
+ if (end !== "uncertain" || syntax.backslashes === "uncertain-before-the-quote") return end;
1869
+ return readsBackslashesLiterally(syntax, reading) ? doubledQuoteEnd(source, from, opener, "ordinary") : escapedQuoteEnd(source, from, opener, reading.lexicon);
1870
+ };
1871
+ var opensAUnicodeEscapedQuote = (source, start) => source.charAt(start) !== SINGLE_QUOTE && UNICODE_ESCAPE_PREFIX.test(source.slice(Math.max(0, start - 2), start));
1872
+ var swallowsABacktick = (source, start, end, lexicon) => {
1873
+ if (source.charAt(start) !== BACKTICK) return false;
1874
+ for (let index = start; index !== -1 && index < end; index = source.indexOf(BACKTICK, index + 1)) {
1875
+ if (mayBeAMultibyteTrailByte(source, index, lexicon)) return true;
1876
+ }
1877
+ return false;
1878
+ };
1879
+ var unterminatedTextRunsToTheEnd = (reading) => reading.backslashMode === "literal";
1880
+ var quotedToken = (source, start, reading, inside) => {
1881
+ if (opensAUnicodeEscapedQuote(source, start)) return "uncertain";
1882
+ const syntax = syntaxOfQuoteAt(source, start, reading.lexicon);
1883
+ const opener = openerOfQuoteAt(source, start, reading.lexicon);
1884
+ const end = quotedTextEnd(source, start, opener, syntax, reading);
1885
+ if (end === "uncertain") return "uncertain";
1886
+ if (end === "unterminated") {
1887
+ return unterminatedTextRunsToTheEnd(reading) ? { text: STRING_PLACEHOLDER, end: source.length, insideExecutableComment: inside } : "uncertain";
1888
+ }
1889
+ if (swallowsABacktick(source, start, end, reading.lexicon)) return "uncertain";
1890
+ const quote = source.charAt(start);
1891
+ const text = syntax.content === "hidden" ? STRING_PLACEHOLDER : source.slice(start + opener.length, end - opener.length).replaceAll(quote + quote, quote);
1892
+ return { text, end, insideExecutableComment: inside };
1893
+ };
1894
+ var lineCommentEnd = (source, start, lexicon) => {
1895
+ const terminator = endOfRun(source, start, (character) => !isLineCommentTerminator(character));
1896
+ if (source.charAt(terminator) !== CARRIAGE_RETURN2) return terminator;
1897
+ if (lexicon.carriageReturnInLineComment === "uncertain") return "uncertain";
1898
+ if (lexicon.carriageReturnInLineComment === "ends-the-comment") return terminator;
1899
+ const newline = source.indexOf(NEWLINE2, terminator);
1900
+ return newline === -1 ? source.length : newline;
1901
+ };
1902
+ var lineCommentToken = (source, start, lexicon, inside) => {
1903
+ if (inside) return "uncertain";
1904
+ const end = lineCommentEnd(source, start, lexicon);
1905
+ return end === "uncertain" ? "uncertain" : { text: TOKEN_GAP, end, insideExecutableComment: false };
1906
+ };
1907
+ var dashDashStartsAComment = (next, lexicon) => {
1908
+ if (lexicon.dashDash === "comment" || next === "") return true;
1909
+ if (lexicon.dashDash === "uncertain-before-text") return ANY_WHITESPACE.test(next) || "uncertain";
1910
+ if (MYSQL_WHITESPACE.has(next)) return true;
1911
+ return isControlOrSpace(next) ? "uncertain" : false;
1912
+ };
1913
+ var dashDashToken = (source, start, lexicon, inside) => {
1914
+ const startsAComment = dashDashStartsAComment(source.charAt(start + DASH_DASH.length), lexicon);
1915
+ if (startsAComment === "uncertain") return "uncertain";
1916
+ return startsAComment ? lineCommentToken(source, start, lexicon, inside) : { text: source.charAt(start), end: start + 1, insideExecutableComment: inside };
1917
+ };
1918
+ var hashToken = (source, start, lexicon, inside) => {
1919
+ if (lexicon.hash === "uncertain") return "uncertain";
1920
+ if (lexicon.hash === "comment") return lineCommentToken(source, start, lexicon, inside);
1921
+ return { text: HASH, end: start + 1, insideExecutableComment: inside };
1922
+ };
1923
+ var blockCommentToken = (source, start, lexicon, inside) => {
1924
+ if (inside) return "uncertain";
1925
+ const opener = EXECUTABLE_COMMENT_OPENER.exec(source.slice(start, start + 4))?.[0];
1926
+ if (opener !== void 0 && lexicon.executableComments === "uncertain") return "uncertain";
1927
+ if (opener !== void 0) {
1928
+ return { text: TOKEN_GAP, end: endOfRun(source, start + opener.length, isDecimalDigit), insideExecutableComment: true };
1929
+ }
1930
+ const end = blockCommentEnd(source, start, lexicon);
1931
+ return end === "uncertain" ? "uncertain" : { text: TOKEN_GAP, end, insideExecutableComment: false };
1932
+ };
1933
+ var dollarToken = (source, start, lexicon, inside) => {
1934
+ const delimiter = dollarQuoteDelimiterAt(source, start);
1935
+ if (delimiter === void 0) return { text: DOLLAR, end: start + 1, insideExecutableComment: inside };
1936
+ if (lexicon.dollarQuotes === "uncertain") return "uncertain";
1937
+ const close = source.indexOf(delimiter, start + delimiter.length);
1938
+ return close === -1 ? "uncertain" : { text: delimiter + delimiter, end: close + delimiter.length, insideExecutableComment: inside };
1939
+ };
1940
+ var numberToken = (source, start, inside) => {
1941
+ const end = endOfRun(source, start, isWordCharacter);
1942
+ const text = source.slice(start, end);
1943
+ if (!DECIMAL_DIGITS.test(text) && dollarQuoteDelimiterAt(source, end) !== void 0) return "uncertain";
1944
+ return { text, end, insideExecutableComment: inside };
1945
+ };
1946
+ var identifierToken = (source, start, inside) => {
1947
+ const end = endOfRun(source, start, isIdentifierPart);
1948
+ return { text: source.slice(start, end), end, insideExecutableComment: inside };
1949
+ };
1950
+ var clientCommandToken = (source, start, inside) => {
1951
+ const command = source.slice(start, start + CLIENT_COMMAND_LENGTH);
1952
+ return STATEMENT_TERMINATOR_CLIENT_COMMAND.test(command) ? { text: STATEMENT_SEPARATOR2, end: start + CLIENT_COMMAND_LENGTH, insideExecutableComment: inside } : "uncertain";
1953
+ };
1954
+ var nextSqlToken = (source, start, reading, inside) => {
1955
+ const { lexicon } = reading;
1956
+ const character = source.charAt(start);
1957
+ if (isQuote(character)) return quotedToken(source, start, reading, inside);
1958
+ if (source.startsWith(DASH_DASH, start)) return dashDashToken(source, start, lexicon, inside);
1959
+ if (character === HASH) return hashToken(source, start, lexicon, inside);
1960
+ if (source.startsWith(BLOCK_COMMENT_OPEN2, start)) return blockCommentToken(source, start, lexicon, inside);
1961
+ if (inside && source.startsWith(BLOCK_COMMENT_CLOSE2, start)) {
1962
+ return { text: TOKEN_GAP, end: start + BLOCK_COMMENT_CLOSE2.length, insideExecutableComment: false };
1963
+ }
1964
+ if (character === BACKSLASH && lexicon.backslashOutsideLiterals === "client-command") return clientCommandToken(source, start, inside);
1965
+ if (character === DOLLAR) return dollarToken(source, start, lexicon, inside);
1966
+ if (isIdentifierStart(character)) return identifierToken(source, start, inside);
1967
+ if (isDecimalDigit(character)) return numberToken(source, start, inside);
1968
+ return { text: character, end: start + 1, insideExecutableComment: inside };
1969
+ };
1970
+ var readsABackslashTheSqlModeDecides = (source, start, end, lexicon) => isQuote(source.charAt(start)) && syntaxOfQuoteAt(source, start, lexicon).backslashes === "escape-unless-the-sql-mode-disables-it" && source.slice(start, end).includes(BACKSLASH);
1971
+ var sqlReadingOf = (source, reading) => {
1972
+ const pieces = [];
1973
+ let inside = false;
1974
+ let backslashModeMatters = false;
1975
+ for (let index = 0; index < source.length; ) {
1976
+ const token = nextSqlToken(source, index, reading, inside);
1977
+ if (token === "uncertain") return "uncertain";
1978
+ backslashModeMatters ||= readsABackslashTheSqlModeDecides(source, index, token.end, reading.lexicon);
1979
+ pieces.push(token.text);
1980
+ inside = token.insideExecutableComment;
1981
+ index = token.end;
1982
+ }
1983
+ return inside ? "uncertain" : { text: pieces.join(""), backslashModeMatters };
1984
+ };
1985
+ var sqlModeDecidesBackslashes = (lexicon) => [lexicon.singleQuotes, lexicon.doubleQuotes, lexicon.backticks].some((syntax) => syntax.backslashes === "escape-unless-the-sql-mode-disables-it");
1986
+ var backslashModesOf = (lexicon) => sqlModeDecidesBackslashes(lexicon) ? ["escape", "literal"] : ["escape"];
1987
+ var isReadingText = (result) => result !== "uncertain";
1988
+ var mayChangeTheBackslashMode = (readings) => readings.some((reading) => reading.backslashModeMatters) && readings.some((reading) => SQL_MODE_SETTING.test(reading.text));
1989
+ var sqlOutsideLiterals = (source, lexicon) => {
1990
+ const results = backslashModesOf(lexicon).map((backslashMode) => sqlReadingOf(source, { lexicon, backslashMode }));
1991
+ const readings = results.filter(isReadingText);
1992
+ if (readings.length < results.length || mayChangeTheBackslashMode(readings)) return UNCERTAIN_SQL;
1993
+ return { kind: "readable", texts: [...new Set(readings.map((reading) => reading.text))] };
1994
+ };
1995
+
1996
+ // ../contracts/src/command-analysis/env-invocation.ts
1997
+ var GNU_ENV = {
1998
+ shortOptions: { switches: /* @__PURE__ */ new Set(["i", "v", "0"]), withAValue: /* @__PURE__ */ new Set(["a", "C", "S", "u"]) },
1999
+ longOptions: [
2000
+ { name: "argv0", argument: "required", effect: "continues" },
2001
+ { name: "ignore-environment", argument: "none", effect: "continues" },
2002
+ { name: "null", argument: "none", effect: "continues" },
2003
+ { name: "unset", argument: "required", effect: "continues" },
2004
+ { name: "chdir", argument: "required", effect: "continues" },
2005
+ { name: "default-signal", argument: "optional", effect: "continues" },
2006
+ { name: "ignore-signal", argument: "optional", effect: "continues" },
2007
+ { name: "block-signal", argument: "optional", effect: "continues" },
2008
+ { name: "list-signal-handling", argument: "none", effect: "continues" },
2009
+ { name: "debug", argument: "none", effect: "continues" },
2010
+ { name: "split-string", argument: "required", effect: "splits" },
2011
+ { name: "help", argument: "none", effect: "exits" },
2012
+ { name: "version", argument: "none", effect: "exits" }
2013
+ ]
2014
+ };
2015
+ var BSD_ENV = {
2016
+ shortOptions: { switches: /* @__PURE__ */ new Set(["-", "i", "v", "0"]), withAValue: /* @__PURE__ */ new Set(["C", "L", "P", "S", "U", "u"]) },
2017
+ longOptions: null
2018
+ };
2019
+ var ENV_FLAVORS = [GNU_ENV, BSD_ENV];
2020
+ var UNREADABLE = { kind: "unreadable" };
2021
+ var RUNS_NOTHING = { kind: "runs-nothing" };
2022
+ var EXITS = { kind: "exits" };
2023
+ var SPLIT_STRING_LETTER = "S";
2024
+ var END_OF_OPTIONS = "--";
2025
+ var LONE_DASH = "-";
2026
+ var OPTION_PREFIX = "-";
2027
+ var NO_CLUSTER = "";
2028
+ var LONG_OPTION_PREFIX = "--";
2029
+ var ASSIGNMENT_SEPARATOR = "=";
2030
+ var nextOption = (next) => ({ kind: "next", next });
2031
+ var finished = (reading) => ({ kind: "done", reading });
2032
+ var commandAfterOptions = (args, firstOperand) => {
2033
+ let start = args[firstOperand]?.text === LONE_DASH ? firstOperand + 1 : firstOperand;
2034
+ while (args[start]?.text.includes(ASSIGNMENT_SEPARATOR)) start += 1;
2035
+ return { kind: "command", start };
2036
+ };
2037
+ var splitReading = (args, index, clusterBefore, attached) => {
2038
+ const word = args[index];
2039
+ const prefix = [...args.slice(0, index).map((arg) => arg.text), ...clusterBefore.length > 1 ? [clusterBefore] : []];
2040
+ if (word !== void 0 && attached !== void 0) return { kind: "split", prefix, value: { ...word, text: attached }, rest: index + 1 };
2041
+ return { kind: "split", prefix, value: args[index + 1], rest: index + 2 };
2042
+ };
2043
+ var requiredValueStep = (args, index) => index + 1 < args.length ? nextOption(index + 2) : finished(EXITS);
2044
+ var shortOptionStep = (args, index, text, options) => {
2045
+ for (let position = 1; position < text.length; position += 1) {
2046
+ const letter = text.charAt(position);
2047
+ if (options.switches.has(letter)) continue;
2048
+ if (!options.withAValue.has(letter)) return finished(EXITS);
2049
+ const attached = text.slice(position + 1);
2050
+ if (letter === SPLIT_STRING_LETTER) return finished(splitReading(args, index, text.slice(0, position), attached === "" ? void 0 : attached));
2051
+ return attached === "" ? requiredValueStep(args, index) : nextOption(index + 1);
2052
+ }
2053
+ return nextOption(index + 1);
2054
+ };
2055
+ var gnuLongOptionAbbreviatedBy = (name, options) => {
2056
+ const exact = options.find((option) => option.name === name);
2057
+ if (exact !== void 0) return exact;
2058
+ const candidates = options.filter((option) => option.name.startsWith(name));
2059
+ return candidates.length === 1 ? candidates[0] : void 0;
2060
+ };
2061
+ var longOptionStep = (args, index, text, options) => {
2062
+ const body = text.slice(LONG_OPTION_PREFIX.length);
2063
+ const separator = body.indexOf(ASSIGNMENT_SEPARATOR);
2064
+ const attached = separator === -1 ? void 0 : body.slice(separator + 1);
2065
+ const option = gnuLongOptionAbbreviatedBy(separator === -1 ? body : body.slice(0, separator), options);
2066
+ if (option === void 0) return finished(UNREADABLE);
2067
+ if (option.effect === "exits" || option.argument === "none" && attached !== void 0) return finished(EXITS);
2068
+ if (option.effect === "splits") return finished(splitReading(args, index, NO_CLUSTER, attached));
2069
+ return option.argument === "required" && attached === void 0 ? requiredValueStep(args, index) : nextOption(index + 1);
2070
+ };
2071
+ var optionStep = (args, index, word, flavor) => {
2072
+ if (word.expands) return finished(UNREADABLE);
2073
+ if (flavor.longOptions !== null && word.text.startsWith(LONG_OPTION_PREFIX)) return longOptionStep(args, index, word.text, flavor.longOptions);
2074
+ return shortOptionStep(args, index, word.text, flavor.shortOptions);
2075
+ };
2076
+ var flavorReadingOf = (args, flavor) => {
2077
+ for (let index = 0; index < args.length; ) {
2078
+ const word = args[index];
2079
+ if (word === void 0) break;
2080
+ if (word.text === END_OF_OPTIONS) return commandAfterOptions(args, index + 1);
2081
+ if (word.text === LONE_DASH || !word.text.startsWith(OPTION_PREFIX)) return commandAfterOptions(args, index);
2082
+ const step = optionStep(args, index, word, flavor);
2083
+ if (step.kind === "done") return step.reading;
2084
+ index = step.next;
2085
+ }
2086
+ return commandAfterOptions(args, args.length);
2087
+ };
2088
+ var runsSomething = (reading) => reading.kind === "command" || reading.kind === "split";
2089
+ var sameEnvReading = (left, right) => {
2090
+ if (left.kind === "command" && right.kind === "command") return left.start === right.start;
2091
+ if (left.kind !== "split" || right.kind !== "split") return false;
2092
+ return left.rest === right.rest && left.prefix.length === right.prefix.length && left.prefix.every((text, position) => text === right.prefix[position]) && left.value?.text === right.value?.text && left.value?.expands === right.value?.expands;
2093
+ };
2094
+ var envReadingOf = (args) => {
2095
+ const readings = ENV_FLAVORS.map((flavor) => flavorReadingOf(args, flavor));
2096
+ if (readings.some((reading) => reading.kind === "unreadable")) return UNREADABLE;
2097
+ const running = readings.filter(runsSomething);
2098
+ const [first, ...others] = running;
2099
+ if (first === void 0) return RUNS_NOTHING;
2100
+ return others.every((other) => sameEnvReading(first, other)) ? first : { kind: "ambiguous", readings: running };
2101
+ };
2102
+
2103
+ // ../contracts/src/command-analysis/shell-command-string.ts
2104
+ var NO_LETTERS = /* @__PURE__ */ new Set();
2105
+ var BASH_OPTIONS = {
2106
+ lettersWithAValue: /* @__PURE__ */ new Set(["o", "O"]),
2107
+ lettersThatEndOptions: NO_LETTERS,
2108
+ leadingLongOptionsWithAValue: /* @__PURE__ */ new Set(["--rcfile", "--init-file", "-rcfile", "-init-file"])
2109
+ };
2110
+ var SHELL_OPTION_SYNTAX = /* @__PURE__ */ new Map([
2111
+ ["sh", BASH_OPTIONS],
2112
+ ["bash", BASH_OPTIONS],
2113
+ ["zsh", { lettersWithAValue: /* @__PURE__ */ new Set(["o"]), lettersThatEndOptions: /* @__PURE__ */ new Set(["b"]), leadingLongOptionsWithAValue: NO_LETTERS }],
2114
+ ["dash", { lettersWithAValue: /* @__PURE__ */ new Set(["o"]), lettersThatEndOptions: NO_LETTERS, leadingLongOptionsWithAValue: NO_LETTERS }],
2115
+ ["ksh", { lettersWithAValue: /* @__PURE__ */ new Set(["o", "R"]), lettersThatEndOptions: NO_LETTERS, leadingLongOptionsWithAValue: NO_LETTERS }]
2116
+ ]);
2117
+ var POSIX_SHELL_PROGRAMS = new Set(SHELL_OPTION_SYNTAX.keys());
2118
+ var ABSENT = { kind: "absent" };
2119
+ var UNREADABLE2 = { kind: "unreadable" };
2120
+ var COMMAND_STRING_LETTER = "c";
2121
+ var END_OF_OPTIONS2 = "--";
2122
+ var LONE_DASH2 = "-";
2123
+ var LONG_OPTION_PREFIX2 = "--";
2124
+ var SHORT_OPTION_CLUSTER = /^[-+][A-Za-z]*$/;
2125
+ var COMMAND_STRING_CLUSTER = /^[-+][A-Za-z]*c[A-Za-z]*$/;
2126
+ var clusterReadingOf = (cluster, syntax) => {
2127
+ const letters = cluster.slice(1);
2128
+ const valueLetter = [...letters].findIndex((letter) => syntax.lettersWithAValue.has(letter));
2129
+ if (valueLetter !== -1 && valueLetter !== letters.length - 1) return null;
2130
+ return {
2131
+ runsACommandString: letters.includes(COMMAND_STRING_LETTER),
2132
+ takesAValue: valueLetter !== -1,
2133
+ endsOptions: [...letters].some((letter) => syntax.lettersThatEndOptions.has(letter))
2134
+ };
2135
+ };
2136
+ var endsOptionParsing = (text) => text === END_OF_OPTIONS2 || text === LONE_DASH2;
2137
+ var isAnOperand = (text) => !text.startsWith("-") && !text.startsWith("+");
2138
+ var optionValueIsUnreadable = (value) => value === void 0 || value.expands;
2139
+ var shellCommandStringOf = (shell, args) => {
2140
+ const syntax = SHELL_OPTION_SYNTAX.get(shell);
2141
+ if (syntax === void 0 || !args.some((arg) => COMMAND_STRING_CLUSTER.test(arg.text))) return ABSENT;
2142
+ let runsACommandString = false;
2143
+ let seenAShortOption = false;
2144
+ let index = 0;
2145
+ while (index < args.length) {
2146
+ const word = args[index];
2147
+ if (word === void 0 || word.expands) return UNREADABLE2;
2148
+ if (endsOptionParsing(word.text)) {
2149
+ index += 1;
2150
+ break;
2151
+ }
2152
+ if (isAnOperand(word.text)) break;
2153
+ if (!seenAShortOption && syntax.leadingLongOptionsWithAValue.has(word.text)) {
2154
+ if (optionValueIsUnreadable(args[index + 1])) return UNREADABLE2;
2155
+ index += 2;
2156
+ continue;
2157
+ }
2158
+ if (word.text.startsWith(LONG_OPTION_PREFIX2)) {
2159
+ index += 1;
2160
+ continue;
2161
+ }
2162
+ const cluster = SHORT_OPTION_CLUSTER.test(word.text) ? clusterReadingOf(word.text, syntax) : null;
2163
+ if (cluster === null) return UNREADABLE2;
2164
+ if (cluster.takesAValue && optionValueIsUnreadable(args[index + 1])) return UNREADABLE2;
2165
+ seenAShortOption = true;
2166
+ runsACommandString ||= cluster.runsACommandString;
2167
+ index += cluster.takesAValue ? 2 : 1;
2168
+ if (cluster.endsOptions) break;
2169
+ }
2170
+ if (!runsACommandString) return ABSENT;
2171
+ const operand = args[index];
2172
+ return operand === void 0 || operand.expands ? UNREADABLE2 : { kind: "readable", script: operand.text };
2173
+ };
2174
+
1753
2175
  // ../contracts/src/degraded.ts
1754
2176
  var DEGRADED_PREFIX = "[degraded]";
1755
2177
  var degradedPayload = (subsystem, report) => ({
@@ -1762,37 +2184,6 @@ var degradedPayload = (subsystem, report) => ({
1762
2184
  });
1763
2185
  var degradedLine = (subsystem, report) => `${DEGRADED_PREFIX} ${JSON.stringify(degradedPayload(subsystem, report))}`;
1764
2186
 
1765
- // ../contracts/src/setup-wire.ts
1766
- var PAIR_TTL_SECONDS = 900;
1767
- var computerOsOfPlatform = (platform) => {
1768
- switch (platform) {
1769
- case "darwin":
1770
- return "mac";
1771
- case "win32":
1772
- return "windows";
1773
- case "linux":
1774
- return "linux";
1775
- default:
1776
- return null;
1777
- }
1778
- };
1779
- var SETUP_AGENT_CHOICES = [
1780
- "claude_code",
1781
- "codex",
1782
- "gemini_cli",
1783
- "hermes",
1784
- "cursor",
1785
- "vscode",
1786
- "opencode",
1787
- "fx",
1788
- ...COMPATIBLE_AGENT_TYPES,
1789
- "custom"
1790
- ];
1791
- var isComputerAgent = (agent) => agent !== "custom";
1792
- var NO_PAIRING_COMPUTER = { computerName: null, os: null, agents: null };
1793
- var SETUP_CONNECT_MODES = ["app", "browser", "web", "none"];
1794
- var isSetupConnectMode = (value) => typeof value === "string" && SETUP_CONNECT_MODES.includes(value);
1795
-
1796
2187
  // ../contracts/src/observability.ts
1797
2188
  var CLIENT_CONTEXT_HEADERS = {
1798
2189
  surface: "x-pushary-surface",
@@ -1840,6 +2231,37 @@ var AUTH_REJECTION_REASONS = [
1840
2231
  ...AGENT_SITE_REJECTION_REASONS
1841
2232
  ];
1842
2233
 
2234
+ // ../contracts/src/setup-wire.ts
2235
+ var PAIR_TTL_SECONDS = 900;
2236
+ var computerOsOfPlatform = (platform) => {
2237
+ switch (platform) {
2238
+ case "darwin":
2239
+ return "mac";
2240
+ case "win32":
2241
+ return "windows";
2242
+ case "linux":
2243
+ return "linux";
2244
+ default:
2245
+ return null;
2246
+ }
2247
+ };
2248
+ var SETUP_AGENT_CHOICES = [
2249
+ "claude_code",
2250
+ "codex",
2251
+ "gemini_cli",
2252
+ "hermes",
2253
+ "cursor",
2254
+ "vscode",
2255
+ "opencode",
2256
+ "fx",
2257
+ ...COMPATIBLE_AGENT_TYPES,
2258
+ "custom"
2259
+ ];
2260
+ var isComputerAgent = (agent) => agent !== "custom";
2261
+ var NO_PAIRING_COMPUTER = { computerName: null, os: null, agents: null };
2262
+ var SETUP_CONNECT_MODES = ["app", "browser", "web", "none"];
2263
+ var isSetupConnectMode = (value) => typeof value === "string" && SETUP_CONNECT_MODES.includes(value);
2264
+
1843
2265
  // ../contracts/src/declined-agents.ts
1844
2266
  var DECLINED_AGENTS_FILE = "declined-agents.json";
1845
2267
  var DECLINED_AGENTS_VERSION = 1;
@@ -2165,12 +2587,17 @@ var rankWholeOrSegments = (toolName, arg, intent, matches) => {
2165
2587
  const matched = toolName in POLICY_COMMAND_KEYS ? shellSegmentsMatch(arg, intent, matches) : matches(arg);
2166
2588
  return matched ? "prefix" : "none";
2167
2589
  };
2590
+ var argumentOpenIndex = (pattern) => pattern.endsWith(")") ? pattern.indexOf("(") : -1;
2591
+ var patternToolName = (pattern) => {
2592
+ const open = argumentOpenIndex(pattern);
2593
+ return open === -1 ? pattern : pattern.slice(0, open);
2594
+ };
2168
2595
  var matchToolPattern = (pattern, toolName, arg, intent = PATTERN_INTENT.grant) => {
2169
- const open = pattern.indexOf("(");
2170
- if (open === -1 || !pattern.endsWith(")")) {
2596
+ const open = argumentOpenIndex(pattern);
2597
+ if (open === -1) {
2171
2598
  return pattern === toolName ? "tool" : "none";
2172
2599
  }
2173
- if (pattern.slice(0, open) !== toolName || arg === void 0) return "none";
2600
+ if (patternToolName(pattern) !== toolName || arg === void 0) return "none";
2174
2601
  const inner = pattern.slice(open + 1, -1);
2175
2602
  if (inner.endsWith(":*")) {
2176
2603
  const prefix = inner.slice(0, -2);
@@ -2453,7 +2880,7 @@ var uniqFileOperandCount = (args) => {
2453
2880
  if (optionsEnded || !isFlagToken(arg) || arg === STDIN_OPERAND) {
2454
2881
  operands += 1;
2455
2882
  optionsEnded = true;
2456
- } else if (arg === END_OF_OPTIONS) {
2883
+ } else if (arg === END_OF_OPTIONS3) {
2457
2884
  optionsEnded = true;
2458
2885
  } else if (UNIQ_OPTIONS_WITH_A_SEPARATE_VALUE.includes(arg)) {
2459
2886
  index += 1;
@@ -2462,7 +2889,7 @@ var uniqFileOperandCount = (args) => {
2462
2889
  return operands;
2463
2890
  };
2464
2891
  var STDIN_OPERAND = "-";
2465
- var LONG_OPTION_PREFIX = "--";
2892
+ var LONG_OPTION_PREFIX3 = "--";
2466
2893
  var OPTION_VALUE_SEPARATOR = "=";
2467
2894
  var longOptionName = (token) => token.split(OPTION_VALUE_SEPARATOR, 1)[0] ?? token;
2468
2895
  var abbreviatesALongOption = (token, longOptions) => {
@@ -2471,8 +2898,8 @@ var abbreviatesALongOption = (token, longOptions) => {
2471
2898
  };
2472
2899
  var clustersAShortOption = (token, shortOptions) => shortOptions.some((option) => token.slice(1).includes(option.slice(1)));
2473
2900
  var isRefusedOption = (token, options) => {
2474
- if (token === END_OF_OPTIONS || !isFlagToken(token)) return false;
2475
- return token.startsWith(LONG_OPTION_PREFIX) ? abbreviatesALongOption(token, options.long) : clustersAShortOption(token, options.short);
2901
+ if (token === END_OF_OPTIONS3 || !isFlagToken(token)) return false;
2902
+ return token.startsWith(LONG_OPTION_PREFIX3) ? abbreviatesALongOption(token, options.long) : clustersAShortOption(token, options.short);
2476
2903
  };
2477
2904
  var carriesNoRefusedOption = (args, options) => !args.some((arg) => isRefusedOption(arg, options));
2478
2905
  var SED_PRINT_ONLY_SCRIPT = /^(?:\d+|\$)(?:,(?:\d+|\$))?p$/;
@@ -2485,8 +2912,8 @@ var isReadOnlyDate = (args) => args.every((arg) => arg.startsWith(DATE_FORMAT_PR
2485
2912
  var PRINTF_TEXT_CONVERSION = /%(?:%|[-+ #0]*\d*(?:\.\d*)?[bcqs])/g;
2486
2913
  var PRINTF_CONVERSION_START = "%";
2487
2914
  var ARITHMETIC_SAFE_NUMBER = /^[-+]?(?:0[xX][0-9a-fA-F]+|\d+(?:\.\d+)?)$/;
2488
- var printfAssignsNothing = (args) => args[0] === END_OF_OPTIONS || !isFlagToken(args[0] ?? "");
2489
- var printfOperands = (args) => args[0] === END_OF_OPTIONS ? args.slice(1) : args;
2915
+ var printfAssignsNothing = (args) => args[0] === END_OF_OPTIONS3 || !isFlagToken(args[0] ?? "");
2916
+ var printfOperands = (args) => args[0] === END_OF_OPTIONS3 ? args.slice(1) : args;
2490
2917
  var convertsArgumentsOnlyAsText = (format) => !format.replace(PRINTF_TEXT_CONVERSION, "").includes(PRINTF_CONVERSION_START);
2491
2918
  var printfNeverEvaluatesAnArgument = ([format = "", ...values]) => convertsArgumentsOnlyAsText(format) || values.every((value) => ARITHMETIC_SAFE_NUMBER.test(value));
2492
2919
  var isOutputOnlyPrintf = (args) => printfAssignsNothing(args) && printfNeverEvaluatesAnArgument(printfOperands(args));
@@ -2758,7 +3185,7 @@ var SHELL_RESERVED_WORDS = /* @__PURE__ */ new Set([
2758
3185
  "]]"
2759
3186
  ]);
2760
3187
  var HARMLESS_GLOBAL_FLAGS = /* @__PURE__ */ new Set(["--no-pager", "--version", "-v", "-V", "--help", "-h"]);
2761
- var END_OF_OPTIONS = "--";
3188
+ var END_OF_OPTIONS3 = "--";
2762
3189
  var SUBCOMMAND_DEPTH = 3;
2763
3190
  var SHELL_LINE_CONTINUATION = /\\\n/g;
2764
3191
  var invocationOf = (segment) => {
@@ -2770,13 +3197,13 @@ var argsAfterHarmlessGlobalFlags = (args) => {
2770
3197
  return firstMeaningful === -1 ? [] : args.slice(firstMeaningful);
2771
3198
  };
2772
3199
  var subcommandWordsOf = (args) => {
2773
- const endOfOptions = args.findIndex((arg) => arg.text === END_OF_OPTIONS);
3200
+ const endOfOptions = args.findIndex((arg) => arg.text === END_OF_OPTIONS3);
2774
3201
  const options = endOfOptions === -1 ? args : args.slice(0, endOfOptions);
2775
3202
  return options.filter((arg) => !arg.text.startsWith("-")).slice(0, SUBCOMMAND_DEPTH);
2776
3203
  };
2777
3204
  var passesInlineCode = (arg) => {
2778
3205
  if (arg === INLINE_CODE_SUBCOMMAND || arg === STANDARD_INPUT_ARGUMENT || INLINE_CODE_LONG_FLAG.test(arg)) return true;
2779
- if (arg.startsWith(END_OF_OPTIONS)) return false;
3206
+ if (arg.startsWith(END_OF_OPTIONS3)) return false;
2780
3207
  const cluster = SHORT_FLAG_CLUSTER.exec(arg)?.[1] ?? "";
2781
3208
  return [...cluster].some((letter) => INLINE_CODE_SHORT_FLAG_LETTERS.has(letter));
2782
3209
  };
@@ -2804,9 +3231,9 @@ var invocationTextWith = ({ program, args }, wordText) => {
2804
3231
  };
2805
3232
  var normalizedInvocation = (invocation) => invocationTextWith(invocation, (word) => word.text);
2806
3233
  var SHELL_METACHARACTER = /[\s;&|<>()$`\\"'*?[\]#~{}!]/;
2807
- var SINGLE_QUOTE = "'";
3234
+ var SINGLE_QUOTE2 = "'";
2808
3235
  var ESCAPED_SINGLE_QUOTE = `'\\''`;
2809
- var asOneShellWord = (text) => SHELL_METACHARACTER.test(text) ? `${SINGLE_QUOTE}${text.replaceAll(SINGLE_QUOTE, ESCAPED_SINGLE_QUOTE)}${SINGLE_QUOTE}` : text;
3236
+ var asOneShellWord = (text) => SHELL_METACHARACTER.test(text) ? `${SINGLE_QUOTE2}${text.replaceAll(SINGLE_QUOTE2, ESCAPED_SINGLE_QUOTE)}${SINGLE_QUOTE2}` : text;
2810
3237
  var quotedInvocation = (invocation) => invocationTextWith(invocation, (word) => asOneShellWord(word.text));
2811
3238
  var normalizedCommand = (command) => {
2812
3239
  const segments = readableCommandSegments(command);
@@ -2888,19 +3315,99 @@ var changesProduction = (invocation) => {
2888
3315
  const words = wordsOfInvocation(invocation);
2889
3316
  return words.some((word, index) => wordSelectsProduction(word, words[index - 1])) && (deployCliChangesSomething(words) || SCHEMA_CHANGE_WORD.test(normalizedInvocation(invocation)));
2890
3317
  };
2891
- var MYSQL_SYNTAX = { inlineFlags: /* @__PURE__ */ new Set(["-e", "--execute"]), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: false };
2892
- var SQLITE_SYNTAX = { inlineFlags: /* @__PURE__ */ new Set(["-cmd"]), scriptFlags: /* @__PURE__ */ new Set(["-init"]), positionalSql: true };
3318
+ var STRING_WITH_DOUBLED_QUOTES = { backslashes: "uncertain-before-the-quote", content: "hidden" };
3319
+ var IDENTIFIER_WITH_DOUBLED_QUOTES = { backslashes: "uncertain-before-the-quote", content: "shown" };
3320
+ var MYSQL_STRING = { backslashes: "escape-unless-the-sql-mode-disables-it", content: "hidden" };
3321
+ var STRING_WITH_BACKSLASH_ESCAPES = { backslashes: "escape", content: "hidden" };
3322
+ var SHOWN_TEXT_WITH_BACKSLASH_ESCAPES = { backslashes: "escape", content: "shown" };
3323
+ var POSTGRES_LEXICON = {
3324
+ singleQuotes: STRING_WITH_DOUBLED_QUOTES,
3325
+ doubleQuotes: IDENTIFIER_WITH_DOUBLED_QUOTES,
3326
+ backticks: IDENTIFIER_WITH_DOUBLED_QUOTES,
3327
+ tripleQuotes: "absent",
3328
+ escapeStringPrefix: "backslash-escapes",
3329
+ dollarQuotes: "string",
3330
+ dashDash: "comment",
3331
+ carriageReturnInLineComment: "ends-the-comment",
3332
+ hash: "text",
3333
+ executableComments: "uncertain",
3334
+ nestedBlockComments: "nest",
3335
+ backslashOutsideLiterals: "text",
3336
+ clientCharsets: "may-be-multibyte"
3337
+ };
3338
+ var MYSQL_LEXICON = {
3339
+ singleQuotes: MYSQL_STRING,
3340
+ doubleQuotes: STRING_WITH_DOUBLED_QUOTES,
3341
+ backticks: IDENTIFIER_WITH_DOUBLED_QUOTES,
3342
+ tripleQuotes: "absent",
3343
+ escapeStringPrefix: "absent",
3344
+ dollarQuotes: "uncertain",
3345
+ dashDash: "comment-before-whitespace",
3346
+ carriageReturnInLineComment: "stays-in-the-comment",
3347
+ hash: "comment",
3348
+ executableComments: "executed",
3349
+ nestedBlockComments: "uncertain",
3350
+ backslashOutsideLiterals: "client-command",
3351
+ clientCharsets: "may-be-multibyte"
3352
+ };
3353
+ var SQLITE_LEXICON = {
3354
+ singleQuotes: STRING_WITH_DOUBLED_QUOTES,
3355
+ doubleQuotes: IDENTIFIER_WITH_DOUBLED_QUOTES,
3356
+ backticks: IDENTIFIER_WITH_DOUBLED_QUOTES,
3357
+ tripleQuotes: "absent",
3358
+ escapeStringPrefix: "absent",
3359
+ dollarQuotes: "uncertain",
3360
+ dashDash: "comment",
3361
+ carriageReturnInLineComment: "stays-in-the-comment",
3362
+ hash: "text",
3363
+ executableComments: "uncertain",
3364
+ nestedBlockComments: "uncertain",
3365
+ backslashOutsideLiterals: "text",
3366
+ clientCharsets: "unicode"
3367
+ };
3368
+ var GOOGLE_SQL_LEXICON = {
3369
+ singleQuotes: STRING_WITH_BACKSLASH_ESCAPES,
3370
+ doubleQuotes: SHOWN_TEXT_WITH_BACKSLASH_ESCAPES,
3371
+ backticks: SHOWN_TEXT_WITH_BACKSLASH_ESCAPES,
3372
+ tripleQuotes: "quote",
3373
+ escapeStringPrefix: "absent",
3374
+ dollarQuotes: "uncertain",
3375
+ dashDash: "comment",
3376
+ carriageReturnInLineComment: "uncertain",
3377
+ hash: "comment",
3378
+ executableComments: "uncertain",
3379
+ nestedBlockComments: "uncertain",
3380
+ backslashOutsideLiterals: "text",
3381
+ clientCharsets: "unicode"
3382
+ };
3383
+ var UNVERIFIED_SQL_LEXICON = {
3384
+ singleQuotes: STRING_WITH_DOUBLED_QUOTES,
3385
+ doubleQuotes: IDENTIFIER_WITH_DOUBLED_QUOTES,
3386
+ backticks: IDENTIFIER_WITH_DOUBLED_QUOTES,
3387
+ tripleQuotes: "absent",
3388
+ escapeStringPrefix: "absent",
3389
+ dollarQuotes: "uncertain",
3390
+ dashDash: "uncertain-before-text",
3391
+ carriageReturnInLineComment: "uncertain",
3392
+ hash: "uncertain",
3393
+ executableComments: "uncertain",
3394
+ nestedBlockComments: "uncertain",
3395
+ backslashOutsideLiterals: "text",
3396
+ clientCharsets: "may-be-multibyte"
3397
+ };
3398
+ var MYSQL_SYNTAX = { inlineFlags: /* @__PURE__ */ new Set(["-e", "--execute"]), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: false, lexicon: MYSQL_LEXICON };
3399
+ var SQLITE_SYNTAX = { inlineFlags: /* @__PURE__ */ new Set(["-cmd"]), scriptFlags: /* @__PURE__ */ new Set(["-init"]), positionalSql: true, lexicon: SQLITE_LEXICON };
2893
3400
  var SQL_CLIENT_SYNTAX = /* @__PURE__ */ new Map([
2894
- ["psql", { inlineFlags: /* @__PURE__ */ new Set(["-c", "--command"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "--file"]), positionalSql: false }],
3401
+ ["psql", { inlineFlags: /* @__PURE__ */ new Set(["-c", "--command"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "--file"]), positionalSql: false, lexicon: POSTGRES_LEXICON }],
2895
3402
  ["mysql", MYSQL_SYNTAX],
2896
3403
  ["mariadb", MYSQL_SYNTAX],
2897
3404
  ["sqlite3", SQLITE_SYNTAX],
2898
3405
  ["sqlite", SQLITE_SYNTAX],
2899
- ["duckdb", { inlineFlags: /* @__PURE__ */ new Set(["-c", "-s", "-cmd"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "-init"]), positionalSql: true }],
2900
- ["clickhouse-client", { inlineFlags: /* @__PURE__ */ new Set(["-q", "--query"]), scriptFlags: /* @__PURE__ */ new Set(["--queries-file"]), positionalSql: false }],
2901
- ["bq", { inlineFlags: /* @__PURE__ */ new Set(), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: true }],
2902
- ["mongosh", { inlineFlags: /* @__PURE__ */ new Set(["--eval"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "--file"]), positionalSql: false }],
2903
- ["mongo", { inlineFlags: /* @__PURE__ */ new Set(["--eval"]), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: false }]
3406
+ ["duckdb", { inlineFlags: /* @__PURE__ */ new Set(["-c", "-s", "-cmd"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "-init"]), positionalSql: true, lexicon: UNVERIFIED_SQL_LEXICON }],
3407
+ ["clickhouse-client", { inlineFlags: /* @__PURE__ */ new Set(["-q", "--query"]), scriptFlags: /* @__PURE__ */ new Set(["--queries-file"]), positionalSql: false, lexicon: UNVERIFIED_SQL_LEXICON }],
3408
+ ["bq", { inlineFlags: /* @__PURE__ */ new Set(), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: true, lexicon: GOOGLE_SQL_LEXICON }],
3409
+ ["mongosh", { inlineFlags: /* @__PURE__ */ new Set(["--eval"]), scriptFlags: /* @__PURE__ */ new Set(["-f", "--file"]), positionalSql: false, lexicon: UNVERIFIED_SQL_LEXICON }],
3410
+ ["mongo", { inlineFlags: /* @__PURE__ */ new Set(["--eval"]), scriptFlags: /* @__PURE__ */ new Set(), positionalSql: false, lexicon: UNVERIFIED_SQL_LEXICON }]
2904
3411
  ]);
2905
3412
  var SQL_WRITE_STATEMENT = new RegExp([
2906
3413
  String.raw`\b(?:insert|update|delete|merge|upsert|alter|create|drop|truncate|grant|revoke|copy|vacuum|reindex|rename|attach|detach)\b`,
@@ -2909,21 +3416,26 @@ var SQL_WRITE_STATEMENT = new RegExp([
2909
3416
  String.raw`\binto\s+(?:out|dump)file\b`,
2910
3417
  String.raw`\bset\s+(?:global|persist)\b`,
2911
3418
  String.raw`\bkill\s+(?:query|connection|\d)`,
2912
- String.raw`\bcall\s+[\w.]+\s*\(`,
2913
- String.raw`\bdo\s+(?:\$\w*\$|')`,
3419
+ String.raw`\bcall\b`,
3420
+ String.raw`\bexecute\s+immediate\b`,
3421
+ String.raw`\bprepare\s+\S+\s+from\b`,
3422
+ String.raw`\bselect\b[^;]*\binto\b(?!\s*@)`,
3423
+ String.raw`(?:^|;)\s*lock\b`,
3424
+ String.raw`(?:^|;)\s*do\b`,
2914
3425
  String.raw`\bpg_terminate_backend\b`,
2915
3426
  String.raw`\bsetval\b`,
2916
3427
  String.raw`\bpragma\s+writable_schema\b`,
2917
3428
  String.raw`\.(?:insert|update|delete|replace|remove|drop|rename|create|bulkwrite|findoneand)\w*\s*\(`
2918
3429
  ].join("|"), "i");
2919
3430
  var SQL_READ_PHRASE = /\bshow\s+create\b/gi;
2920
- var SQL_STRING_LITERAL = /'(?:[^']|'')*'/g;
2921
- var EMPTY_SQL_STRING = "''";
2922
- var SQL_COMMENT = /--[^\n]*|\/\*[\s\S]*?\*\//g;
2923
- var writesThroughSql = (sql) => {
2924
- const statement = sql.replace(SQL_COMMENT, " ").replace(SQL_STRING_LITERAL, EMPTY_SQL_STRING).replace(SQL_READ_PHRASE, "");
3431
+ var sqlTextWrites = (text) => {
3432
+ const statement = text.replace(SQL_READ_PHRASE, "");
2925
3433
  return SQL_WRITE_STATEMENT.test(statement) || SQL_CLIENT_FILE_COMMAND.test(statement);
2926
3434
  };
3435
+ var writesThroughSql = (sql, lexicon) => {
3436
+ const parsed = sqlOutsideLiterals(sql, lexicon);
3437
+ return parsed.kind === "uncertain" || parsed.texts.some(sqlTextWrites);
3438
+ };
2927
3439
  var SQL_CLIENT_FILE_COMMAND = new RegExp([
2928
3440
  String.raw`(?:^|[\s;=])\\(?:i|ir|include|include_relative|o|out|w|write|gexec|!|\.)(?=\s|$)`,
2929
3441
  String.raw`(?:^|[\s;=])\\g\s*\|`,
@@ -2931,6 +3443,7 @@ var SQL_CLIENT_FILE_COMMAND = new RegExp([
2931
3443
  String.raw`(?:^|[;=])\s*(?:system|source)\s`
2932
3444
  ].join("|"), "i");
2933
3445
  var SHORT_FLAG_CLUSTER_ONLY = /^-([A-Za-z0-9]+)$/;
3446
+ var LEADING_OPTION_DASHES = /^-+/;
2934
3447
  var NO_SQL = { script: false, sql: null, hidden: false };
2935
3448
  var shortFlagOf = (flags, text) => [...flags].find((flag) => /^-[A-Za-z]$/.test(flag) && text.startsWith(flag) && text.length > flag.length && !text.startsWith("--"));
2936
3449
  var sqlArgumentAt = (args, index, syntax) => {
@@ -2950,7 +3463,7 @@ var sqlArgumentAt = (args, index, syntax) => {
2950
3463
  const last = cluster ? `-${cluster.slice(-1)}` : "";
2951
3464
  if (cluster && cluster.length > 1 && syntax.scriptFlags.has(last)) return { script: true, sql: null, hidden: false };
2952
3465
  if (cluster && cluster.length > 1 && syntax.inlineFlags.has(last)) return valueOf(next);
2953
- return { script: false, sql: arg.text, hidden: false };
3466
+ return { script: false, sql: arg.text.replace(LEADING_OPTION_DASHES, ""), hidden: false };
2954
3467
  };
2955
3468
  var namesALongFlagValue = (text, flags) => [...flags].some((flag) => flag.startsWith("--") && text.startsWith(`${flag}${FLAG_VALUE_SEPARATOR}`));
2956
3469
  var positionalSqlIsHidden = (args, syntax) => syntax.positionalSql && args.filter((arg) => !arg.text.startsWith("-")).slice(1).some((arg) => arg.expands);
@@ -2960,7 +3473,7 @@ var sqlClientChangesData = (invocation) => {
2960
3473
  if (syntax === void 0) return false;
2961
3474
  return positionalSqlIsHidden(invocation.args, syntax) || invocation.args.some((_, index) => {
2962
3475
  const { script, sql, hidden } = sqlArgumentAt(invocation.args, index, syntax);
2963
- return script || hidden || sql !== null && writesThroughSql(sql);
3476
+ return script || hidden || sql !== null && writesThroughSql(sql, syntax.lexicon);
2964
3477
  });
2965
3478
  };
2966
3479
  var PULL_REQUEST_CLIS = /* @__PURE__ */ new Set(["gh", "glab"]);
@@ -3102,10 +3615,24 @@ var GITHUB_READ_COMMANDS = /* @__PURE__ */ new Map([
3102
3615
  var GITHUB_OPTIONS_WITH_VALUES = /* @__PURE__ */ new Set(["-R", "--repo", "--hostname"]);
3103
3616
  var GITHUB_API_SUBCOMMAND = "api";
3104
3617
  var GITHUB_GRAPHQL_ENDPOINT = "graphql";
3105
- var HTTP_METHOD_FLAGS = /* @__PURE__ */ new Set(["-X", "--method"]);
3106
- var HTTP_METHOD_ATTACHED = /^(?:-X|--method=)(.+)$/;
3618
+ var HTTP_METHOD_OPTIONS = /* @__PURE__ */ new Set(["-X", "--method"]);
3107
3619
  var HTTP_READ_METHODS = /* @__PURE__ */ new Set(["GET", "HEAD"]);
3108
- var GITHUB_API_BODY_FLAG = /^(?:-[fF]|--(?:field|raw-field|input)(?:=|$))/;
3620
+ var GITHUB_API_BODY_OPTIONS = /* @__PURE__ */ new Set(["-f", "-F", "--field", "--raw-field", "--input"]);
3621
+ var GITHUB_API_SHORT_SWITCHES = /* @__PURE__ */ new Set(["i", "h"]);
3622
+ var GITHUB_API_SHORT_OPTIONS_WITH_A_VALUE = /* @__PURE__ */ new Set(["X", "F", "f", "H", "p", "t", "q"]);
3623
+ var GITHUB_API_LONG_OPTIONS_WITH_A_VALUE = /* @__PURE__ */ new Set([
3624
+ "--method",
3625
+ "--field",
3626
+ "--raw-field",
3627
+ "--header",
3628
+ "--preview",
3629
+ "--input",
3630
+ "--template",
3631
+ "--jq",
3632
+ "--cache",
3633
+ "--hostname"
3634
+ ]);
3635
+ var PFLAG_ATTACHED_VALUE_PREFIX = /^=/;
3109
3636
  var GITHUB_API_FILE_FIELD = /=@|^--input(?:=|$)/;
3110
3637
  var GRAPHQL_MUTATION = /\bmutation\b/i;
3111
3638
  var STRIPE_READ_COMMANDS = /* @__PURE__ */ new Set([
@@ -3154,29 +3681,63 @@ var S3_URL_PREFIX = "s3://";
3154
3681
  var TWILIO_TOPIC_SEPARATOR = ":";
3155
3682
  var TWILIO_READ_ACTIONS = /* @__PURE__ */ new Set(["list", "fetch"]);
3156
3683
  var positionalWordsOf = (args, optionsWithValues) => {
3157
- const endOfOptions = args.findIndex((arg) => arg.text === END_OF_OPTIONS);
3684
+ const endOfOptions = args.findIndex((arg) => arg.text === END_OF_OPTIONS3);
3158
3685
  const options = endOfOptions === -1 ? args : args.slice(0, endOfOptions);
3159
3686
  const operands = endOfOptions === -1 ? [] : args.slice(endOfOptions + 1);
3160
3687
  const positional = options.filter((arg, index) => !arg.text.startsWith("-") && !optionsWithValues.has(options[index - 1]?.text ?? ""));
3161
3688
  return [...positional, ...operands];
3162
3689
  };
3163
- var httpMethodOf = (args) => {
3164
- for (const [index, arg] of args.entries()) {
3165
- const attached = HTTP_METHOD_ATTACHED.exec(arg.text);
3166
- if (attached) return arg.expands ? null : attached[1];
3167
- if (HTTP_METHOD_FLAGS.has(arg.text)) {
3168
- const value = args[index + 1];
3169
- return value === void 0 || value.expands ? null : value.text;
3690
+ var NO_CLI_OPTION = [];
3691
+ var githubApiLongOptionAt = (args, index, arg) => {
3692
+ const separator = arg.text.indexOf(FLAG_VALUE_SEPARATOR);
3693
+ if (separator !== -1) {
3694
+ return { options: [{ name: arg.text.slice(0, separator), value: { ...arg, text: arg.text.slice(separator + 1) } }], next: index + 1 };
3695
+ }
3696
+ if (!GITHUB_API_LONG_OPTIONS_WITH_A_VALUE.has(arg.text)) return { options: [{ name: arg.text, value: void 0 }], next: index + 1 };
3697
+ return { options: [{ name: arg.text, value: args[index + 1] }], next: index + 2 };
3698
+ };
3699
+ var githubApiShortOptionsAt = (args, index, arg) => {
3700
+ const options = [];
3701
+ for (let position = 1; position < arg.text.length; position += 1) {
3702
+ const letter = arg.text.charAt(position);
3703
+ const name = `-${letter}`;
3704
+ if (GITHUB_API_SHORT_SWITCHES.has(letter)) {
3705
+ options.push({ name, value: void 0 });
3706
+ continue;
3170
3707
  }
3708
+ if (!GITHUB_API_SHORT_OPTIONS_WITH_A_VALUE.has(letter)) return null;
3709
+ const attached = arg.text.slice(position + 1);
3710
+ if (attached === "") return { options: [...options, { name, value: args[index + 1] }], next: index + 2 };
3711
+ return { options: [...options, { name, value: { ...arg, text: attached.replace(PFLAG_ATTACHED_VALUE_PREFIX, "") } }], next: index + 1 };
3171
3712
  }
3172
- return void 0;
3713
+ return { options, next: index + 1 };
3714
+ };
3715
+ var githubApiOptionsAt = (args, index, arg) => {
3716
+ if (LONG_OPTION.test(arg.text)) return githubApiLongOptionAt(args, index, arg);
3717
+ if (FLAG.test(arg.text) && arg.text !== STANDARD_INPUT_ARGUMENT) return githubApiShortOptionsAt(args, index, arg);
3718
+ return { options: NO_CLI_OPTION, next: index + 1 };
3719
+ };
3720
+ var githubApiOptionsOf = (args) => {
3721
+ const options = [];
3722
+ for (let index = 0; index < args.length; ) {
3723
+ const arg = args[index];
3724
+ if (arg === void 0 || arg.text === END_OF_OPTIONS3) break;
3725
+ const parsed = githubApiOptionsAt(args, index, arg);
3726
+ if (parsed === null) return null;
3727
+ options.push(...parsed.options);
3728
+ index = parsed.next;
3729
+ }
3730
+ return options;
3173
3731
  };
3732
+ var requestMethodCanWrite = (method) => method === void 0 || method.expands || !HTTP_READ_METHODS.has(method.text.toUpperCase());
3174
3733
  var graphqlRequestCanWrite = (args) => args.some((arg) => arg.expands || GRAPHQL_MUTATION.test(arg.text) || GITHUB_API_FILE_FIELD.test(arg.text));
3175
3734
  var githubApiRequestWrites = (args) => {
3176
- const method = httpMethodOf(args);
3177
- if (method !== void 0) return method === null || !HTTP_READ_METHODS.has(method.toUpperCase());
3735
+ const options = githubApiOptionsOf(args);
3736
+ if (options === null) return true;
3737
+ const method = options.filter((option) => HTTP_METHOD_OPTIONS.has(option.name)).at(-1);
3738
+ if (method !== void 0) return requestMethodCanWrite(method.value);
3178
3739
  if (args.some((arg) => arg.text === GITHUB_GRAPHQL_ENDPOINT)) return graphqlRequestCanWrite(args);
3179
- return args.some((arg) => GITHUB_API_BODY_FLAG.test(arg.text));
3740
+ return options.some((option) => GITHUB_API_BODY_OPTIONS.has(option.name));
3180
3741
  };
3181
3742
  var githubCommandOnlyReads = (noun, verb) => {
3182
3743
  if (noun === void 0 || GITHUB_COMMANDS_THAT_ONLY_READ.has(noun.text)) return true;
@@ -3360,8 +3921,9 @@ var findRunnerEnd = (args, from) => {
3360
3921
  };
3361
3922
  var wrapperSyntax = (optionsWithAValue = [], operandsBeforeTheCommand = 0) => ({ optionsWithAValue: new Set(optionsWithAValue), operandsBeforeTheCommand });
3362
3923
  var ENVIRONMENT_ASSIGNMENTS = wrapperSyntax();
3924
+ var ENV = "env";
3925
+ var ENV_SPLIT_STRING_ESCAPE = /[\\$]/;
3363
3926
  var WRAPPER_SYNTAX = /* @__PURE__ */ new Map([
3364
- ["env", wrapperSyntax(["-u", "--unset", "-C", "--chdir", "-S", "--split-string", "-P"])],
3365
3927
  ["xargs", wrapperSyntax([
3366
3928
  "-I",
3367
3929
  "-J",
@@ -3423,22 +3985,39 @@ var WRAPPER_SYNTAX = /* @__PURE__ */ new Map([
3423
3985
  ["pnpx", wrapperSyntax()],
3424
3986
  ["uvx", wrapperSyntax(["--from", "--with", "-p", "--python"])]
3425
3987
  ]);
3426
- var SHELLS = /* @__PURE__ */ new Set(["sh", "bash", "zsh", "dash", "ksh"]);
3427
- var SCRIPT_FLAG_CLUSTER = /^-[A-Za-z]*c$/;
3428
3988
  var EVAL = "eval";
3429
3989
  var MAX_CONSEQUENCE_DEPTH = 4;
3990
+ var shortValueOptionPosition = (text, options) => {
3991
+ if (!text.startsWith("-") || text.startsWith("--")) return -1;
3992
+ for (let index = 1; index < text.length; index += 1) {
3993
+ if (options.has(`-${text[index]}`)) return index;
3994
+ }
3995
+ return -1;
3996
+ };
3997
+ var wrapperOptionConsumesNextWord = (text, options) => {
3998
+ if (options.has(text)) return true;
3999
+ const position = shortValueOptionPosition(text, options);
4000
+ return position !== -1 && position === text.length - 1;
4001
+ };
3430
4002
  var commandStartAfterWrapper = (words, syntax) => {
3431
4003
  let index = 0;
3432
4004
  while (index < words.length) {
3433
4005
  const text = words[index]?.text ?? "";
3434
- if (text === END_OF_OPTIONS) return index + 1 + syntax.operandsBeforeTheCommand;
4006
+ if (text === END_OF_OPTIONS3) return index + 1 + syntax.operandsBeforeTheCommand;
3435
4007
  if (!SHELL_ENV_ASSIGNMENT.test(text) && (!FLAG.test(text) || text === STANDARD_INPUT_ARGUMENT)) break;
3436
- index += syntax.optionsWithAValue.has(text) ? 2 : 1;
4008
+ index += wrapperOptionConsumesNextWord(text, syntax.optionsWithAValue) ? 2 : 1;
3437
4009
  }
3438
4010
  return index + syntax.operandsBeforeTheCommand;
3439
4011
  };
4012
+ var envWrappedInvocation = (args) => {
4013
+ const reading = envReadingOf(args);
4014
+ if (reading.kind !== "command") return null;
4015
+ const command = args[reading.start];
4016
+ return command === void 0 ? null : { program: command, args: args.slice(reading.start + 1) };
4017
+ };
3440
4018
  var wrappedInvocation = ({ program, args }) => {
3441
4019
  if (program === void 0) return null;
4020
+ if (basenameOf(program.text) === ENV) return envWrappedInvocation(args);
3442
4021
  const assigns = SHELL_ENV_ASSIGNMENT.test(program.text);
3443
4022
  const syntax = assigns ? ENVIRONMENT_ASSIGNMENTS : WRAPPER_SYNTAX.get(basenameOf(program.text));
3444
4023
  if (syntax === void 0) return null;
@@ -3447,17 +4026,29 @@ var wrappedInvocation = ({ program, args }) => {
3447
4026
  const command = words[start];
3448
4027
  return command === void 0 ? null : { program: command, args: words.slice(start + 1) };
3449
4028
  };
3450
- var innermostInvocation = (invocation, depth = 0) => {
3451
- const wrapped = depth < MAX_CONSEQUENCE_DEPTH ? wrappedInvocation(invocation) : null;
3452
- return wrapped === null ? invocation : innermostInvocation(wrapped, depth + 1);
4029
+ var innermostInvocation = (invocation) => {
4030
+ let current = invocation;
4031
+ let wrapped = wrappedInvocation(current);
4032
+ while (wrapped !== null) {
4033
+ current = wrapped;
4034
+ wrapped = wrappedInvocation(current);
4035
+ }
4036
+ return current;
4037
+ };
4038
+ var envSplitScriptOf = ({ prefix, value, rest }, args) => {
4039
+ if (value === void 0 || value.expands || ENV_SPLIT_STRING_ESCAPE.test(value.text)) return null;
4040
+ return [ENV, ...prefix.map(asOneShellWord), value.text, ...args.slice(rest).map((arg) => asOneShellWord(arg.text))].join(" ");
3453
4041
  };
3454
4042
  var shellScriptOf = ({ program, args }) => {
3455
4043
  if (program === void 0) return null;
3456
- if (basenameOf(program.text) === EVAL) return args.some((arg) => arg.expands) ? null : args.map((arg) => arg.text).join(" ");
3457
- if (!SHELLS.has(basenameOf(program.text))) return null;
3458
- const flag = args.findIndex((arg) => SCRIPT_FLAG_CLUSTER.test(arg.text));
3459
- const script = flag === -1 ? void 0 : args[flag + 1];
3460
- return script === void 0 || script.expands ? null : script.text;
4044
+ const name = basenameOf(program.text);
4045
+ if (name === ENV) {
4046
+ const reading = envReadingOf(args);
4047
+ return reading.kind === "split" ? envSplitScriptOf(reading, args) : null;
4048
+ }
4049
+ if (name === EVAL) return args.some((arg) => arg.expands) ? null : args.map((arg) => arg.text).join(" ");
4050
+ const commandString = shellCommandStringOf(name, args);
4051
+ return commandString.kind === "readable" ? commandString.script : null;
3461
4052
  };
3462
4053
  var FLAG = /^-/;
3463
4054
  var FLAG_WITH_ATTACHED_VALUE = /^-[^=]*=/;
@@ -3485,18 +4076,19 @@ var honoursPreviewFlags = ({ program, args }) => {
3485
4076
  var onlyPreviews = (invocation) => invocation.program !== void 0 && honoursPreviewFlags(invocation) && invocation.args.some((arg) => !arg.expands && PREVIEW_FLAG.test(arg.text));
3486
4077
  var changesWhatIsDeployed = (toolName, invocation, normalized) => !onlyPreviews(invocation) && (changesProduction(invocation) || mergesAPullRequest(invocation) || isCoveredByPolicy(DEPLOY_AND_SCHEMA_COMMAND_PATTERNS, toolName, normalized));
3487
4078
  var invocationHasAVisibleConsequence = (toolName, invocation, depth) => {
3488
- if (invocation.program === void 0 || depth > MAX_CONSEQUENCE_DEPTH) return false;
4079
+ if (depth > MAX_CONSEQUENCE_DEPTH) return true;
4080
+ if (invocation.program === void 0) return false;
3489
4081
  const normalized = quotedInvocation(invocation);
3490
- const wrapped = wrappedInvocation(invocation);
4082
+ const innermost = innermostInvocation(invocation);
3491
4083
  const script = shellScriptOf(invocation);
3492
- return classifyDecisionRisk(toolName, normalized) === "destructive" || changesWhatIsDeployed(toolName, invocation, normalized) || writesASecretFile(invocation) || losesDataVisibly(toolName, invocation, normalized, depth) || subcommandDestroysVisibly(invocation) || sqlClientChangesData(invocation) || wrapped !== null && invocationHasAVisibleConsequence(toolName, wrapped, depth + 1) || script !== null && commandHasAVisibleConsequenceAt(toolName, script, depth + 1) || readingsPastGlobalFlags(invocation).some((reading) => invocationHasAVisibleConsequence(toolName, reading, depth + 1));
4084
+ return classifyDecisionRisk(toolName, normalized) === "destructive" || changesWhatIsDeployed(toolName, invocation, normalized) || writesASecretFile(invocation) || losesDataVisibly(toolName, invocation, normalized, depth) || subcommandDestroysVisibly(invocation) || sqlClientChangesData(invocation) || innermost !== invocation && invocationHasAVisibleConsequence(toolName, innermost, depth) || script === null && passesAnInlineScript(invocation) || script !== null && commandHasAVisibleConsequenceAt(toolName, script, depth + 1) || readingsPastGlobalFlags(invocation).some((reading) => invocationHasAVisibleConsequence(toolName, reading, depth + 1));
3493
4085
  };
3494
4086
  var RUNS_FETCHED_CODE = /(?:\$\(|`|<\()\s*(?:curl|wget)\b/;
3495
4087
  var FETCHING_PROGRAMS = /* @__PURE__ */ new Set(["curl", "wget"]);
3496
4088
  var READS_ITS_SCRIPT_FROM_STANDARD_INPUT = /^-[A-Za-z]*s[A-Za-z]*$/;
3497
4089
  var interpreterNameOf = (program) => basenameOf(program.text).replace(/\d+(?:\.\d+)*$/, "");
3498
- var runsScripts = (program) => SHELLS.has(basenameOf(program.text)) || INLINE_CODE_INTERPRETERS.has(interpreterNameOf(program));
3499
- var runsWhatItReads = ({ program, args }) => program !== void 0 && runsScripts(program) && (args.length === 0 || args.every((arg) => arg.text.startsWith("-")) || args.some((arg) => arg.text === STANDARD_INPUT_ARGUMENT) || SHELLS.has(basenameOf(program.text)) && args.some((arg) => READS_ITS_SCRIPT_FROM_STANDARD_INPUT.test(arg.text)));
4090
+ var runsScripts = (program) => POSIX_SHELL_PROGRAMS.has(basenameOf(program.text)) || INLINE_CODE_INTERPRETERS.has(interpreterNameOf(program));
4091
+ var runsWhatItReads = ({ program, args }) => program !== void 0 && runsScripts(program) && (args.length === 0 || args.every((arg) => arg.text.startsWith("-")) || args.some((arg) => arg.text === STANDARD_INPUT_ARGUMENT) || POSIX_SHELL_PROGRAMS.has(basenameOf(program.text)) && args.some((arg) => READS_ITS_SCRIPT_FROM_STANDARD_INPUT.test(arg.text)));
3500
4092
  var fetches = (invocation) => FETCHING_PROGRAMS.has(basenameOf(innermostInvocation(invocation).program?.text ?? ""));
3501
4093
  var URL_QUERY_OR_FRAGMENT2 = /[?#].*$/;
3502
4094
  var SOURCES_A_SCRIPT = /* @__PURE__ */ new Set(["source", "."]);
@@ -3611,7 +4203,7 @@ var roughSegmentsOf = (command) => {
3611
4203
  };
3612
4204
  var roughSegmentHasAVisibleConsequence = (toolName, segment, fetchesCode, depth) => {
3613
4205
  const innermost = innermostInvocation(segment.invocation);
3614
- const runsAHeredocScript = innermost.program !== void 0 && SHELLS.has(basenameOf(innermost.program.text));
4206
+ const runsAHeredocScript = innermost.program !== void 0 && POSIX_SHELL_PROGRAMS.has(basenameOf(innermost.program.text));
3615
4207
  return invocationHasAVisibleConsequence(toolName, segment.invocation, depth) || sqlClientSyntaxOf(innermost) !== void 0 && (segment.readsInput || segment.feedsASubstitution) || segment.readsAPipe && fetchesCode && runsWhatItReads(innermost) || runsAHeredocScript && segment.heredocs.some((body) => commandHasAVisibleConsequenceAt(toolName, body, depth + 1));
3616
4208
  };
3617
4209
  var roughReadingHasAVisibleConsequence = (toolName, command, depth) => {
@@ -3701,14 +4293,28 @@ var canonicalInvocationText = (invocation) => invocationTextWith(invocation, (wo
3701
4293
  var spellingsOfAnInvocation = (invocation, innermost) => [invocation, innermost, ...gitReadingsPastGlobalOptions(innermost), ...readingsPastGlobalFlags(innermost)].flatMap((reading) => [verbatimInvocationText(reading), canonicalInvocationText(reading)]);
3702
4294
  var NO_INLINE_SCRIPT = { kind: "none" };
3703
4295
  var HIDDEN_INLINE_SCRIPT = { kind: "hidden" };
4296
+ var ENV_READINGS_THAT_NAME_THEIR_OUTCOME = /* @__PURE__ */ new Set(["command", "runs-nothing"]);
4297
+ var envPassesItsCommandIndirectly = (reading) => !ENV_READINGS_THAT_NAME_THEIR_OUTCOME.has(reading.kind);
3704
4298
  var passesAnInlineScript = ({ program, args }) => {
3705
4299
  const name = basenameOf(program?.text ?? "");
3706
- return name === EVAL || SHELLS.has(name) && args.some((arg) => SCRIPT_FLAG_CLUSTER.test(arg.text));
3707
- };
3708
- var shellReadsItsScript = (invocation) => SHELLS.has(basenameOf(invocation.program?.text ?? "")) && runsWhatItReads(invocation);
4300
+ return name === EVAL || shellCommandStringOf(name, args).kind !== "absent" || name === ENV && envPassesItsCommandIndirectly(envReadingOf(args));
4301
+ };
4302
+ var envCommandScriptOf = (start, args) => args[start]?.expands ? null : args.slice(start).map((word) => asOneShellWord(word.text)).join(" ");
4303
+ var envCandidateScriptOf = (reading, args) => reading.kind === "split" ? envSplitScriptOf(reading, args) : envCommandScriptOf(reading.start, args);
4304
+ var isAScript = (script) => script !== null;
4305
+ var envCandidateScriptsOf = ({ program, args }) => {
4306
+ if (basenameOf(program?.text ?? "") !== ENV) return NO_INLINE_SCRIPT;
4307
+ const reading = envReadingOf(args);
4308
+ if (reading.kind !== "ambiguous") return NO_INLINE_SCRIPT;
4309
+ const scripts = reading.readings.map((candidate) => envCandidateScriptOf(candidate, args));
4310
+ return scripts.every(isAScript) ? { kind: "readable", scripts } : HIDDEN_INLINE_SCRIPT;
4311
+ };
4312
+ var shellReadsItsScript = (invocation) => POSIX_SHELL_PROGRAMS.has(basenameOf(invocation.program?.text ?? "")) && runsWhatItReads(invocation);
3709
4313
  var inlineScriptsOf = (invocation, heredocs) => {
3710
4314
  const script = shellScriptOf(invocation);
3711
4315
  if (script !== null) return { kind: "readable", scripts: [script] };
4316
+ const envCandidates = envCandidateScriptsOf(invocation);
4317
+ if (envCandidates.kind !== "none") return envCandidates;
3712
4318
  if (passesAnInlineScript(invocation)) return HIDDEN_INLINE_SCRIPT;
3713
4319
  if (!shellReadsItsScript(invocation)) return NO_INLINE_SCRIPT;
3714
4320
  return heredocs.length > 0 ? { kind: "readable", scripts: heredocs } : HIDDEN_INLINE_SCRIPT;
@@ -5190,6 +5796,8 @@ export {
5190
5796
  MAX_HOOK_ACTIVATION_EVIDENCE_ROWS,
5191
5797
  isHookActivationReport,
5192
5798
  hookActivationResult,
5799
+ CLIENT_REPORT_PATH,
5800
+ clientContextHeaders,
5193
5801
  PAIR_TTL_SECONDS,
5194
5802
  computerOsOfPlatform,
5195
5803
  SETUP_AGENT_CHOICES,
@@ -5197,8 +5805,6 @@ export {
5197
5805
  NO_PAIRING_COMPUTER,
5198
5806
  SETUP_CONNECT_MODES,
5199
5807
  isSetupConnectMode,
5200
- CLIENT_REPORT_PATH,
5201
- clientContextHeaders,
5202
5808
  DECLINED_AGENTS_FILE,
5203
5809
  parseDeclinedAgents,
5204
5810
  serializeDeclinedAgents,