Skip to content

Commit c6e1c10

Browse files
committed
Harden dirac CLI defaults
1 parent 986bba5 commit c6e1c10

5 files changed

Lines changed: 19 additions & 15 deletions

File tree

crates/calciforge/examples/config.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -97,14 +97,14 @@ primary_channels = ["telegram"]
9797
id = "dirac"
9898
kind = "dirac-cli"
9999
command = "dirac"
100-
args = ["--yolo", "--json"]
100+
args = ["--json"]
101101
timeout_ms = 600000
102102

103103
[agents.registry]
104104
display_name = "Dirac CLI"
105105
description = "Dirac coding agent via the official dirac-cli"
106106
specialties = ["coding", "refactoring", "token-efficiency"]
107-
access = ["filesystem", "git", "shell"]
107+
access = ["filesystem", "git"]
108108
primary_channels = ["telegram"]
109109

110110
# OpenCode via ACP (stdio transport)

crates/calciforge/src/adapters/dirac_cli.rs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
//! Dirac CLI adapter.
22
//!
33
//! This adapter dispatches messages through `dirac` in scripted mode.
4-
//! Default invocation uses `--yolo --json` with a fixed argv prompt and writes
4+
//! Default invocation uses JSON output with a fixed argv prompt and writes
55
//! the user task on stdin, avoiding prompt leakage through process listings.
6+
//! Operators who want approval-bypass modes must opt in explicitly in config.
67
78
use std::collections::HashMap;
89
use std::process::Stdio;
@@ -157,7 +158,7 @@ impl DiracCliAdapter {
157158
}
158159

159160
fn default_dirac_args() -> Vec<String> {
160-
vec!["--yolo".to_string(), "--json".to_string()]
161+
vec!["--json".to_string()]
161162
}
162163

