fix: refresh pi dependency compatibility
Update Pi packages to 0.79.9 and align pi-ask with current TUI/RPC behavior. - guard custom ask/settings flows to TUI mode with a clear non-TUI fallback - reset config cache on extension reload so edited settings are picked up - clean up remote ask flow listeners on session shutdown - forward editor focus/invalidation and keep @ file autocomplete explicit - document the non-TUI contract and cover the compatibility fixes with tests
This commit is contained in:
+3
-3
@@ -255,9 +255,9 @@ Dirty dismiss:
|
|||||||
- when `Confirm dismiss when dirty` is enabled, cancelling or dismissing a dirty ask flow requires the same action a second time
|
- when `Confirm dismiss when dirty` is enabled, cancelling or dismissing a dirty ask flow requires the same action a second time
|
||||||
- the dirty-dismiss warning stays visible until the user changes tabs in the ask flow
|
- the dirty-dismiss warning stays visible until the user changes tabs in the ask flow
|
||||||
|
|
||||||
## Non-interactive mode
|
## Non-TUI and non-interactive modes
|
||||||
|
|
||||||
If `ctx.hasUI === false`, the tool returns a `Needs user input` message in `content` and a cancelled result in `details`.
|
The rich ask flow uses `ctx.ui.custom()` and opens only in TUI mode. In print, JSON, RPC, or any other non-TUI mode, the tool returns a `Needs user input: ask_user requires interactive TUI mode.` message in `content` and a cancelled result in `details` instead of opening custom UI.
|
||||||
|
|
||||||
Validation is handled inside the tool so malformed calls produce the same structured error shape as other invalid payloads instead of relying on pre-execution schema failures.
|
Validation is handled inside the tool so malformed calls produce the same structured error shape as other invalid payloads instead of relying on pre-execution schema failures.
|
||||||
|
|
||||||
@@ -269,7 +269,7 @@ When enabled, pi-ask emits one best-effort external notification per ask session
|
|||||||
|
|
||||||
## Remote inter-extension events
|
## Remote inter-extension events
|
||||||
|
|
||||||
pi-ask exposes a local `pi.events` contract for trusted Pi extensions. It does not expose a network API and does not automate terminal keystrokes.
|
pi-ask exposes a local `pi.events` contract for trusted Pi extensions. It does not expose a network API and does not automate terminal keystrokes. RPC or headless integrations should use a trusted in-process bridge extension that consumes these events rather than expecting the TUI-only custom surface to open.
|
||||||
|
|
||||||
Channels:
|
Channels:
|
||||||
|
|
||||||
|
|||||||
+7
-7
@@ -93,9 +93,9 @@
|
|||||||
"@biomejs/biome": "2.4.12",
|
"@biomejs/biome": "2.4.12",
|
||||||
"@commitlint/cli": "^19.8.1",
|
"@commitlint/cli": "^19.8.1",
|
||||||
"@commitlint/config-conventional": "^19.8.1",
|
"@commitlint/config-conventional": "^19.8.1",
|
||||||
"@earendil-works/pi-ai": "0.75.4",
|
"@earendil-works/pi-ai": "0.79.9",
|
||||||
"@earendil-works/pi-coding-agent": "0.75.4",
|
"@earendil-works/pi-coding-agent": "0.79.9",
|
||||||
"@earendil-works/pi-tui": "0.75.4",
|
"@earendil-works/pi-tui": "0.79.9",
|
||||||
"@semantic-release/changelog": "^6.0.3",
|
"@semantic-release/changelog": "^6.0.3",
|
||||||
"@semantic-release/commit-analyzer": "^13.0.1",
|
"@semantic-release/commit-analyzer": "^13.0.1",
|
||||||
"@semantic-release/git": "^10.0.1",
|
"@semantic-release/git": "^10.0.1",
|
||||||
@@ -118,10 +118,10 @@
|
|||||||
},
|
},
|
||||||
"pnpm": {
|
"pnpm": {
|
||||||
"overrides": {
|
"overrides": {
|
||||||
"@earendil-works/pi-agent-core": "0.75.4",
|
"@earendil-works/pi-agent-core": "0.79.9",
|
||||||
"@earendil-works/pi-ai": "0.75.4",
|
"@earendil-works/pi-ai": "0.79.9",
|
||||||
"@earendil-works/pi-tui": "0.75.4",
|
"@earendil-works/pi-tui": "0.79.9",
|
||||||
"@earendil-works/pi-coding-agent": "0.75.4"
|
"@earendil-works/pi-coding-agent": "0.79.9"
|
||||||
},
|
},
|
||||||
"ignoredBuiltDependencies": [
|
"ignoredBuiltDependencies": [
|
||||||
"lefthook"
|
"lefthook"
|
||||||
|
|||||||
Generated
+130
-105
@@ -5,10 +5,10 @@ settings:
|
|||||||
excludeLinksFromLockfile: false
|
excludeLinksFromLockfile: false
|
||||||
|
|
||||||
overrides:
|
overrides:
|
||||||
'@earendil-works/pi-agent-core': 0.75.4
|
'@earendil-works/pi-agent-core': 0.79.9
|
||||||
'@earendil-works/pi-ai': 0.75.4
|
'@earendil-works/pi-ai': 0.79.9
|
||||||
'@earendil-works/pi-tui': 0.75.4
|
'@earendil-works/pi-tui': 0.79.9
|
||||||
'@earendil-works/pi-coding-agent': 0.75.4
|
'@earendil-works/pi-coding-agent': 0.79.9
|
||||||
|
|
||||||
importers:
|
importers:
|
||||||
|
|
||||||
@@ -24,14 +24,14 @@ importers:
|
|||||||
specifier: ^19.8.1
|
specifier: ^19.8.1
|
||||||
version: 19.8.1
|
version: 19.8.1
|
||||||
'@earendil-works/pi-ai':
|
'@earendil-works/pi-ai':
|
||||||
specifier: 0.75.4
|
specifier: 0.79.9
|
||||||
version: 0.75.4(ws@8.20.0)(zod@4.3.6)
|
version: 0.79.9(ws@8.20.0)(zod@4.3.6)
|
||||||
'@earendil-works/pi-coding-agent':
|
'@earendil-works/pi-coding-agent':
|
||||||
specifier: 0.75.4
|
specifier: 0.79.9
|
||||||
version: 0.75.4(ws@8.20.0)(zod@4.3.6)
|
version: 0.79.9(ws@8.20.0)(zod@4.3.6)
|
||||||
'@earendil-works/pi-tui':
|
'@earendil-works/pi-tui':
|
||||||
specifier: 0.75.4
|
specifier: 0.79.9
|
||||||
version: 0.75.4
|
version: 0.79.9
|
||||||
'@semantic-release/changelog':
|
'@semantic-release/changelog':
|
||||||
specifier: ^6.0.3
|
specifier: ^6.0.3
|
||||||
version: 6.0.3(semantic-release@25.0.3(typescript@6.0.2))
|
version: 6.0.3(semantic-release@25.0.3(typescript@6.0.2))
|
||||||
@@ -367,22 +367,22 @@ packages:
|
|||||||
resolution: {integrity: sha512-ZJoS8oSq2CAZEpc/YI9SulLrdiIyXeHb/OGqGrkUP6Q7YV+0ouNAa7GjqRdXeQPncHQIDz/jbCTlHScvYvO/gA==}
|
resolution: {integrity: sha512-ZJoS8oSq2CAZEpc/YI9SulLrdiIyXeHb/OGqGrkUP6Q7YV+0ouNAa7GjqRdXeQPncHQIDz/jbCTlHScvYvO/gA==}
|
||||||
engines: {node: '>=v18'}
|
engines: {node: '>=v18'}
|
||||||
|
|
||||||
'@earendil-works/pi-agent-core@0.75.4':
|
'@earendil-works/pi-agent-core@0.79.9':
|
||||||
resolution: {integrity: sha512-cGYbysb4EqUf0B28OeqFq2ppm1XF3bYBOP71q9dv38yf/UJfzMjiXBeNelrcio+QWIoVrW+xzYm7sMzYIUc9Og==}
|
resolution: {integrity: sha512-GsFbPR85nhncKoU9++fTKa11PzwUkAmkrKXo97dBOzi10Td72rVV6vmfxKjwPLHTzRbJMa0byr12YhODZ59yLA==}
|
||||||
engines: {node: '>=22.19.0'}
|
engines: {node: '>=22.19.0'}
|
||||||
|
|
||||||
'@earendil-works/pi-ai@0.75.4':
|
'@earendil-works/pi-ai@0.79.9':
|
||||||
resolution: {integrity: sha512-m/w8Hh3vQ0rAycwJiJWdzkypkn4295f4eq/966lDRy8aX5sk6bgYXH8TQmL16TO7Uwc7MbJG0QoyFHgX8RqXUQ==}
|
resolution: {integrity: sha512-fHmgNMONwCCE7bQAKbcz76sgm3iQuA7km1mpIc4H5xXd9+zhPh/faULz6ARkgjQE0EufHnfZPJY39+lNf8Sa9g==}
|
||||||
engines: {node: '>=22.19.0'}
|
engines: {node: '>=22.19.0'}
|
||||||
hasBin: true
|
hasBin: true
|
||||||
|
|
||||||
'@earendil-works/pi-coding-agent@0.75.4':
|
'@earendil-works/pi-coding-agent@0.79.9':
|
||||||
resolution: {integrity: sha512-Fb+FRo08b5H9pYKbQJ708/5OKL0+K/yclhfCMEhrBzSPTZZ4c85nY1YsBo4qwL20ohBMlBezHMRuHzcJ1ylEoQ==}
|
resolution: {integrity: sha512-8TZ796Zn0NE4vmhxG9hv4ZtJDGJzhqMjlmFg8ZkUKxfqB7LJa4ums2jSJKtnyAZfAamN6VzqzN0A82RNDqv8Ag==}
|
||||||
engines: {node: '>=22.19.0'}
|
engines: {node: '>=22.19.0'}
|
||||||
hasBin: true
|
hasBin: true
|
||||||
|
|
||||||
'@earendil-works/pi-tui@0.75.4':
|
'@earendil-works/pi-tui@0.79.9':
|
||||||
resolution: {integrity: sha512-PDhKU7u6fmEcvHUFHzrRwGc/Ytokj/hO+X4RPf+MWKEGpvg3B1vHv88Ee+Dy33004tYkQF5YeXV4btJZcp5x1g==}
|
resolution: {integrity: sha512-XcqfoGyoX64OSMQklMR1vG2MRi1TCPSUERRCmPDvYKCK6LtZoBqJ6idNCLRklNYveCj4gHDOzOsLhGqn04jmYw==}
|
||||||
engines: {node: '>=22.19.0'}
|
engines: {node: '>=22.19.0'}
|
||||||
|
|
||||||
'@google/genai@1.52.0':
|
'@google/genai@1.52.0':
|
||||||
@@ -394,76 +394,81 @@ packages:
|
|||||||
'@modelcontextprotocol/sdk':
|
'@modelcontextprotocol/sdk':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-arm64@0.3.6':
|
'@mariozechner/clipboard-darwin-arm64@0.3.9':
|
||||||
resolution: {integrity: sha512-HjaisYCAbHi/1+N1yDAQHc8ZXGffufIUT5NSOSVR3f3AuMDusxTtnbK8tZ7JFDkShua1oNGZoNwQHsc8MPtE0Q==}
|
resolution: {integrity: sha512-BfgV7vCEWZwJwZJw03r6bP5+tf0iI/ANuQYCxi9RNn7FrWB3yzGuMKCrNLRl6V761vXRdL8+OqZ0wd4TqlsNOQ==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [darwin]
|
os: [darwin]
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-universal@0.3.6':
|
'@mariozechner/clipboard-darwin-universal@0.3.9':
|
||||||
resolution: {integrity: sha512-8BWtPjOtJOJoykml3w0fx0zRrfWP31mXrJwfoA7xzNprkZw1uolCNfgmjDiVBseoKjp16EGITz7bN+61qn8dWA==}
|
resolution: {integrity: sha512-BGGR4iA9Z2shAjI65eI5xtyb3LYNlDW9X3gxKxDbqtbnREohsrqznov6zpKoIrsRWpzlYVEdKphS7ksJ0/ndSQ==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
os: [darwin]
|
os: [darwin]
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-x64@0.3.6':
|
'@mariozechner/clipboard-darwin-x64@0.3.9':
|
||||||
resolution: {integrity: sha512-p9syiZD1kU4I+1ya7f7g+zD1GiUvR8fdlRlNmgsZNWlyjtc8rlV2EjTLd/35x1LsdBq020GVvtzp0ZmPgBI09Q==}
|
resolution: {integrity: sha512-4kURmCbS6nt8uYhtmWpUcJWyPHfmAr5dTpXD1nO3pIfa+TSQ9DbrGOYCKH+aEFW47XhQ4Vp8ZTszie+wfFvDKg==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [darwin]
|
os: [darwin]
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-arm64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-arm64-gnu@0.3.9':
|
||||||
resolution: {integrity: sha512-5JFf5rGofrm+V29HNF+wLthXphHdQpMbKDUYJ5tML6/Z5DLlLOV/9Ak4kDPtYyZ+Dzf+kAusE0VsFg4+tfP1IA==}
|
resolution: {integrity: sha512-g59OkUGP2DDfCOIKypHeYgv2M55u/cKvXa5dSxFbEJ34XvIQMdcVmpKCkGUro3ZgefXiGVdwguvTMQGpHWzIXw==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
libc: [glibc]
|
libc: [glibc]
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-arm64-musl@0.3.6':
|
'@mariozechner/clipboard-linux-arm64-musl@0.3.9':
|
||||||
resolution: {integrity: sha512-JlVjxxw0GbGC0djXYWRIqyteO3J1KZ/QG3udlEFaOD5TLOM1FnmXXAPDQBqr+aBVr720ef9K00dirYnJ0LDCtw==}
|
resolution: {integrity: sha512-AGuJdgKsmJdm4Pych7kv3sqe591ERRaAHW3xjLooiFzn8J+PxUyof++7YZrB5Y5tpnTO+K18Og3taj2NpluCRQ==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
libc: [musl]
|
libc: [musl]
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-riscv64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-riscv64-gnu@0.3.9':
|
||||||
resolution: {integrity: sha512-4t8BUi5zZ+L77otFQVnVSlaTyAX4TVk9EqQm4syMrEQp96trFEHEwwNHcNEBGzYv5+K7mxay50TthYkz47OWzQ==}
|
resolution: {integrity: sha512-DXBEAiuMpk7dhS1a9NzNxVAFi1vaKoPu7rQNgY8LIDLGrK3lnIp3nT10DUum+PKVJoJppIP+NAA8IZe4DMNDPw==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [riscv64]
|
cpu: [riscv64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
libc: [glibc]
|
libc: [glibc]
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-x64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-x64-gnu@0.3.9':
|
||||||
resolution: {integrity: sha512-trtPwcNLW37irwQCJLtCxLw757jjJZk3TSnY/MU9bhtWtA3K9b/eLW0e4RGhUXDoFRds9opNWWaUDuFLa8dm0w==}
|
resolution: {integrity: sha512-WORrMLd6EpElEME7JRKfSaY34nW1P5LbdgK5YNCS1ncG2LqmITsSMEJ8nh2mpvxb3TxqbOOKgY7k9eMJYlW9Mw==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
libc: [glibc]
|
libc: [glibc]
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-x64-musl@0.3.6':
|
'@mariozechner/clipboard-linux-x64-musl@0.3.9':
|
||||||
resolution: {integrity: sha512-WfnzIvOCCWQiN0MmltCEo6cLceUDbYe+I7xyFZjaps5A+2Op/M2CY7Rey+C4ucQhrvmpoHmTSFgY9ODWk7snoA==}
|
resolution: {integrity: sha512-/DHn+1DrfL6oRaPPWXaOKvonFFrni666fxd+zFqiQEfvBH0tsHVWjq9iqBk0oDp0qaPA72lIMy5BptxISBEhZQ==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
libc: [musl]
|
libc: [musl]
|
||||||
|
|
||||||
'@mariozechner/clipboard-win32-arm64-msvc@0.3.6':
|
'@mariozechner/clipboard-win32-arm64-msvc@0.3.9':
|
||||||
resolution: {integrity: sha512-+8+1aHYsBPUjmW3otmWlg+Hijt0iJvoBBs5e0mxFeUd4gDaKMB8Bn6x7c6KVtscg7E5j5NFXnwQqNSIAO4p8zQ==}
|
resolution: {integrity: sha512-O5FHD3ErkMwMhNzAfu3ggy0ug4z7btZuoQgwwxlzPrwV2bxlD6WDpqBY4NCgICAgZdDKdp+loUEKVAVt8aYnhQ==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [win32]
|
os: [win32]
|
||||||
|
|
||||||
'@mariozechner/clipboard-win32-x64-msvc@0.3.6':
|
'@mariozechner/clipboard-win32-x64-msvc@0.3.9':
|
||||||
resolution: {integrity: sha512-S4xfPmERC8ZkiLHe3vekZCjdDwNEETCuvCgQK2kP6/TnvmUkq1y2Pk+DjM4t8uh9KMX9bH4zs5ePcKa8GTXmfg==}
|
resolution: {integrity: sha512-ihQC3EufqEY81vhXBgVBtK4prL+wc62zJsSvxrgz7K1hsdt6OObz6v9p3Rn1OG3GJksTTKMJF0u/guMISHPhSA==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [win32]
|
os: [win32]
|
||||||
|
|
||||||
'@mariozechner/clipboard@0.3.6':
|
'@mariozechner/clipboard@0.3.9':
|
||||||
resolution: {integrity: sha512-MXdtr+6+ntlIVHdrZYuZNQydu6o8yZswFJ2Ln81j2O/Y9B/LDHvEaIm95xWNPkjGTWriSOeLnQJRFs6dYb60bg==}
|
resolution: {integrity: sha512-ABnA53mdfkGZwOFUdZNv2S0CWGO/EIuPj8Vv9xmBFmSYg/qFc7ihO6q5FcQjvoE67kZpWkEc4AhD6B/os04yuA==}
|
||||||
engines: {node: '>= 10'}
|
engines: {node: '>= 10'}
|
||||||
|
|
||||||
'@mistralai/mistralai@2.2.1':
|
'@mistralai/mistralai@2.2.6':
|
||||||
resolution: {integrity: sha512-uKU8CZmL2RzYKmplsU01hii4p3pe4HqJefpWNRWXm1Tcm0Sm4xXfwSLIy4k7ZCPlbETCGcp69E7hZs+WOJ5itQ==}
|
resolution: {integrity: sha512-W8pX7zHxjJvMIpw8JMxeJEleapXX0Q9NPszdNzqkM3MIEoIGPObdodujj+WHteXEvGfaP/AMwlNyRfEzSY6dQQ==}
|
||||||
|
peerDependencies:
|
||||||
|
'@opentelemetry/api': ^1.9.0
|
||||||
|
peerDependenciesMeta:
|
||||||
|
'@opentelemetry/api':
|
||||||
|
optional: true
|
||||||
|
|
||||||
'@nodable/entities@2.1.0':
|
'@nodable/entities@2.1.0':
|
||||||
resolution: {integrity: sha512-nyT7T3nbMyBI/lvr6L5TyWbFJAI9FTgVRakNoBqCD+PmID8DzFrrNdLLtHMwMszOtqZa8PAOV24ZqDnQrhQINA==}
|
resolution: {integrity: sha512-nyT7T3nbMyBI/lvr6L5TyWbFJAI9FTgVRakNoBqCD+PmID8DzFrrNdLLtHMwMszOtqZa8PAOV24ZqDnQrhQINA==}
|
||||||
@@ -516,6 +521,14 @@ packages:
|
|||||||
'@octokit/types@16.0.0':
|
'@octokit/types@16.0.0':
|
||||||
resolution: {integrity: sha512-sKq+9r1Mm4efXW1FCk7hFSeJo4QKreL/tTbR0rz/qx/r1Oa2VV83LTA/H/MuCOX7uCIJmQVRKBcbmWoySjAnSg==}
|
resolution: {integrity: sha512-sKq+9r1Mm4efXW1FCk7hFSeJo4QKreL/tTbR0rz/qx/r1Oa2VV83LTA/H/MuCOX7uCIJmQVRKBcbmWoySjAnSg==}
|
||||||
|
|
||||||
|
'@opentelemetry/api@1.9.0':
|
||||||
|
resolution: {integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==}
|
||||||
|
engines: {node: '>=8.0.0'}
|
||||||
|
|
||||||
|
'@opentelemetry/semantic-conventions@1.41.1':
|
||||||
|
resolution: {integrity: sha512-/UhIkaZgPutTFmQ7RnIJGgDXZmtEJ7Dvi86xNTFWcnRxVRNk/aotsqDJYeEvDP+FSMB2SdW+pQzNMcWP0rwuNA==}
|
||||||
|
engines: {node: '>=14'}
|
||||||
|
|
||||||
'@pnpm/config.env-replace@1.1.0':
|
'@pnpm/config.env-replace@1.1.0':
|
||||||
resolution: {integrity: sha512-htyl8TWnKL7K/ESFa1oW2UB5lVDxuF5DpM7tBi6Hu2LNL3mWkIzNLG6N4zoCUP1lCKNxWy/3iu8mS8MvToGd6w==}
|
resolution: {integrity: sha512-htyl8TWnKL7K/ESFa1oW2UB5lVDxuF5DpM7tBi6Hu2LNL3mWkIzNLG6N4zoCUP1lCKNxWy/3iu8mS8MvToGd6w==}
|
||||||
engines: {node: '>=12.22.0'}
|
engines: {node: '>=12.22.0'}
|
||||||
@@ -636,6 +649,10 @@ packages:
|
|||||||
resolution: {integrity: sha512-GGP3O9QFD24uGeAXYUjwSTXARoqpZykHadOmA8G5vfJPK0/DC67qa//0qvqrJzL1xc8WQWX7/yc7fwudjPHPhA==}
|
resolution: {integrity: sha512-GGP3O9QFD24uGeAXYUjwSTXARoqpZykHadOmA8G5vfJPK0/DC67qa//0qvqrJzL1xc8WQWX7/yc7fwudjPHPhA==}
|
||||||
engines: {node: '>=14.0.0'}
|
engines: {node: '>=14.0.0'}
|
||||||
|
|
||||||
|
'@smithy/node-http-handler@4.7.3':
|
||||||
|
resolution: {integrity: sha512-/jPhevcTFPMVl6KNjbaI47iOg1zxC7IsnX4PQDGVZKMFceOXtB8IEYaB7a9VvkP/3oC60WzTeKocvSI7vLT0vA==}
|
||||||
|
engines: {node: '>=18.0.0'}
|
||||||
|
|
||||||
'@smithy/node-http-handler@4.7.4':
|
'@smithy/node-http-handler@4.7.4':
|
||||||
resolution: {integrity: sha512-HIeF+1vrDGzPkkv39Hj2vlHSXHY3p958jd/8ZnePIY6+ZOsQX8coyEUKO5yQu4r0bQIVsbpotVIrXXwyycMStQ==}
|
resolution: {integrity: sha512-HIeF+1vrDGzPkkv39Hj2vlHSXHY3p958jd/8ZnePIY6+ZOsQX8coyEUKO5yQu4r0bQIVsbpotVIrXXwyycMStQ==}
|
||||||
engines: {node: '>=18.0.0'}
|
engines: {node: '>=18.0.0'}
|
||||||
@@ -644,10 +661,6 @@ packages:
|
|||||||
resolution: {integrity: sha512-e5UtkMvsatzBfbeBZjEOt0k0Z3BEsjTFL/n6fdO5vtBLe67tdy0dX7xw2DU7uZ3acwoHyeCqpU2Fzb7pxwHb6Q==}
|
resolution: {integrity: sha512-e5UtkMvsatzBfbeBZjEOt0k0Z3BEsjTFL/n6fdO5vtBLe67tdy0dX7xw2DU7uZ3acwoHyeCqpU2Fzb7pxwHb6Q==}
|
||||||
engines: {node: '>=18.0.0'}
|
engines: {node: '>=18.0.0'}
|
||||||
|
|
||||||
'@smithy/types@4.14.1':
|
|
||||||
resolution: {integrity: sha512-59b5HtSVrVR/eYNei3BUj3DCPKD/G7EtDDe7OEJE7i7FtQFugYo6MxbotS8mVJkLNVf8gYaAlEBwwtJ9HzhWSg==}
|
|
||||||
engines: {node: '>=18.0.0'}
|
|
||||||
|
|
||||||
'@smithy/types@4.14.2':
|
'@smithy/types@4.14.2':
|
||||||
resolution: {integrity: sha512-P+otAxbV4CqBybp7EkcJCrig63yE2E7PuNVOmilVMRcx/O+QDzGULTrKsq4DV13gSfak9ObPrWaHl/9bL5YcWw==}
|
resolution: {integrity: sha512-P+otAxbV4CqBybp7EkcJCrig63yE2E7PuNVOmilVMRcx/O+QDzGULTrKsq4DV13gSfak9ObPrWaHl/9bL5YcWw==}
|
||||||
engines: {node: '>=18.0.0'}
|
engines: {node: '>=18.0.0'}
|
||||||
@@ -1182,10 +1195,6 @@ packages:
|
|||||||
resolution: {integrity: sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==}
|
resolution: {integrity: sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==}
|
||||||
engines: {node: 6.* || 8.* || >= 10.*}
|
engines: {node: 6.* || 8.* || >= 10.*}
|
||||||
|
|
||||||
get-east-asian-width@1.5.0:
|
|
||||||
resolution: {integrity: sha512-CQ+bEO+Tva/qlmw24dCejulK5pMzVnUOFOijVogd3KQs07HnRIgp8TGipvCCRT06xeYEbpbgwaCxglFyiuIcmA==}
|
|
||||||
engines: {node: '>=18'}
|
|
||||||
|
|
||||||
get-east-asian-width@1.6.0:
|
get-east-asian-width@1.6.0:
|
||||||
resolution: {integrity: sha512-QRbvDIbx6YklUe6RxeTeleMR0yv3cYH6PsPZHcnVn7xv7zO1BHN8r0XETu8n6Ye3Q+ahtSarc3WgtNWmehIBfA==}
|
resolution: {integrity: sha512-QRbvDIbx6YklUe6RxeTeleMR0yv3cYH6PsPZHcnVn7xv7zO1BHN8r0XETu8n6Ye3Q+ahtSarc3WgtNWmehIBfA==}
|
||||||
engines: {node: '>=18'}
|
engines: {node: '>=18'}
|
||||||
@@ -1487,9 +1496,6 @@ packages:
|
|||||||
jws@4.0.1:
|
jws@4.0.1:
|
||||||
resolution: {integrity: sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA==}
|
resolution: {integrity: sha512-EKI/M/yqPncGUUh44xz0PxSidXFr/+r0pA70+gIYhjv+et7yxM+s29Y+VGDkovRofQem0fs7Uvf4+YmAdyRduA==}
|
||||||
|
|
||||||
koffi@2.16.2:
|
|
||||||
resolution: {integrity: sha512-owU0MRwv6xkrVqCd+33uw6BaYppkTRXbO/rVdJNI2dvZG0gzyRhYwW25eWtc5pauwK8TGh3AbkFONSezdykfSA==}
|
|
||||||
|
|
||||||
lefthook-darwin-arm64@2.1.6:
|
lefthook-darwin-arm64@2.1.6:
|
||||||
resolution: {integrity: sha512-hyB7eeiX78BS66f70byTJacDLC/xV1vgMv9n+idFUsrM7J3Udd/ag9Ag5NP3t0eN0EqQqAtrNnt35EH01lxnRQ==}
|
resolution: {integrity: sha512-hyB7eeiX78BS66f70byTJacDLC/xV1vgMv9n+idFUsrM7J3Udd/ag9Ag5NP3t0eN0EqQqAtrNnt35EH01lxnRQ==}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
@@ -1640,6 +1646,11 @@ packages:
|
|||||||
engines: {node: '>= 18'}
|
engines: {node: '>= 18'}
|
||||||
hasBin: true
|
hasBin: true
|
||||||
|
|
||||||
|
marked@18.0.5:
|
||||||
|
resolution: {integrity: sha512-S6GcvALHg6K4ohtu4E7x0a1AqhAjp6cV8KhLSyN9qVapnzJkusVBxZRcIU9AeYsbe6P1hKDusSbEOzGyyuce6w==}
|
||||||
|
engines: {node: '>= 20'}
|
||||||
|
hasBin: true
|
||||||
|
|
||||||
meow@12.1.1:
|
meow@12.1.1:
|
||||||
resolution: {integrity: sha512-BhXM0Au22RwUneMPwSCnyhTOizdWoIEPU9sp0Aqa1PnDMR5Wv2FGXYDjuzJEIX+Eo2Rb8xuYe5jrnm5QowQFkw==}
|
resolution: {integrity: sha512-BhXM0Au22RwUneMPwSCnyhTOizdWoIEPU9sp0Aqa1PnDMR5Wv2FGXYDjuzJEIX+Eo2Rb8xuYe5jrnm5QowQFkw==}
|
||||||
engines: {node: '>=16.10'}
|
engines: {node: '>=16.10'}
|
||||||
@@ -2107,6 +2118,11 @@ packages:
|
|||||||
engines: {node: '>=10'}
|
engines: {node: '>=10'}
|
||||||
hasBin: true
|
hasBin: true
|
||||||
|
|
||||||
|
semver@7.8.0:
|
||||||
|
resolution: {integrity: sha512-AcM7dV/5ul4EekoQ29Agm5vri8JNqRyj39o0qpX6vDF2GZrtutZl5RwgD1XnZjiTAfncsJhMI48QQH3sN87YNA==}
|
||||||
|
engines: {node: '>=10'}
|
||||||
|
hasBin: true
|
||||||
|
|
||||||
shebang-command@2.0.0:
|
shebang-command@2.0.0:
|
||||||
resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==}
|
resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==}
|
||||||
engines: {node: '>=8'}
|
engines: {node: '>=8'}
|
||||||
@@ -2350,8 +2366,8 @@ packages:
|
|||||||
resolution: {integrity: sha512-xXnp4kTyor2Zq+J1FfPI6Eq3ew5h6Vl0F/8d9XU5zZQf1tX9s2Su1/3PiMmUANFULpmksxkClamIZcaUqryHsQ==}
|
resolution: {integrity: sha512-xXnp4kTyor2Zq+J1FfPI6Eq3ew5h6Vl0F/8d9XU5zZQf1tX9s2Su1/3PiMmUANFULpmksxkClamIZcaUqryHsQ==}
|
||||||
engines: {node: '>=20.18.1'}
|
engines: {node: '>=20.18.1'}
|
||||||
|
|
||||||
undici@8.3.0:
|
undici@8.5.0:
|
||||||
resolution: {integrity: sha512-TkUDgb6tl7KOGZ+7e8E3d2FYgUQgF6z5YypqjWmixVQSQERFcVrVg0ySADm2LVLRh5ljAaHTCR5Fmz3Q34rB7Q==}
|
resolution: {integrity: sha512-xamtWoB1EshgjpmlXd7GGm2VfdDtw1+rD8uhry8pSNW3If6S8E0m2T2+orSKeZXEn/aPJMviCpDBA65WJt8zhg==}
|
||||||
engines: {node: '>=22.19.0'}
|
engines: {node: '>=22.19.0'}
|
||||||
|
|
||||||
unicode-emoji-modifier-base@1.0.0:
|
unicode-emoji-modifier-base@1.0.0:
|
||||||
@@ -2572,7 +2588,7 @@ snapshots:
|
|||||||
'@smithy/core': 3.24.4
|
'@smithy/core': 3.24.4
|
||||||
'@smithy/fetch-http-handler': 5.4.4
|
'@smithy/fetch-http-handler': 5.4.4
|
||||||
'@smithy/node-http-handler': 4.7.4
|
'@smithy/node-http-handler': 4.7.4
|
||||||
'@smithy/types': 4.14.1
|
'@smithy/types': 4.14.2
|
||||||
tslib: 2.8.1
|
tslib: 2.8.1
|
||||||
|
|
||||||
'@aws-sdk/core@3.974.13':
|
'@aws-sdk/core@3.974.13':
|
||||||
@@ -2721,7 +2737,7 @@ snapshots:
|
|||||||
'@aws-sdk/nested-clients': 3.997.11
|
'@aws-sdk/nested-clients': 3.997.11
|
||||||
'@aws-sdk/types': 3.973.9
|
'@aws-sdk/types': 3.973.9
|
||||||
'@smithy/core': 3.24.4
|
'@smithy/core': 3.24.4
|
||||||
'@smithy/types': 4.14.1
|
'@smithy/types': 4.14.2
|
||||||
tslib: 2.8.1
|
tslib: 2.8.1
|
||||||
|
|
||||||
'@aws-sdk/token-providers@3.1052.0':
|
'@aws-sdk/token-providers@3.1052.0':
|
||||||
@@ -2962,9 +2978,9 @@ snapshots:
|
|||||||
picocolors: 1.1.1
|
picocolors: 1.1.1
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@earendil-works/pi-agent-core@0.75.4(ws@8.20.0)(zod@4.3.6)':
|
'@earendil-works/pi-agent-core@0.79.9(ws@8.20.0)(zod@4.3.6)':
|
||||||
dependencies:
|
dependencies:
|
||||||
'@earendil-works/pi-ai': 0.75.4(ws@8.20.0)(zod@4.3.6)
|
'@earendil-works/pi-ai': 0.79.9(ws@8.20.0)(zod@4.3.6)
|
||||||
ignore: 7.0.5
|
ignore: 7.0.5
|
||||||
typebox: 1.1.38
|
typebox: 1.1.38
|
||||||
yaml: 2.9.0
|
yaml: 2.9.0
|
||||||
@@ -2976,12 +2992,14 @@ snapshots:
|
|||||||
- ws
|
- ws
|
||||||
- zod
|
- zod
|
||||||
|
|
||||||
'@earendil-works/pi-ai@0.75.4(ws@8.20.0)(zod@4.3.6)':
|
'@earendil-works/pi-ai@0.79.9(ws@8.20.0)(zod@4.3.6)':
|
||||||
dependencies:
|
dependencies:
|
||||||
'@anthropic-ai/sdk': 0.91.1(zod@4.3.6)
|
'@anthropic-ai/sdk': 0.91.1(zod@4.3.6)
|
||||||
'@aws-sdk/client-bedrock-runtime': 3.1048.0
|
'@aws-sdk/client-bedrock-runtime': 3.1048.0
|
||||||
'@google/genai': 1.52.0
|
'@google/genai': 1.52.0
|
||||||
'@mistralai/mistralai': 2.2.1
|
'@mistralai/mistralai': 2.2.6(@opentelemetry/api@1.9.0)
|
||||||
|
'@opentelemetry/api': 1.9.0
|
||||||
|
'@smithy/node-http-handler': 4.7.3
|
||||||
http-proxy-agent: 7.0.2
|
http-proxy-agent: 7.0.2
|
||||||
https-proxy-agent: 7.0.6
|
https-proxy-agent: 7.0.6
|
||||||
openai: 6.26.0(ws@8.20.0)(zod@4.3.6)
|
openai: 6.26.0(ws@8.20.0)(zod@4.3.6)
|
||||||
@@ -2995,11 +3013,11 @@ snapshots:
|
|||||||
- ws
|
- ws
|
||||||
- zod
|
- zod
|
||||||
|
|
||||||
'@earendil-works/pi-coding-agent@0.75.4(ws@8.20.0)(zod@4.3.6)':
|
'@earendil-works/pi-coding-agent@0.79.9(ws@8.20.0)(zod@4.3.6)':
|
||||||
dependencies:
|
dependencies:
|
||||||
'@earendil-works/pi-agent-core': 0.75.4(ws@8.20.0)(zod@4.3.6)
|
'@earendil-works/pi-agent-core': 0.79.9(ws@8.20.0)(zod@4.3.6)
|
||||||
'@earendil-works/pi-ai': 0.75.4(ws@8.20.0)(zod@4.3.6)
|
'@earendil-works/pi-ai': 0.79.9(ws@8.20.0)(zod@4.3.6)
|
||||||
'@earendil-works/pi-tui': 0.75.4
|
'@earendil-works/pi-tui': 0.79.9
|
||||||
'@silvia-odwyer/photon-node': 0.3.4
|
'@silvia-odwyer/photon-node': 0.3.4
|
||||||
chalk: 5.6.2
|
chalk: 5.6.2
|
||||||
cross-spawn: 7.0.6
|
cross-spawn: 7.0.6
|
||||||
@@ -3011,11 +3029,12 @@ snapshots:
|
|||||||
jiti: 2.7.0
|
jiti: 2.7.0
|
||||||
minimatch: 10.2.5
|
minimatch: 10.2.5
|
||||||
proper-lockfile: 4.1.2
|
proper-lockfile: 4.1.2
|
||||||
|
semver: 7.8.0
|
||||||
typebox: 1.1.38
|
typebox: 1.1.38
|
||||||
undici: 8.3.0
|
undici: 8.5.0
|
||||||
yaml: 2.9.0
|
yaml: 2.9.0
|
||||||
optionalDependencies:
|
optionalDependencies:
|
||||||
'@mariozechner/clipboard': 0.3.6
|
'@mariozechner/clipboard': 0.3.9
|
||||||
transitivePeerDependencies:
|
transitivePeerDependencies:
|
||||||
- '@modelcontextprotocol/sdk'
|
- '@modelcontextprotocol/sdk'
|
||||||
- bufferutil
|
- bufferutil
|
||||||
@@ -3024,12 +3043,10 @@ snapshots:
|
|||||||
- ws
|
- ws
|
||||||
- zod
|
- zod
|
||||||
|
|
||||||
'@earendil-works/pi-tui@0.75.4':
|
'@earendil-works/pi-tui@0.79.9':
|
||||||
dependencies:
|
dependencies:
|
||||||
get-east-asian-width: 1.6.0
|
get-east-asian-width: 1.6.0
|
||||||
marked: 15.0.12
|
marked: 18.0.5
|
||||||
optionalDependencies:
|
|
||||||
koffi: 2.16.2
|
|
||||||
|
|
||||||
'@google/genai@1.52.0':
|
'@google/genai@1.52.0':
|
||||||
dependencies:
|
dependencies:
|
||||||
@@ -3042,55 +3059,58 @@ snapshots:
|
|||||||
- supports-color
|
- supports-color
|
||||||
- utf-8-validate
|
- utf-8-validate
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-arm64@0.3.6':
|
'@mariozechner/clipboard-darwin-arm64@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-universal@0.3.6':
|
'@mariozechner/clipboard-darwin-universal@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-darwin-x64@0.3.6':
|
'@mariozechner/clipboard-darwin-x64@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-arm64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-arm64-gnu@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-arm64-musl@0.3.6':
|
'@mariozechner/clipboard-linux-arm64-musl@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-riscv64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-riscv64-gnu@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-x64-gnu@0.3.6':
|
'@mariozechner/clipboard-linux-x64-gnu@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-linux-x64-musl@0.3.6':
|
'@mariozechner/clipboard-linux-x64-musl@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-win32-arm64-msvc@0.3.6':
|
'@mariozechner/clipboard-win32-arm64-msvc@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard-win32-x64-msvc@0.3.6':
|
'@mariozechner/clipboard-win32-x64-msvc@0.3.9':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mariozechner/clipboard@0.3.6':
|
'@mariozechner/clipboard@0.3.9':
|
||||||
optionalDependencies:
|
optionalDependencies:
|
||||||
'@mariozechner/clipboard-darwin-arm64': 0.3.6
|
'@mariozechner/clipboard-darwin-arm64': 0.3.9
|
||||||
'@mariozechner/clipboard-darwin-universal': 0.3.6
|
'@mariozechner/clipboard-darwin-universal': 0.3.9
|
||||||
'@mariozechner/clipboard-darwin-x64': 0.3.6
|
'@mariozechner/clipboard-darwin-x64': 0.3.9
|
||||||
'@mariozechner/clipboard-linux-arm64-gnu': 0.3.6
|
'@mariozechner/clipboard-linux-arm64-gnu': 0.3.9
|
||||||
'@mariozechner/clipboard-linux-arm64-musl': 0.3.6
|
'@mariozechner/clipboard-linux-arm64-musl': 0.3.9
|
||||||
'@mariozechner/clipboard-linux-riscv64-gnu': 0.3.6
|
'@mariozechner/clipboard-linux-riscv64-gnu': 0.3.9
|
||||||
'@mariozechner/clipboard-linux-x64-gnu': 0.3.6
|
'@mariozechner/clipboard-linux-x64-gnu': 0.3.9
|
||||||
'@mariozechner/clipboard-linux-x64-musl': 0.3.6
|
'@mariozechner/clipboard-linux-x64-musl': 0.3.9
|
||||||
'@mariozechner/clipboard-win32-arm64-msvc': 0.3.6
|
'@mariozechner/clipboard-win32-arm64-msvc': 0.3.9
|
||||||
'@mariozechner/clipboard-win32-x64-msvc': 0.3.6
|
'@mariozechner/clipboard-win32-x64-msvc': 0.3.9
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@mistralai/mistralai@2.2.1':
|
'@mistralai/mistralai@2.2.6(@opentelemetry/api@1.9.0)':
|
||||||
dependencies:
|
dependencies:
|
||||||
|
'@opentelemetry/semantic-conventions': 1.41.1
|
||||||
ws: 8.20.0
|
ws: 8.20.0
|
||||||
zod: 4.3.6
|
zod: 4.3.6
|
||||||
zod-to-json-schema: 3.25.2(zod@4.3.6)
|
zod-to-json-schema: 3.25.2(zod@4.3.6)
|
||||||
|
optionalDependencies:
|
||||||
|
'@opentelemetry/api': 1.9.0
|
||||||
transitivePeerDependencies:
|
transitivePeerDependencies:
|
||||||
- bufferutil
|
- bufferutil
|
||||||
- utf-8-validate
|
- utf-8-validate
|
||||||
@@ -3157,6 +3177,10 @@ snapshots:
|
|||||||
dependencies:
|
dependencies:
|
||||||
'@octokit/openapi-types': 27.0.0
|
'@octokit/openapi-types': 27.0.0
|
||||||
|
|
||||||
|
'@opentelemetry/api@1.9.0': {}
|
||||||
|
|
||||||
|
'@opentelemetry/semantic-conventions@1.41.1': {}
|
||||||
|
|
||||||
'@pnpm/config.env-replace@1.1.0': {}
|
'@pnpm/config.env-replace@1.1.0': {}
|
||||||
|
|
||||||
'@pnpm/network.ca-file@1.0.2':
|
'@pnpm/network.ca-file@1.0.2':
|
||||||
@@ -3322,6 +3346,12 @@ snapshots:
|
|||||||
dependencies:
|
dependencies:
|
||||||
tslib: 2.8.1
|
tslib: 2.8.1
|
||||||
|
|
||||||
|
'@smithy/node-http-handler@4.7.3':
|
||||||
|
dependencies:
|
||||||
|
'@smithy/core': 3.24.4
|
||||||
|
'@smithy/types': 4.14.2
|
||||||
|
tslib: 2.8.1
|
||||||
|
|
||||||
'@smithy/node-http-handler@4.7.4':
|
'@smithy/node-http-handler@4.7.4':
|
||||||
dependencies:
|
dependencies:
|
||||||
'@smithy/core': 3.24.4
|
'@smithy/core': 3.24.4
|
||||||
@@ -3334,10 +3364,6 @@ snapshots:
|
|||||||
'@smithy/types': 4.14.2
|
'@smithy/types': 4.14.2
|
||||||
tslib: 2.8.1
|
tslib: 2.8.1
|
||||||
|
|
||||||
'@smithy/types@4.14.1':
|
|
||||||
dependencies:
|
|
||||||
tslib: 2.8.1
|
|
||||||
|
|
||||||
'@smithy/types@4.14.2':
|
'@smithy/types@4.14.2':
|
||||||
dependencies:
|
dependencies:
|
||||||
tslib: 2.8.1
|
tslib: 2.8.1
|
||||||
@@ -3902,8 +3928,6 @@ snapshots:
|
|||||||
|
|
||||||
get-caller-file@2.0.5: {}
|
get-caller-file@2.0.5: {}
|
||||||
|
|
||||||
get-east-asian-width@1.5.0: {}
|
|
||||||
|
|
||||||
get-east-asian-width@1.6.0: {}
|
get-east-asian-width@1.6.0: {}
|
||||||
|
|
||||||
get-stream@6.0.1: {}
|
get-stream@6.0.1: {}
|
||||||
@@ -4195,9 +4219,6 @@ snapshots:
|
|||||||
jwa: 2.0.1
|
jwa: 2.0.1
|
||||||
safe-buffer: 5.2.1
|
safe-buffer: 5.2.1
|
||||||
|
|
||||||
koffi@2.16.2:
|
|
||||||
optional: true
|
|
||||||
|
|
||||||
lefthook-darwin-arm64@2.1.6:
|
lefthook-darwin-arm64@2.1.6:
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
@@ -4323,6 +4344,8 @@ snapshots:
|
|||||||
|
|
||||||
marked@15.0.12: {}
|
marked@15.0.12: {}
|
||||||
|
|
||||||
|
marked@18.0.5: {}
|
||||||
|
|
||||||
meow@12.1.1: {}
|
meow@12.1.1: {}
|
||||||
|
|
||||||
meow@13.2.0: {}
|
meow@13.2.0: {}
|
||||||
@@ -4393,7 +4416,7 @@ snapshots:
|
|||||||
|
|
||||||
normalize-package-data@8.0.0:
|
normalize-package-data@8.0.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
hosted-git-info: 9.0.2
|
hosted-git-info: 9.0.3
|
||||||
semver: 7.7.4
|
semver: 7.7.4
|
||||||
validate-npm-package-license: 3.0.4
|
validate-npm-package-license: 3.0.4
|
||||||
|
|
||||||
@@ -4722,6 +4745,8 @@ snapshots:
|
|||||||
|
|
||||||
semver@7.7.4: {}
|
semver@7.7.4: {}
|
||||||
|
|
||||||
|
semver@7.8.0: {}
|
||||||
|
|
||||||
shebang-command@2.0.0:
|
shebang-command@2.0.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
shebang-regex: 3.0.0
|
shebang-regex: 3.0.0
|
||||||
@@ -4782,7 +4807,7 @@ snapshots:
|
|||||||
string-width@7.2.0:
|
string-width@7.2.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
emoji-regex: 10.6.0
|
emoji-regex: 10.6.0
|
||||||
get-east-asian-width: 1.5.0
|
get-east-asian-width: 1.6.0
|
||||||
strip-ansi: 7.2.0
|
strip-ansi: 7.2.0
|
||||||
|
|
||||||
string_decoder@1.1.1:
|
string_decoder@1.1.1:
|
||||||
@@ -4928,7 +4953,7 @@ snapshots:
|
|||||||
|
|
||||||
undici@7.25.0: {}
|
undici@7.25.0: {}
|
||||||
|
|
||||||
undici@8.3.0: {}
|
undici@8.5.0: {}
|
||||||
|
|
||||||
unicode-emoji-modifier-base@1.0.0: {}
|
unicode-emoji-modifier-base@1.0.0: {}
|
||||||
|
|
||||||
|
|||||||
@@ -79,8 +79,8 @@ async function runAnswerCommand(
|
|||||||
ctx: ExtensionCommandContext,
|
ctx: ExtensionCommandContext,
|
||||||
remoteAsk?: RemoteAskRuntime
|
remoteAsk?: RemoteAskRuntime
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
if (!ctx.hasUI) {
|
if (ctx.mode !== "tui") {
|
||||||
ctx.ui.notify("/answer requires interactive UI.", "error");
|
ctx.ui.notify("/answer requires interactive TUI mode.", "error");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -253,8 +253,8 @@ async function runReplayCommand(
|
|||||||
source: AskPayloadSource;
|
source: AskPayloadSource;
|
||||||
}
|
}
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
if (!ctx.hasUI) {
|
if (ctx.mode !== "tui") {
|
||||||
ctx.ui.notify("Ask replay requires interactive UI.", "error");
|
ctx.ui.notify("Ask replay requires interactive TUI mode.", "error");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const lookup = findLatestPayloadInCurrentBranch(ctx, options.source);
|
const lookup = findLatestPayloadInCurrentBranch(ctx, options.source);
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ export function registerAskSettingsCommand(pi: ExtensionAPI) {
|
|||||||
pi.registerCommand("ask-settings", {
|
pi.registerCommand("ask-settings", {
|
||||||
description: "Open ask settings",
|
description: "Open ask settings",
|
||||||
handler: async (_args: string, ctx: ExtensionCommandContext) => {
|
handler: async (_args: string, ctx: ExtensionCommandContext) => {
|
||||||
await showAskSettings(ctx.ui);
|
await showAskSettings(ctx);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -153,8 +153,8 @@ function formatNonInteractiveMessage(
|
|||||||
state: ReturnType<typeof createInitialState>
|
state: ReturnType<typeof createInitialState>
|
||||||
): string {
|
): string {
|
||||||
const lines = [
|
const lines = [
|
||||||
"Needs user input: ask_user requires interactive UI.",
|
"Needs user input: ask_user requires interactive TUI mode.",
|
||||||
"Run same tool call in interactive session, or ask user these questions manually:",
|
"Run same tool call in interactive TUI mode, or ask user these questions manually:",
|
||||||
];
|
];
|
||||||
|
|
||||||
for (const [index, question] of state.questions.entries()) {
|
for (const [index, question] of state.questions.entries()) {
|
||||||
|
|||||||
+1
-1
@@ -67,7 +67,7 @@ async function executeAskTool(
|
|||||||
source: "tool",
|
source: "tool",
|
||||||
sourceEntryId: toolCallId,
|
sourceEntryId: toolCallId,
|
||||||
});
|
});
|
||||||
if (!ctx.hasUI) {
|
if (ctx.mode !== "tui") {
|
||||||
return nonInteractiveResponse(validation.state);
|
return nonInteractiveResponse(validation.state);
|
||||||
}
|
}
|
||||||
ctx.ui.setWorkingVisible(false);
|
ctx.ui.setWorkingVisible(false);
|
||||||
|
|||||||
@@ -171,6 +171,10 @@ export function getAskConfigStore(): AskConfigStore {
|
|||||||
return askConfigStore;
|
return askConfigStore;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function resetAskConfigStore(): void {
|
||||||
|
askConfigStore = undefined;
|
||||||
|
}
|
||||||
|
|
||||||
export function getAskConfigPath(): string {
|
export function getAskConfigPath(): string {
|
||||||
return join(getAgentDir(), "extensions", "eko24ive-pi-ask.json");
|
return join(getAgentDir(), "extensions", "eko24ive-pi-ask.json");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import type { ExtensionAPI } from "@earendil-works/pi-coding-agent";
|
|||||||
import { registerAnswerCommands } from "./answer-commands.ts";
|
import { registerAnswerCommands } from "./answer-commands.ts";
|
||||||
import { registerAskSettingsCommand } from "./ask-settings-command.ts";
|
import { registerAskSettingsCommand } from "./ask-settings-command.ts";
|
||||||
import { registerAskTool } from "./ask-tool.ts";
|
import { registerAskTool } from "./ask-tool.ts";
|
||||||
|
import { resetAskConfigStore } from "./config/store.ts";
|
||||||
import { createRemoteAskRuntime } from "./remote-ask.ts";
|
import { createRemoteAskRuntime } from "./remote-ask.ts";
|
||||||
|
|
||||||
const PACKAGE_ROOT = resolve(dirname(fileURLToPath(import.meta.url)), "..");
|
const PACKAGE_ROOT = resolve(dirname(fileURLToPath(import.meta.url)), "..");
|
||||||
@@ -15,10 +16,14 @@ const CONFIGURATION_DOC_PATH = resolve(
|
|||||||
const PI_ASK_CONFIG_PROMPT = `When the user asks to configure, customize, debug, or explain @eko24ive/pi-ask settings or keymaps, first read ${CONFIGURATION_DOC_PATH} and follow it as the source of truth before editing config files.`;
|
const PI_ASK_CONFIG_PROMPT = `When the user asks to configure, customize, debug, or explain @eko24ive/pi-ask settings or keymaps, first read ${CONFIGURATION_DOC_PATH} and follow it as the source of truth before editing config files.`;
|
||||||
|
|
||||||
export default function askExtension(pi: ExtensionAPI) {
|
export default function askExtension(pi: ExtensionAPI) {
|
||||||
|
resetAskConfigStore();
|
||||||
pi.on("before_agent_start", async (event) => ({
|
pi.on("before_agent_start", async (event) => ({
|
||||||
systemPrompt: `${event.systemPrompt}\n\n${PI_ASK_CONFIG_PROMPT}`,
|
systemPrompt: `${event.systemPrompt}\n\n${PI_ASK_CONFIG_PROMPT}`,
|
||||||
}));
|
}));
|
||||||
const remoteAsk = createRemoteAskRuntime(pi.events);
|
const remoteAsk = createRemoteAskRuntime(pi.events);
|
||||||
|
pi.on("session_shutdown", () => {
|
||||||
|
remoteAsk.disposeAll();
|
||||||
|
});
|
||||||
registerAskTool(pi, remoteAsk);
|
registerAskTool(pi, remoteAsk);
|
||||||
registerAskSettingsCommand(pi);
|
registerAskSettingsCommand(pi);
|
||||||
registerAnswerCommands(pi, remoteAsk);
|
registerAnswerCommands(pi, remoteAsk);
|
||||||
|
|||||||
+6
-2
@@ -95,6 +95,7 @@ export interface RemoteAskFlowHandle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface RemoteAskRuntime {
|
export interface RemoteAskRuntime {
|
||||||
|
disposeAll: () => void;
|
||||||
startFlow: (flow: RemoteAskFlowInput) => RemoteAskFlowHandle;
|
startFlow: (flow: RemoteAskFlowInput) => RemoteAskFlowHandle;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -102,12 +103,15 @@ type EventBus = ExtensionAPI["events"];
|
|||||||
|
|
||||||
export function createRemoteAskRuntime(events: EventBus): RemoteAskRuntime {
|
export function createRemoteAskRuntime(events: EventBus): RemoteAskRuntime {
|
||||||
const activeFlows = new Map<string, ActiveRemoteAskFlow>();
|
const activeFlows = new Map<string, ActiveRemoteAskFlow>();
|
||||||
|
const unsubscribeSubmit = events.on(PI_ASK_SUBMIT_EVENT, (data) => {
|
||||||
events.on(PI_ASK_SUBMIT_EVENT, (data) => {
|
|
||||||
handleSubmitEvent(events, activeFlows, data);
|
handleSubmitEvent(events, activeFlows, data);
|
||||||
});
|
});
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
disposeAll() {
|
||||||
|
activeFlows.clear();
|
||||||
|
unsubscribeSubmit();
|
||||||
|
},
|
||||||
startFlow(flow) {
|
startFlow(flow) {
|
||||||
return startRemoteAskFlow(events, activeFlows, flow);
|
return startRemoteAskFlow(events, activeFlows, flow);
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -13,10 +13,13 @@ const FD_BINARY_NAMES =
|
|||||||
* themselves when reusing CombinedAutocompleteProvider for `@` file mentions.
|
* themselves when reusing CombinedAutocompleteProvider for `@` file mentions.
|
||||||
*/
|
*/
|
||||||
export function createAskAutocompleteProvider(cwd: string) {
|
export function createAskAutocompleteProvider(cwd: string) {
|
||||||
return new CombinedAutocompleteProvider(
|
return Object.assign(
|
||||||
|
new CombinedAutocompleteProvider(
|
||||||
[],
|
[],
|
||||||
cwd,
|
cwd,
|
||||||
findAutocompleteBinary(FD_BINARY_NAMES)
|
findAutocompleteBinary(FD_BINARY_NAMES)
|
||||||
|
),
|
||||||
|
{ triggerCharacters: ["@"] }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+14
-2
@@ -113,6 +113,12 @@ export async function runAskFlow(
|
|||||||
presentSingleAsMulti:
|
presentSingleAsMulti:
|
||||||
options.presentSingleAsMulti ?? config.behaviour.presentSingleAsMulti,
|
options.presentSingleAsMulti ?? config.behaviour.presentSingleAsMulti,
|
||||||
};
|
};
|
||||||
|
if (ctx.mode !== "tui") {
|
||||||
|
return {
|
||||||
|
...toAskResult(createInitialState(params, flowOptions)),
|
||||||
|
cancelled: true,
|
||||||
|
};
|
||||||
|
}
|
||||||
return ctx.ui.custom<AskResult>((...args) =>
|
return ctx.ui.custom<AskResult>((...args) =>
|
||||||
createAskFlowController(args, {
|
createAskFlowController(args, {
|
||||||
...params,
|
...params,
|
||||||
@@ -172,9 +178,15 @@ function createAskFlowController(
|
|||||||
});
|
});
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
get focused() {
|
||||||
|
return controller.editor.focused;
|
||||||
|
},
|
||||||
|
set focused(value: boolean) {
|
||||||
|
controller.editor.focused = value;
|
||||||
|
},
|
||||||
render: (width: number) => renderController(controller, width),
|
render: (width: number) => renderController(controller, width),
|
||||||
invalidate() {
|
invalidate() {
|
||||||
// The editor manages its own async autocomplete redraws.
|
controller.editor.invalidate();
|
||||||
},
|
},
|
||||||
handleInput(data: string) {
|
handleInput(data: string) {
|
||||||
handleControllerInput(controller, data);
|
handleControllerInput(controller, data);
|
||||||
@@ -536,7 +548,7 @@ function showSettingsModal(controller: AskFlowController) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
controller.settingsOpen = true;
|
controller.settingsOpen = true;
|
||||||
showAskSettings(controller.ctx.ui).finally(() => {
|
showAskSettings(controller.ctx).finally(() => {
|
||||||
controller.settingsOpen = false;
|
controller.settingsOpen = false;
|
||||||
refresh(controller);
|
refresh(controller);
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -3,11 +3,15 @@ import { getAskConfigPath, getAskConfigStore } from "../config/store.ts";
|
|||||||
import { AskSettingsList } from "./settings-list.ts";
|
import { AskSettingsList } from "./settings-list.ts";
|
||||||
|
|
||||||
export async function showAskSettings(
|
export async function showAskSettings(
|
||||||
ui: Pick<ExtensionContext, "ui">["ui"]
|
ctx: Pick<ExtensionContext, "mode" | "ui">
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
|
if (ctx.mode !== "tui") {
|
||||||
|
ctx.ui.notify("/ask-settings requires interactive TUI mode.", "error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
const store = getAskConfigStore();
|
const store = getAskConfigStore();
|
||||||
const { config, notice } = await store.ensureLoaded();
|
const { config, notice } = await store.ensureLoaded();
|
||||||
return ui.custom<void>(
|
return ctx.ui.custom<void>(
|
||||||
(tui, theme, _keybindings, done) =>
|
(tui, theme, _keybindings, done) =>
|
||||||
new AskSettingsList(theme, {
|
new AskSettingsList(theme, {
|
||||||
configPath: getAskConfigPath(),
|
configPath: getAskConfigPath(),
|
||||||
|
|||||||
@@ -0,0 +1,47 @@
|
|||||||
|
import assert from "node:assert/strict";
|
||||||
|
import test from "node:test";
|
||||||
|
import { registerAnswerCommands } from "../src/answer-commands.ts";
|
||||||
|
|
||||||
|
function registerCommands() {
|
||||||
|
const commands = new Map<
|
||||||
|
string,
|
||||||
|
{ handler: (args: string, ctx: any) => Promise<void> }
|
||||||
|
>();
|
||||||
|
registerAnswerCommands({
|
||||||
|
registerCommand(
|
||||||
|
name: string,
|
||||||
|
command: { handler: (args: string, ctx: any) => Promise<void> }
|
||||||
|
) {
|
||||||
|
commands.set(name, command);
|
||||||
|
},
|
||||||
|
} as never);
|
||||||
|
return commands;
|
||||||
|
}
|
||||||
|
|
||||||
|
test("answer commands do not open custom UI outside TUI mode", async () => {
|
||||||
|
const commands = registerCommands();
|
||||||
|
const notifications: Array<{ message: string; type: string }> = [];
|
||||||
|
let customOpened = false;
|
||||||
|
const ctx = {
|
||||||
|
mode: "rpc",
|
||||||
|
ui: {
|
||||||
|
custom() {
|
||||||
|
customOpened = true;
|
||||||
|
},
|
||||||
|
notify(message: string, type: string) {
|
||||||
|
notifications.push({ message, type });
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
await commands.get("answer")?.handler("", ctx);
|
||||||
|
await commands.get("answer:again")?.handler("", ctx);
|
||||||
|
await commands.get("ask:replay")?.handler("", ctx);
|
||||||
|
|
||||||
|
assert.equal(customOpened, false);
|
||||||
|
assert.deepEqual(notifications, [
|
||||||
|
{ message: "/answer requires interactive TUI mode.", type: "error" },
|
||||||
|
{ message: "Ask replay requires interactive TUI mode.", type: "error" },
|
||||||
|
{ message: "Ask replay requires interactive TUI mode.", type: "error" },
|
||||||
|
]);
|
||||||
|
});
|
||||||
@@ -37,6 +37,7 @@ test("registers /ask-settings and opens the shared settings overlay", async () =
|
|||||||
|
|
||||||
const customCalls: Array<{ options: unknown; lines: string[] }> = [];
|
const customCalls: Array<{ options: unknown; lines: string[] }> = [];
|
||||||
await commands.get("ask-settings")?.handler("", {
|
await commands.get("ask-settings")?.handler("", {
|
||||||
|
mode: "tui",
|
||||||
ui: {
|
ui: {
|
||||||
custom(callback: any, options: unknown) {
|
custom(callback: any, options: unknown) {
|
||||||
const done = () => {
|
const done = () => {
|
||||||
@@ -75,3 +76,40 @@ test("registers /ask-settings and opens the shared settings overlay", async () =
|
|||||||
delete process.env.PI_CODING_AGENT_DIR;
|
delete process.env.PI_CODING_AGENT_DIR;
|
||||||
await rm(agentDir, { force: true, recursive: true });
|
await rm(agentDir, { force: true, recursive: true });
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("/ask-settings notifies outside TUI instead of opening custom UI", async () => {
|
||||||
|
const commands = new Map<
|
||||||
|
string,
|
||||||
|
{ handler: (args: string, ctx: any) => Promise<void> }
|
||||||
|
>();
|
||||||
|
registerAskSettingsCommand({
|
||||||
|
registerCommand(
|
||||||
|
name: string,
|
||||||
|
command: { handler: (args: string, ctx: any) => Promise<void> }
|
||||||
|
) {
|
||||||
|
commands.set(name, command);
|
||||||
|
},
|
||||||
|
} as never);
|
||||||
|
|
||||||
|
const notifications: Array<{ message: string; type: string }> = [];
|
||||||
|
let customOpened = false;
|
||||||
|
await commands.get("ask-settings")?.handler("", {
|
||||||
|
mode: "rpc",
|
||||||
|
ui: {
|
||||||
|
custom() {
|
||||||
|
customOpened = true;
|
||||||
|
},
|
||||||
|
notify(message: string, type: string) {
|
||||||
|
notifications.push({ message, type });
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
assert.equal(customOpened, false);
|
||||||
|
assert.deepEqual(notifications, [
|
||||||
|
{
|
||||||
|
message: "/ask-settings requires interactive TUI mode.",
|
||||||
|
type: "error",
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|||||||
+22
-3
@@ -4,7 +4,7 @@ import { registerAskTool } from "../src/ask-tool.ts";
|
|||||||
import type { AskParams } from "../src/types.ts";
|
import type { AskParams } from "../src/types.ts";
|
||||||
|
|
||||||
const NON_INTERACTIVE_MESSAGE_RE =
|
const NON_INTERACTIVE_MESSAGE_RE =
|
||||||
/Needs user input: ask_user requires interactive UI\./;
|
/Needs user input: ask_user requires interactive TUI mode\./;
|
||||||
const FIRST_QUESTION_RE = /1\. Goal: What should I optimize for\?/;
|
const FIRST_QUESTION_RE = /1\. Goal: What should I optimize for\?/;
|
||||||
const SPEED_OPTION_RE = /- Speed \[speed\]/;
|
const SPEED_OPTION_RE = /- Speed \[speed\]/;
|
||||||
const CUSTOM_OPTION_RE = /- Type your own \[custom\]/;
|
const CUSTOM_OPTION_RE = /- Type your own \[custom\]/;
|
||||||
@@ -47,8 +47,8 @@ function registerMockTool() {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function makeCtx(hasUi: boolean): unknown {
|
function makeCtx(hasUi: boolean, mode = hasUi ? "tui" : "print"): unknown {
|
||||||
return { [HAS_UI]: hasUi };
|
return { [HAS_UI]: hasUi, mode };
|
||||||
}
|
}
|
||||||
|
|
||||||
function sampleParams(): AskParams {
|
function sampleParams(): AskParams {
|
||||||
@@ -113,6 +113,25 @@ test("ask tool returns pending questions in non-interactive mode", async () => {
|
|||||||
assert.match(result.content[0].text, CUSTOM_OPTION_RE);
|
assert.match(result.content[0].text, CUSTOM_OPTION_RE);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("ask tool does not open custom UI outside TUI mode", async () => {
|
||||||
|
const { tool } = registerMockTool();
|
||||||
|
let customOpened = false;
|
||||||
|
|
||||||
|
const result = await tool.execute("call-1", sampleParams(), undefined, noop, {
|
||||||
|
[HAS_UI]: true,
|
||||||
|
mode: "rpc",
|
||||||
|
ui: {
|
||||||
|
custom() {
|
||||||
|
customOpened = true;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
assert.equal(customOpened, false);
|
||||||
|
assert.equal(result.details.cancelled, true);
|
||||||
|
assert.match(result.content[0].text, NON_INTERACTIVE_MESSAGE_RE);
|
||||||
|
});
|
||||||
|
|
||||||
test("ask tool includes custom answer fallback for preview questions", async () => {
|
test("ask tool includes custom answer fallback for preview questions", async () => {
|
||||||
const { tool } = registerMockTool();
|
const { tool } = registerMockTool();
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,9 @@
|
|||||||
|
import assert from "node:assert/strict";
|
||||||
|
import test from "node:test";
|
||||||
|
import { createAskAutocompleteProvider } from "../src/ui/autocomplete.ts";
|
||||||
|
|
||||||
|
test("ask autocomplete explicitly triggers on file mention marker", () => {
|
||||||
|
const provider = createAskAutocompleteProvider(process.cwd());
|
||||||
|
|
||||||
|
assert.deepEqual(provider.triggerCharacters, ["@"]);
|
||||||
|
});
|
||||||
@@ -5,7 +5,11 @@ import { dirname, join } from "node:path";
|
|||||||
import test from "node:test";
|
import test from "node:test";
|
||||||
import { DEFAULT_ASK_CONFIG } from "../src/config/defaults.ts";
|
import { DEFAULT_ASK_CONFIG } from "../src/config/defaults.ts";
|
||||||
import type { AskConfig } from "../src/config/schema.ts";
|
import type { AskConfig } from "../src/config/schema.ts";
|
||||||
import { AskConfigStore } from "../src/config/store.ts";
|
import {
|
||||||
|
AskConfigStore,
|
||||||
|
getAskConfigStore,
|
||||||
|
resetAskConfigStore,
|
||||||
|
} from "../src/config/store.ts";
|
||||||
|
|
||||||
const DEFAULT_KEYMAPS_NOTICE_PATTERN =
|
const DEFAULT_KEYMAPS_NOTICE_PATTERN =
|
||||||
/Using default ask keymaps for this session/;
|
/Using default ask keymaps for this session/;
|
||||||
@@ -31,6 +35,38 @@ async function makeTempPath(name: string): Promise<string> {
|
|||||||
return join(root, "eko24ive-pi-ask.json");
|
return join(root, "eko24ive-pi-ask.json");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test("resetAskConfigStore reloads the global store from disk", async () => {
|
||||||
|
const root = await import("node:fs/promises").then(({ mkdtemp }) =>
|
||||||
|
mkdtemp(join(tmpdir(), "pi-ask-config-reset-"))
|
||||||
|
);
|
||||||
|
const path = join(root, "extensions", "eko24ive-pi-ask.json");
|
||||||
|
await mkdir(dirname(path), { recursive: true });
|
||||||
|
await writeFile(
|
||||||
|
path,
|
||||||
|
JSON.stringify({
|
||||||
|
...expectedConfigFile(),
|
||||||
|
behaviour: {
|
||||||
|
...DEFAULT_ASK_CONFIG.behaviour,
|
||||||
|
autoSubmitWhenAnsweredWithoutNotes: true,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
);
|
||||||
|
process.env.PI_CODING_AGENT_DIR = root;
|
||||||
|
resetAskConfigStore();
|
||||||
|
getAskConfigStore().setConfig(DEFAULT_ASK_CONFIG);
|
||||||
|
|
||||||
|
resetAskConfigStore();
|
||||||
|
const result = await getAskConfigStore().ensureLoaded();
|
||||||
|
|
||||||
|
assert.equal(
|
||||||
|
result.config.behaviour.autoSubmitWhenAnsweredWithoutNotes,
|
||||||
|
true
|
||||||
|
);
|
||||||
|
delete process.env.PI_CODING_AGENT_DIR;
|
||||||
|
resetAskConfigStore();
|
||||||
|
await rm(root, { force: true, recursive: true });
|
||||||
|
});
|
||||||
|
|
||||||
test("config store writes defaults when file is missing", async () => {
|
test("config store writes defaults when file is missing", async () => {
|
||||||
const path = await makeTempPath("pi-ask-config-missing-");
|
const path = await makeTempPath("pi-ask-config-missing-");
|
||||||
const store = new AskConfigStore(path);
|
const store = new AskConfigStore(path);
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import assert from "node:assert/strict";
|
import assert from "node:assert/strict";
|
||||||
import test from "node:test";
|
import test from "node:test";
|
||||||
|
import { Editor } from "@earendil-works/pi-tui";
|
||||||
import { DEFAULT_ASK_CONFIG } from "../src/config/defaults.ts";
|
import { DEFAULT_ASK_CONFIG } from "../src/config/defaults.ts";
|
||||||
import { getAskConfigStore } from "../src/config/store.ts";
|
import { getAskConfigStore } from "../src/config/store.ts";
|
||||||
import { createInitialState } from "../src/state/create.ts";
|
import { createInitialState } from "../src/state/create.ts";
|
||||||
@@ -279,6 +280,7 @@ test("custom editor submit key controls actual editor submission", async () => {
|
|||||||
const resultPromise = runAskFlow(
|
const resultPromise = runAskFlow(
|
||||||
{
|
{
|
||||||
cwd: process.cwd(),
|
cwd: process.cwd(),
|
||||||
|
mode: "tui",
|
||||||
ui: {
|
ui: {
|
||||||
custom(callback: (...args: unknown[]) => unknown) {
|
custom(callback: (...args: unknown[]) => unknown) {
|
||||||
return new Promise((resolve) => {
|
return new Promise((resolve) => {
|
||||||
@@ -331,6 +333,78 @@ function plainTheme() {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test("ask flow forwards focus and invalidation to its editor", async () => {
|
||||||
|
getAskConfigStore().setConfig({
|
||||||
|
...DEFAULT_ASK_CONFIG,
|
||||||
|
notifications: {
|
||||||
|
...DEFAULT_ASK_CONFIG.notifications,
|
||||||
|
enabled: false,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
const originalInvalidate = Editor.prototype.invalidate;
|
||||||
|
let invalidateCalls = 0;
|
||||||
|
Editor.prototype.invalidate = function patchedInvalidate(this: Editor) {
|
||||||
|
invalidateCalls += 1;
|
||||||
|
return originalInvalidate.call(this);
|
||||||
|
};
|
||||||
|
let component:
|
||||||
|
| {
|
||||||
|
focused: boolean;
|
||||||
|
handleInput(data: string): void;
|
||||||
|
invalidate(): void;
|
||||||
|
}
|
||||||
|
| undefined;
|
||||||
|
|
||||||
|
try {
|
||||||
|
const resultPromise = runAskFlow(
|
||||||
|
{
|
||||||
|
cwd: process.cwd(),
|
||||||
|
mode: "tui",
|
||||||
|
ui: {
|
||||||
|
custom(callback: (...args: unknown[]) => unknown) {
|
||||||
|
return new Promise((resolve) => {
|
||||||
|
component = callback(
|
||||||
|
{
|
||||||
|
requestRender() {
|
||||||
|
// Rendering is not needed for this controller test.
|
||||||
|
},
|
||||||
|
},
|
||||||
|
plainTheme(),
|
||||||
|
{},
|
||||||
|
resolve
|
||||||
|
) as typeof component;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
} as never,
|
||||||
|
{
|
||||||
|
questions: [
|
||||||
|
{
|
||||||
|
id: "q1",
|
||||||
|
prompt: "Question?",
|
||||||
|
options: [{ value: "a", label: "A" }],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
await new Promise((resolve) => setImmediate(resolve));
|
||||||
|
assert(component);
|
||||||
|
component.focused = true;
|
||||||
|
assert.equal(component.focused, true);
|
||||||
|
component.focused = false;
|
||||||
|
assert.equal(component.focused, false);
|
||||||
|
component.invalidate();
|
||||||
|
assert.equal(invalidateCalls, 1);
|
||||||
|
component.handleInput("\x1b");
|
||||||
|
const result = await resultPromise;
|
||||||
|
assert.equal(result.cancelled, true);
|
||||||
|
} finally {
|
||||||
|
Editor.prototype.invalidate = originalInvalidate;
|
||||||
|
getAskConfigStore().setConfig(DEFAULT_ASK_CONFIG);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
test("custom configured note shortcuts are used at runtime", () => {
|
test("custom configured note shortcuts are used at runtime", () => {
|
||||||
const navigation = createInitialState({
|
const navigation = createInitialState({
|
||||||
questions: [
|
questions: [
|
||||||
|
|||||||
@@ -172,6 +172,45 @@ test("started event questions are cloned", async () => {
|
|||||||
assert.equal(questions[0].options[0].label, "Yes");
|
assert.equal(questions[0].options[0].label, "Yes");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("remote runtime disposes active flows and submit listener", () => {
|
||||||
|
const bus = new TestEventBus();
|
||||||
|
const remoteAsk = createRemoteAskRuntime(bus as never);
|
||||||
|
let submitCalls = 0;
|
||||||
|
const flow = remoteAsk.startFlow({
|
||||||
|
source: "tool",
|
||||||
|
questions: createInitialState({
|
||||||
|
questions: [
|
||||||
|
{
|
||||||
|
id: "decision",
|
||||||
|
prompt: "Proceed?",
|
||||||
|
options: [{ value: "yes", label: "Yes" }],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}).questions,
|
||||||
|
onSubmit: () => {
|
||||||
|
submitCalls += 1;
|
||||||
|
return { ok: true };
|
||||||
|
},
|
||||||
|
});
|
||||||
|
remoteAsk.disposeAll();
|
||||||
|
|
||||||
|
bus.emit(PI_ASK_SUBMIT_EVENT, {
|
||||||
|
version: 1,
|
||||||
|
requestId: "request-1",
|
||||||
|
flowId: flow.flowId,
|
||||||
|
response: {
|
||||||
|
kind: "answer",
|
||||||
|
answers: { decision: { values: ["yes"] } },
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
assert.equal(submitCalls, 0);
|
||||||
|
assert.equal(
|
||||||
|
bus.events.some((event) => event.channel === PI_ASK_SUBMIT_RESULT_EVENT),
|
||||||
|
false
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
test("remote submit resolves an active ask flow and emits lifecycle events", async () => {
|
test("remote submit resolves an active ask flow and emits lifecycle events", async () => {
|
||||||
getAskConfigStore().setConfig({
|
getAskConfigStore().setConfig({
|
||||||
...DEFAULT_ASK_CONFIG,
|
...DEFAULT_ASK_CONFIG,
|
||||||
@@ -197,6 +236,7 @@ test("remote submit resolves an active ask flow and emits lifecycle events", asy
|
|||||||
const result = await runAskFlow(
|
const result = await runAskFlow(
|
||||||
{
|
{
|
||||||
cwd: process.cwd(),
|
cwd: process.cwd(),
|
||||||
|
mode: "tui",
|
||||||
ui: {
|
ui: {
|
||||||
custom(callback: (...args: unknown[]) => unknown) {
|
custom(callback: (...args: unknown[]) => unknown) {
|
||||||
return new Promise((resolve) => {
|
return new Promise((resolve) => {
|
||||||
|
|||||||
Reference in New Issue
Block a user