@f5xc-salesdemos/xcsh 19.48.0 → 19.49.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/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"type": "module",
|
|
3
3
|
"name": "@f5xc-salesdemos/xcsh",
|
|
4
|
-
"version": "19.
|
|
4
|
+
"version": "19.49.0",
|
|
5
5
|
"description": "Coding agent CLI with read, bash, edit, write tools and session management",
|
|
6
6
|
"homepage": "https://github.com/f5xc-salesdemos/xcsh",
|
|
7
7
|
"author": "Can Boluk",
|
|
@@ -54,13 +54,13 @@
|
|
|
54
54
|
"dependencies": {
|
|
55
55
|
"@agentclientprotocol/sdk": "0.16.1",
|
|
56
56
|
"@mozilla/readability": "^0.6",
|
|
57
|
-
"@f5xc-salesdemos/xcsh-stats": "19.
|
|
58
|
-
"@f5xc-salesdemos/pi-agent-core": "19.
|
|
59
|
-
"@f5xc-salesdemos/pi-ai": "19.
|
|
60
|
-
"@f5xc-salesdemos/pi-natives": "19.
|
|
61
|
-
"@f5xc-salesdemos/pi-resource-management": "19.
|
|
62
|
-
"@f5xc-salesdemos/pi-tui": "19.
|
|
63
|
-
"@f5xc-salesdemos/pi-utils": "19.
|
|
57
|
+
"@f5xc-salesdemos/xcsh-stats": "19.49.0",
|
|
58
|
+
"@f5xc-salesdemos/pi-agent-core": "19.49.0",
|
|
59
|
+
"@f5xc-salesdemos/pi-ai": "19.49.0",
|
|
60
|
+
"@f5xc-salesdemos/pi-natives": "19.49.0",
|
|
61
|
+
"@f5xc-salesdemos/pi-resource-management": "19.49.0",
|
|
62
|
+
"@f5xc-salesdemos/pi-tui": "19.49.0",
|
|
63
|
+
"@f5xc-salesdemos/pi-utils": "19.49.0",
|
|
64
64
|
"@sinclair/typebox": "^0.34",
|
|
65
65
|
"@xterm/headless": "^6.0",
|
|
66
66
|
"ajv": "^8.20",
|
|
@@ -17,17 +17,17 @@ export interface BuildInfo {
|
|
|
17
17
|
}
|
|
18
18
|
|
|
19
19
|
export const BUILD_INFO: BuildInfo = {
|
|
20
|
-
"version": "19.
|
|
21
|
-
"commit": "
|
|
22
|
-
"shortCommit": "
|
|
20
|
+
"version": "19.49.0",
|
|
21
|
+
"commit": "fb72a3cf675798ecef6816224a5152ff7a032bbb",
|
|
22
|
+
"shortCommit": "fb72a3c",
|
|
23
23
|
"branch": "main",
|
|
24
|
-
"tag": "v19.
|
|
25
|
-
"commitDate": "2026-06-
|
|
26
|
-
"buildDate": "2026-06-
|
|
24
|
+
"tag": "v19.49.0",
|
|
25
|
+
"commitDate": "2026-06-25T23:35:47Z",
|
|
26
|
+
"buildDate": "2026-06-26T00:02:45.777Z",
|
|
27
27
|
"dirty": true,
|
|
28
28
|
"prNumber": "",
|
|
29
29
|
"repoUrl": "https://github.com/f5xc-salesdemos/xcsh",
|
|
30
30
|
"repoSlug": "f5xc-salesdemos/xcsh",
|
|
31
|
-
"commitUrl": "https://github.com/f5xc-salesdemos/xcsh/commit/
|
|
32
|
-
"releaseUrl": "https://github.com/f5xc-salesdemos/xcsh/releases/tag/v19.
|
|
31
|
+
"commitUrl": "https://github.com/f5xc-salesdemos/xcsh/commit/fb72a3cf675798ecef6816224a5152ff7a032bbb",
|
|
32
|
+
"releaseUrl": "https://github.com/f5xc-salesdemos/xcsh/releases/tag/v19.49.0"
|
|
33
33
|
};
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
# xcsh Chrome Extension Bridge — Tool API Reference
|
|
2
|
+
|
|
3
|
+
> Surfaced via `xcsh://extension`. The xcsh assistant drives the browser through
|
|
4
|
+
> the Chrome extension bridge (native messaging → service worker → CDP). Knowing
|
|
5
|
+
> which tool to use — and which to avoid — for each interaction is essential for
|
|
6
|
+
> deterministic, non-fragile automation.
|
|
7
|
+
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
## Deterministic click path (PREFERRED)
|
|
11
|
+
|
|
12
|
+
### `click_element { js, wait_ms? }`
|
|
13
|
+
**Use for:** clicking any element that exists in the page's main document.
|
|
14
|
+
|
|
15
|
+
`js` is a JavaScript expression that returns the target **Element** (or null). The
|
|
16
|
+
extension resolves geometry from the renderer (`DOM.getContentQuads` — CSS viewport
|
|
17
|
+
px with transforms/zoom/DPR baked in) and **hit-tests** the point
|
|
18
|
+
(`document.elementFromPoint`) before dispatching the trusted click. On occlusion it
|
|
19
|
+
re-scrolls once, then **fails loudly** naming the occluder — never a silent mis-click.
|
|
20
|
+
`wait_ms` polls for async elements (CDK portals, lazy content).
|
|
21
|
+
|
|
22
|
+
**Guarantees:**
|
|
23
|
+
- Deterministic across window sizes and zoom levels (layout-engine coords, not JS rects).
|
|
24
|
+
- Catches overlays (CDK portals, dialogs) and tells you what's in the way.
|
|
25
|
+
- Holds the element handle atomically across scroll → measure → verify → click.
|
|
26
|
+
|
|
27
|
+
**Build the `js` arg via** `buildElementResolverScript(selector)` (the same catalogue
|
|
28
|
+
selector grammar: `text('…')`, `role:text('…')`, `role[name='…']`, CSS, row-scoped `>>`)
|
|
29
|
+
so the click resolves the same element the workflow YAML names.
|
|
30
|
+
|
|
31
|
+
---
|
|
32
|
+
|
|
33
|
+
### `click { ref }`
|
|
34
|
+
Use when you already have an AX `ref` handle (from `read_ax`). Routes through
|
|
35
|
+
`click_element` internally — same determinism guarantees.
|
|
36
|
+
|
|
37
|
+
### `click_xy { x, y }`
|
|
38
|
+
**Last-resort.** Only for viewport points with no backing element (e.g. a computed
|
|
39
|
+
portal-overlay coordinate, or testing a specific pixel). Skips hit-testing.
|
|
40
|
+
|
|
41
|
+
---
|
|
42
|
+
|
|
43
|
+
## CDK-portal / typeahead (REQUIRED for CDK portals)
|
|
44
|
+
|
|
45
|
+
### `label_select { selector, value, label_value?, wait_ms? }`
|
|
46
|
+
**Use for:** any CDK-portal typeahead (`.cdk-overlay-container`): label-selector
|
|
47
|
+
key/operator/value steps, vsui "Type to search" inputs.
|
|
48
|
+
|
|
49
|
+
The extension keeps the input **focused throughout** (uses plain `Runtime.evaluate`,
|
|
50
|
+
NOT `evaluateWithRecovery` which detaches the debugger and kills focus). It:
|
|
51
|
+
1. Clicks the input (focus).
|
|
52
|
+
2. Types `value` via `Input.insertText` (keeps focus).
|
|
53
|
+
3. Polls the CDK portal for a matching option (`span` in `.cdk-overlay-container`).
|
|
54
|
+
4. Clicks the option via trusted CDP.
|
|
55
|
+
5. If `label_value` is provided, enters it into the value field that appears (uses the
|
|
56
|
+
secret-textarea real-typing path if it's a `<textarea>`).
|
|
57
|
+
|
|
58
|
+
**Why mandatory for CDK portals:** `javascript_tool` routes through `evaluateWithRecovery`
|
|
59
|
+
which DETACHES the CDP debugger on timeout — killing input focus and closing the portal.
|
|
60
|
+
`label_select` uses plain `Runtime.evaluate` and holds focus end-to-end.
|
|
61
|
+
|
|
62
|
+
---
|
|
63
|
+
|
|
64
|
+
## Input (trusted)
|
|
65
|
+
|
|
66
|
+
### `type_text { text }`
|
|
67
|
+
Inserts text via `Input.insertText` into the currently-focused element. Fires genuine
|
|
68
|
+
trusted input events that Angular's ControlValueAccessor and vsui pick up. Use this
|
|
69
|
+
(or `fill` via page-actions) for text fields, not programmatic value setting.
|
|
70
|
+
|
|
71
|
+
### `key_press { key }`
|
|
72
|
+
Dispatches a trusted `Input.dispatchKeyEvent` (keyDown + keyUp) for the named key
|
|
73
|
+
(e.g. `"Enter"`, `"Tab"`, `"Escape"`, `"Backspace"`).
|
|
74
|
+
|
|
75
|
+
### `form_input { ref, value }`
|
|
76
|
+
Sets a form field's value via `Runtime.callFunctionOn` — the Angular-compat path that
|
|
77
|
+
bypasses vsui's value-descriptor patching. Use when `fill` isn't available.
|
|
78
|
+
|
|
79
|
+
---
|
|
80
|
+
|
|
81
|
+
## DOM inspection (caution: defocuses active input)
|
|
82
|
+
|
|
83
|
+
### `javascript_tool { code }`
|
|
84
|
+
Evaluates arbitrary JavaScript and returns the result. Routes through
|
|
85
|
+
`evaluateWithRecovery` — **IMPORTANT: this defocuses the currently-focused input and
|
|
86
|
+
closes any open CDK portal / vsui dropdown.** Never call it between a typeahead open
|
|
87
|
+
and a portal selection. Safe for reading DOM state BEFORE opening a typeahead.
|
|
88
|
+
|
|
89
|
+
### `read_ax { }` / `find { selector }`
|
|
90
|
+
Reads the accessibility tree or finds AX nodes by selector. Both freeze the MV3
|
|
91
|
+
service worker on heavy F5 XC SPA pages (30s+) — prefer `javascript_tool` for quick
|
|
92
|
+
DOM queries. `read_ax` is usable on lighter pages.
|
|
93
|
+
|
|
94
|
+
### `get_page_text { }`
|
|
95
|
+
Returns the visible text content of the current page.
|
|
96
|
+
|
|
97
|
+
---
|
|
98
|
+
|
|
99
|
+
## Navigation
|
|
100
|
+
|
|
101
|
+
### `navigate { url }`
|
|
102
|
+
Navigates to a URL. Auto-accepts `beforeunload` ("Leave site?") dialogs — so a dirty
|
|
103
|
+
form's dialog does NOT block navigation. Wait for the target page to settle before
|
|
104
|
+
querying the DOM.
|
|
105
|
+
|
|
106
|
+
### `wait_for { selector, context?, timeoutMs? }` / `assert_text { selector, expected }`
|
|
107
|
+
Wait for an element to appear / assert text. Use these as post-navigation settle points.
|
|
108
|
+
|
|
109
|
+
---
|
|
110
|
+
|
|
111
|
+
## Tab management
|
|
112
|
+
|
|
113
|
+
### `tabs_list`, `tabs_create`, `tabs_close`
|
|
114
|
+
Enumerate, open, and close browser tabs. Useful for multi-tab flows or checking that a
|
|
115
|
+
navigation landed on the intended page.
|
|
116
|
+
|
|
117
|
+
---
|
|
118
|
+
|
|
119
|
+
## Screenshot (avoid in automation)
|
|
120
|
+
|
|
121
|
+
### `screenshot { }` → base64 JPEG
|
|
122
|
+
Captures a scaled canvas screenshot. **Avoid in automation loops** — `captureVisibleTab`
|
|
123
|
+
freezes the MV3 service worker event loop on retina Mac displays, blocking all
|
|
124
|
+
subsequent bridge requests for several seconds.
|
|
125
|
+
|
|
126
|
+
---
|
|
127
|
+
|
|
128
|
+
## Debugging tools
|
|
129
|
+
|
|
130
|
+
### `read_console { pattern? }` / `read_network { pattern? }`
|
|
131
|
+
Read Chrome DevTools console logs or network requests. Use for debugging — not required
|
|
132
|
+
in deterministic create/read/update/delete flows.
|
|
133
|
+
|
|
134
|
+
---
|
|
135
|
+
|
|
136
|
+
## Summary: which tool for which job
|
|
137
|
+
|
|
138
|
+
| Situation | Tool |
|
|
139
|
+
|-----------|------|
|
|
140
|
+
| Click a button/tab/link in the page | `click_element` (buildElementResolverScript) |
|
|
141
|
+
| Click inside a CDK portal option | `label_select` (the ONLY reliable path) |
|
|
142
|
+
| Fill a text input | page-actions `fill` → `type_text` under the hood |
|
|
143
|
+
| Select from a vsui listbox | page-actions `selectOption` → `click_element` + poll |
|
|
144
|
+
| Need current DOM state | `javascript_tool` (but check there's no open typeahead first) |
|
|
145
|
+
| Navigate between pages | `navigate` |
|
|
146
|
+
| Verify something appeared | `wait_for` / `assert_text` |
|
|
147
|
+
| Raw coordinates only | `click_xy` (last resort) |
|
|
@@ -13,6 +13,7 @@ import { XCSHApiClient } from "./xcsh-api-client";
|
|
|
13
13
|
import {
|
|
14
14
|
deriveTenantFromUrl,
|
|
15
15
|
hasEnvOverride,
|
|
16
|
+
isInjectableContextEnvKey,
|
|
16
17
|
normalizeApiUrl,
|
|
17
18
|
RESERVED_ENV_KEYS,
|
|
18
19
|
RESERVED_ENV_MESSAGES,
|
|
@@ -1388,10 +1389,13 @@ export class ContextService {
|
|
|
1388
1389
|
// Inject context profile name for API tool identity surfacing
|
|
1389
1390
|
merged[XCSH_CONTEXT_NAME] = context.name;
|
|
1390
1391
|
|
|
1391
|
-
// Inject
|
|
1392
|
+
// Inject additional env vars from context.env. Allowlist: only XCSH_-namespaced
|
|
1393
|
+
// non-reserved keys may reach the subprocess — a project-local context file is
|
|
1394
|
+
// untrusted input, so anything outside the XCSH_ namespace (LD_PRELOAD,
|
|
1395
|
+
// NODE_OPTIONS, PATH, …) is refused and can never run code.
|
|
1392
1396
|
if (context.env) {
|
|
1393
1397
|
for (const [key, value] of Object.entries(context.env)) {
|
|
1394
|
-
if (!process.env[key]
|
|
1398
|
+
if (isInjectableContextEnvKey(key) && !process.env[key]) merged[key] = value;
|
|
1395
1399
|
}
|
|
1396
1400
|
}
|
|
1397
1401
|
|
package/src/services/xcsh-env.ts
CHANGED
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
*/
|
|
7
7
|
import {
|
|
8
8
|
AUTH_ENV_KEYS,
|
|
9
|
+
isInjectableContextEnvKey,
|
|
9
10
|
isSensitiveEnvKey,
|
|
10
11
|
RESERVED_ENV_KEYS,
|
|
11
12
|
SECRET_ENV_PATTERNS,
|
|
@@ -20,6 +21,7 @@ import {
|
|
|
20
21
|
|
|
21
22
|
export {
|
|
22
23
|
AUTH_ENV_KEYS,
|
|
24
|
+
isInjectableContextEnvKey,
|
|
23
25
|
isSensitiveEnvKey,
|
|
24
26
|
RESERVED_ENV_KEYS,
|
|
25
27
|
SECRET_ENV_PATTERNS,
|