163164
#[async_trait]
@@ -239,10 +240,10 @@ mod tests {
239240
use super::*;
240241

241242
#[test]
242-
fn defaults_append_prompt_when_no_placeholder() {
243+
fn defaults_do_not_bypass_dirac_approvals() {
243244
let a = DiracCliAdapter::new(None, None, None, None, None);
244245
let args = a.build_args();
245-
assert!(args.contains(&"--yolo".to_string()));
246+
assert!(!args.contains(&"--yolo".to_string()));
246247
assert!(args.contains(&"--json".to_string()));
247248
assert_eq!(args.last().map(String::as_str), Some(STDIN_TASK_PROMPT));
248249
}

crates/calciforge/src/adapters/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,7 @@ pub fn agent_supports_model_override(agent: &AgentConfig) -> bool {
360360
/// | `artifact-cli` | subprocess stdin + artifact dir | ❌ one-shot | n/a |
361361
/// | `codex-cli` | `codex exec` | ✅ `resume` path | n/a |
362362
/// | `claude-cli` | `claude --print` | ✅ `--session-id` | n/a |
363-
/// | `dirac-cli` | `dirac --yolo --json` | ❌ one-shot | n/a |
363+
/// | `dirac-cli` | `dirac --json` | ❌ one-shot | n/a |
364364
/// | `kimi-cli` | `kimi --quiet` | ✅ `--session` | n/a |
365365
/// | `ironclaw` | HTTP + SSE events | ✅ server-side | n/a |
366366
/// | `acp` | SACP stdio | ✅ persistent proc | n/a |

docs/agent-adapters.md

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ Adapter lifecycle labels:
4949
| OpenAI-compatible endpoint | `openai-compat` | Plain `/v1/chat/completions` target for Calciforge's model gateway, local test gateways, or compatible model APIs. Set `allow_model_override = true` only when this endpoint should accept Calciforge `!model` selections. |
5050
| Artifact-producing CLI | `kind = "artifact-cli"` | Prototype path for tools such as npcsh media workflows. Calciforge sends the task on stdin, exposes `{artifact_dir}` and `CALCIFORGE_ARTIFACT_DIR`, validates produced files, and returns a text fallback that names attachments without exposing local paths. Telegram and Matrix already use the richer internal envelope; native media upload can be added channel by channel. |
5151
| opencode | `acpx` or generic CLI | Model-agnostic terminal agent with a mature CLI/TUI surface. Prefer ACP when available. |
52-
| Dirac | `kind = "dirac-cli"` | Good scriptable fit. The adapter uses `--yolo --json`, sends the user task on stdin, ignores internal JSON event spam, and returns the final `completion_result`. |
52+
| Dirac | `kind = "dirac-cli"` | Good scriptable fit. The adapter defaults to `--json`, sends the user task on stdin, ignores internal JSON event spam, and returns the final `completion_result`. Approval-bypass flags such as `--yolo` require an explicit operator opt-in. |
5353
| Kimi Code CLI | `kind = "kimi-cli"` or generic ACP | Use `kimi-cli` for print-mode CLI dispatch with `--session` and explicit `--thinking` / `--no-thinking` args. Use generic ACP for `kimi acp` when Calciforge should talk to Kimi's native agent protocol. |
5454
| AgentSwift | Not supported directly | Interesting iOS-specific workflow, but current public shape is a SwiftUI app that drives Claude plus `xcodebuildmcp`/`openspec`, not a stable CLI adapter surface. Revisit if it exposes a noninteractive JSON/ACP/HTTP protocol. |
5555

@@ -229,25 +229,27 @@ Operational guidance:
229229
Dirac is attractive for Calciforge because its CLI is scriptable:
230230

231231
```sh
232-
dirac --yolo --json --timeout 120 --cwd /path/to/project \
232+
dirac --json --timeout 120 --cwd /path/to/project \
233233
"Fix the failing test and summarize the result."
234234
```
235235

236236
Local smoke testing found:
237237

238238
- `dirac --json` can complete a non-edit task and emit a final
239239
`completion_result`.
240-
- `dirac --yolo --json` can perform a simple edit, run `npm test`, and return a
241-
concise final answer.
242-
- Non-yolo scripted runs can stop at approval prompts, which is unsuitable for
243-
unattended Calciforge dispatch.
240+
- Approval-bypass flags such as `--yolo` can perform edits and run commands
241+
without interactive approval, so Calciforge does not enable them by default.
242+
- Non-yolo scripted runs can stop at approval prompts; operators should pair
243+
Dirac agents with trusted identities and constrained workspaces rather than
244+
making approval bypass the default.
244245
- JSON output includes repeated internal `api_req_started` events for the same
245246
request. The Calciforge adapter intentionally ignores those and only returns
246247
final assistant events.
247248

248249
Operational guidance:
249250

250-
- Keep `--yolo` limited to trusted identities and workspaces.
251+
- Only add approval-bypass flags such as `--yolo` for trusted identities and
252+
workspaces after accepting the local command execution risk.
251253
- Set `timeout_ms` generously for real coding tasks; the adapter still kills the
252254
child process if it exceeds Calciforge's timeout.
253255
- Prefer prompt-on-stdin configuration. Avoid putting sensitive request text in

scripts/install.sh

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -424,7 +424,7 @@ CONFIGURE_ONLY=false
424424
NODES_ONLY=false
425425
AGENTS_ONLY=false
426426
NODES_FILE=""
427-
AGENTS="claude,opencode,openclaw,zeroclaw,ironclaw,hermes,dirac"
427+
AGENTS="claude,opencode,openclaw,zeroclaw,ironclaw,hermes"
428428

429429
while [[ $# -gt 0 ]]; do
430430
case "$1" in
@@ -1947,6 +1947,7 @@ if agent_enabled dirac; then
19471947
if command -v dirac &>/dev/null; then
19481948
ok "dirac CLI installed"
19491949
warn "Authenticate once before first use: dirac auth"
1950+
warn "Dirac is opt-in for installation; avoid approval-bypass flags such as --yolo unless you accept local command execution risk."
19501951
fi
19511952
fi
19521953

0 commit comments

Comments
 (0)