acpx 0.1.4 → 0.1.6

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/README.md CHANGED
@@ -1,5 +1,15 @@
1
+ <p align="center">
2
+ <img src="acpx_banner.svg" alt="acpx banner" width="100%" />
3
+ </p>
4
+
1
5
  # acpx
2
6
 
7
+ [![npm version](https://img.shields.io/npm/v/acpx.svg)](https://www.npmjs.com/package/acpx)
8
+ [![npm downloads](https://img.shields.io/npm/dm/acpx.svg)](https://www.npmjs.com/package/acpx)
9
+ [![CI](https://github.com/janitrai/acpx/actions/workflows/ci.yml/badge.svg)](https://github.com/janitrai/acpx/actions/workflows/ci.yml)
10
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
11
+ [![Node.js](https://img.shields.io/node/v/acpx.svg)](https://nodejs.org)
12
+
3
13
  Your agents love acpx! 🤖❤️ They hate having to scrape characters from a PTY session 😤
4
14
 
5
15
  `acpx` is a headless CLI client for the [Agent Client Protocol (ACP)](https://agentclientprotocol.com), so AI agents and orchestrators can talk to coding agents over a structured protocol instead of PTY scraping.
@@ -9,9 +19,19 @@ One command surface for Codex, Claude, Gemini, OpenCode, Pi, or custom ACP serve
9
19
  - **Persistent sessions**: multi-turn conversations that survive across invocations, scoped per repo
10
20
  - **Named sessions**: run parallel workstreams in the same repo (`-s backend`, `-s frontend`)
11
21
  - **Prompt queueing**: submit prompts while one is already running, they execute in order
22
+ - **Cooperative cancel command**: `cancel` sends ACP `session/cancel` via queue IPC without tearing down session state
12
23
  - **Soft-close lifecycle**: close sessions without deleting history from disk
13
24
  - **Queue owner TTL**: keep queue owners alive briefly for follow-up prompts (`--ttl`)
14
25
  - **Fire-and-forget**: `--no-wait` queues a prompt and returns immediately
26
+ - **Graceful cancel**: `Ctrl+C` sends ACP `session/cancel` before force-kill fallback
27
+ - **Session controls**: `set-mode` and `set <key> <value>` for `session/set_mode` and `session/set_config_option`
28
+ - **Crash reconnect**: dead agent processes are detected and sessions are reloaded automatically
29
+ - **Prompt from file/stdin**: `--file <path>` or piped stdin for prompt content
30
+ - **Config files**: global + project JSON config with `acpx config show|init`
31
+ - **Session inspect/history**: `sessions show` and `sessions history --limit <n>`
32
+ - **Local status checks**: `status` reports running/dead/no-session, pid, uptime, last prompt
33
+ - **Client methods**: stable `fs/*` and `terminal/*` handlers with permission controls and cwd sandboxing
34
+ - **Auth handshake**: stable `authenticate` support via env/config credentials
15
35
  - **Structured output**: typed ACP messages (thinking, tool calls, diffs) instead of ANSI scraping
16
36
  - **Any ACP agent**: built-in registry + `--agent` escape hatch for custom servers
17
37
  - **One-shot mode**: `exec` for stateless fire-and-forget tasks
@@ -53,33 +73,36 @@ Copy the block below and paste it into your OpenClaw, Pi, Claude Code, or simila
53
73
  I want you to use acpx to run coding agents over the Agent Client Protocol
54
74
  (ACP) instead of scraping PTY sessions. Please do the following:
55
75
 
56
- 1. Install acpx globally:
57
- npm i -g acpx
76
+ 1. Install the acpx skill so you have the full reference available:
77
+ npx acpx@latest --skill install acpx
58
78
 
59
- 2. Install the acpx skill so you have the full reference available:
60
- acpx --skill export acpx | npx skillflag install
61
-
62
- 3. Read the acpx skill reference so you know every command, flag, and
79
+ 2. Read the acpx skill reference so you know every command, flag, and
63
80
  workflow pattern:
64
81
  https://raw.githubusercontent.com/janitrai/acpx/main/skills/acpx/SKILL.md
65
82
 
66
- 4. If you need the full CLI reference with all options and examples:
83
+ 3. If you need the full CLI reference with all options and examples:
67
84
  https://raw.githubusercontent.com/janitrai/acpx/main/docs/CLI.md
68
85
 
69
86
  From now on, when you need to delegate work to a coding agent, use acpx
70
87
  instead of spawning raw terminal sessions. For example:
71
- acpx codex "fix the failing tests"
72
- acpx claude "refactor the auth module"
73
- acpx codex exec "one-shot: summarize this repo"
88
+ npx acpx@latest codex "fix the failing tests"
89
+ npx acpx@latest claude "refactor the auth module"
90
+ npx acpx@latest codex exec "one-shot: summarize this repo"
74
91
  ```
75
92
 
76
93
  ## Install
77
94
 
78
95
  ```bash
79
- npm i -g acpx
96
+ npm install -g acpx@latest
97
+ ```
98
+
99
+ Or run without installing:
100
+
101
+ ```bash
102
+ npx acpx@latest codex "fix the tests"
80
103
  ```
81
104
 
82
- `acpx` manages persistent sessions, so prefer a global install. Avoid `npx acpx ...` for normal use.
105
+ Session state lives in `~/.acpx/` either way. Global install is a little faster, but `npx acpx@latest` works fine.
83
106
 
84
107
  ## Agent prerequisites
85
108
 
@@ -99,7 +122,13 @@ The only prerequisite is the underlying coding agent you want to use:
99
122
  acpx codex sessions new # create a session (explicit) for this project dir
100
123
  acpx codex 'fix the tests' # implicit prompt (routes via directory-walk)
101
124
  acpx codex prompt 'fix the tests' # explicit prompt subcommand
125
+ echo 'fix flaky tests' | acpx codex # prompt from stdin
126
+ acpx codex --file prompt.md # prompt from file
127
+ acpx codex --file - "extra context" # explicit stdin + appended args
102
128
  acpx codex --no-wait 'draft test migration plan' # enqueue without waiting if session is busy
129
+ acpx codex cancel # cooperative cancel of in-flight prompt
130
+ acpx codex set-mode plan # session/set_mode
131
+ acpx codex set approval_policy conservative # session/set_config_option
103
132
  acpx exec 'summarize this repo' # default agent shortcut (codex)
104
133
  acpx codex exec 'what does this repo do?' # one-shot, no saved session
105
134
 
@@ -110,10 +139,16 @@ acpx codex -s docs 'rewrite API docs' # parallel work in another named
110
139
 
111
140
  acpx codex sessions # list sessions for codex command
112
141
  acpx codex sessions list # explicit list
142
+ acpx codex sessions show # inspect cwd session metadata
143
+ acpx codex sessions history # show recent turn history
113
144
  acpx codex sessions new # create fresh cwd-scoped default session
114
145
  acpx codex sessions new --name api # create fresh named session
115
146
  acpx codex sessions close # close cwd-scoped default session
116
147
  acpx codex sessions close api # close cwd-scoped named session
148
+ acpx codex status # local process status for current session
149
+
150
+ acpx config show # show resolved config (global + project)
151
+ acpx config init # create ~/.acpx/config.json template
117
152
 
118
153
  acpx claude 'refactor auth middleware' # built-in claude agent
119
154
  acpx gemini 'add startup logging' # built-in gemini agent
@@ -151,6 +186,35 @@ acpx --ttl 30 codex 'keep queue owner alive for quick follow-ups'
151
186
  acpx --verbose codex 'debug why adapter startup is failing'
152
187
  ```
153
188
 
189
+ ## Configuration files
190
+
191
+ `acpx` reads config in this order (later wins):
192
+
193
+ 1. global: `~/.acpx/config.json`
194
+ 2. project: `<cwd>/.acpxrc.json`
195
+
196
+ CLI flags always win over config values.
197
+
198
+ Supported keys:
199
+
200
+ ```json
201
+ {
202
+ "defaultAgent": "codex",
203
+ "defaultPermissions": "approve-all",
204
+ "ttl": 300,
205
+ "timeout": null,
206
+ "format": "text",
207
+ "agents": {
208
+ "my-custom": { "command": "./bin/my-acp-server" }
209
+ },
210
+ "auth": {
211
+ "my_auth_method_id": "credential-value"
212
+ }
213
+ }
214
+ ```
215
+
216
+ Use `acpx config show` to inspect the resolved result and `acpx config init` to create the global template.
217
+
154
218
  ## Output formats
155
219
 
156
220
  ```bash
@@ -195,8 +259,13 @@ acpx --agent ./my-custom-acp-server 'do something'
195
259
  - Prompt submissions are queue-aware per session. If a prompt is already running, new prompts are queued and drained by the running `acpx` process.
196
260
  - Queue owners use an idle TTL (default 300s). `--ttl <seconds>` overrides it; `--ttl 0` keeps owners alive indefinitely.
197
261
  - `--no-wait` submits to that queue and returns immediately.
262
+ - `cancel` sends cooperative `session/cancel` to the running queue owner process and returns success when no prompt is running (`nothing to cancel`).
263
+ - `set-mode` and `set` route through queue-owner IPC when active, otherwise they reconnect directly to apply `session/set_mode` and `session/set_config_option`.
198
264
  - `exec` is always one-shot and does not reuse saved sessions.
199
265
  - Session metadata is stored under `~/.acpx/sessions/`.
266
+ - Each successful prompt appends lightweight turn history previews (`role`, `timestamp`, `textPreview`) to session metadata.
267
+ - `Ctrl+C` during a running turn sends ACP `session/cancel` and waits briefly for `stopReason=cancelled` before force-killing if needed.
268
+ - If a saved session pid is dead on the next prompt, `acpx` respawns the agent, attempts `session/load`, and transparently falls back to `session/new` if loading fails.
200
269
 
201
270
  ## Full CLI reference
202
271
 
package/dist/cli.d.ts CHANGED
@@ -1,6 +1,12 @@
1
1
  #!/usr/bin/env node
2
2
  import { AgentCapabilities } from '@agentclientprotocol/sdk';
3
3
 
4
+ type SessionHistoryRole = "user" | "assistant";
5
+ type SessionHistoryEntry = {
6
+ role: SessionHistoryRole;
7
+ timestamp: string;
8
+ textPreview: string;
9
+ };
4
10
  type SessionRecord = {
5
11
  id: string;
6
12
  sessionId: string;
@@ -12,6 +18,13 @@ type SessionRecord = {
12
18
  closed?: boolean;
13
19
  closedAt?: string;
14
20
  pid?: number;
21
+ agentStartedAt?: string;
22
+ lastPromptAt?: string;
23
+ lastAgentExitCode?: number | null;
24
+ lastAgentExitSignal?: NodeJS.Signals | null;
25
+ lastAgentExitAt?: string;
26
+ lastAgentDisconnectReason?: string;
27
+ turnHistory?: SessionHistoryEntry[];
15
28
  protocolVersion?: number;
16
29
  agentCapabilities?: AgentCapabilities;
17
30
  };