mini-code-cli 0.1.1.3__tar.gz → 0.1.1.4__tar.gz
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.
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/PKG-INFO +62 -12
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/README.md +61 -11
- mini_code_cli-0.1.1.4/mini_code_cli/agent_files.py +90 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/agent_loop.py +526 -58
- mini_code_cli-0.1.1.4/mini_code_cli/compaction.py +245 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/config.py +35 -19
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/permissions.py +15 -9
- mini_code_cli-0.1.1.4/mini_code_cli/planning.py +29 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/prompts.py +144 -6
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/runner.py +7 -1
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/subagents/base.py +64 -8
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/subagents/builtin.py +10 -9
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/tokens.py +66 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/tools.py +92 -30
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/ui.py +151 -5
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/utils.py +92 -53
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/PKG-INFO +62 -12
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/SOURCES.txt +9 -1
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/pyproject.toml +1 -1
- mini_code_cli-0.1.1.4/tests/test_advanced_features.py +459 -0
- mini_code_cli-0.1.1.4/tests/test_cli_features.py +177 -0
- mini_code_cli-0.1.1.4/tests/test_config.py +82 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_e2e_agent_loop.py +53 -1
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_interactive.py +11 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_permissions.py +8 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_subagents.py +88 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_tokens.py +29 -2
- mini_code_cli-0.1.1.4/tests/test_tools.py +151 -0
- mini_code_cli-0.1.1.4/tests/test_utils.py +93 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/LICENSE +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/__init__.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/__main__.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/persistence.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/plan.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/sandbox.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/shell_safety_utils.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/skills.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli/subagents/__init__.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/dependency_links.txt +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/entry_points.txt +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/requires.txt +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/mini_code_cli.egg-info/top_level.txt +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/setup.cfg +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_release_script.py +0 -0
- {mini_code_cli-0.1.1.3 → mini_code_cli-0.1.1.4}/tests/test_runner.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: mini-code-cli
|
|
3
|
-
Version: 0.1.1.
|
|
3
|
+
Version: 0.1.1.4
|
|
4
4
|
Summary: Mini Coding Agent. Allows you to easily experiment with a small coding agent.
|
|
5
5
|
Author-email: Nikolai Rozanov <nikolai.rozanov@gmail.com>
|
|
6
6
|
License-Expression: AGPL-3.0-only
|
|
@@ -67,7 +67,7 @@ mini-code --url "https://api.deepseek.com" --model "deepseek-v4-flash"
|
|
|
67
67
|
**3 — The shortcuts** (plan mode, sub-agents, shell, auto-mode, no permission prompts):
|
|
68
68
|
|
|
69
69
|
```bash
|
|
70
|
-
mini-code --all # = --plan --enable-subagents --enable-shell --auto-mode --sudo
|
|
70
|
+
mini-code --all # = --plan --enable-subagents --enable-shell --skills --auto-mode --sudo
|
|
71
71
|
mini-code --all-last # ...and continue your last session
|
|
72
72
|
```
|
|
73
73
|
|
|
@@ -95,20 +95,23 @@ given a reference implementation.
|
|
|
95
95
|
| `--prompt TEXT` | — | initial user prompt |
|
|
96
96
|
| `-a`, `--auto-mode` | off | keep querying the model and running tools until no tool calls remain |
|
|
97
97
|
| `--agent-md FILE` | — | append an `agent.md` file after the system prompt (e.g. `./skill.md`) |
|
|
98
|
-
| `--ask-permission` | off | ask before every tool call
|
|
98
|
+
| `--ask-permission` | off | ask before **every** tool call, including an ALLOW-tier shell command (`--sudo` disables all prompts) |
|
|
99
99
|
| `--sudo` | off | **dangerous:** never ask. DENY-tier commands are still refused |
|
|
100
100
|
| `--allowed-dir DIR` | `./` | sandbox for **file** tools (does not restrict the shell) |
|
|
101
101
|
| `-s`, `--enable-shell` | off | allow shell execution (classifier always applies) |
|
|
102
102
|
| `-g`, `--enable-subagents` | off | expose sub-agents as tools |
|
|
103
|
-
| `--skills` | off | enable the `.mini` skills directory (`skill.md`s, `SKILLS.md`, runnable scripts) |
|
|
104
|
-
| `-p`, `--plan` | off | plan mode (`CURRENT_GOAL.md` / `CURRENT_PLAN.md`, `/plan`) |
|
|
103
|
+
| `--skills` | off | enable the `.mini` skills directory (`skill.md`s, `SKILLS.md`, runnable scripts). **`run_skill` executes those Python scripts — arbitrary code execution, even without `--enable-shell`**; only enable it for a directory you trust |
|
|
104
|
+
| `-p`, `--plan` | off | plan mode (`CURRENT_GOAL.md` / `CURRENT_PLAN.md`, printed plan, `/plan`, `/skip-plan`) |
|
|
105
|
+
| `--plan-strategy NAME` | `plan-verify-step` | `plan-verify-step`, `plan-verify` or `open-plan` (implies `--plan`) |
|
|
106
|
+
| `--scratchpad` | off | give the agent a free-form `.mini/SCRATCHPAD.md` (plus further scratch files) for thoughts, plans and learnings |
|
|
107
|
+
| `--compaction-strategy NAME` | `summarise` | `summarise`, `predict-files` or `predict-messages` |
|
|
105
108
|
| `--llm-timeout S` | `500` | HTTP timeout for LLM requests |
|
|
106
109
|
| `--tool-timeout S` | `120` | timeout for a single tool call |
|
|
107
110
|
| `--max-context-tokens N` | derived | input-token budget before the history is compacted |
|
|
108
111
|
| `--cache-dir DIR` | `~/.cache/mini/sessions/` | where session histories are stored |
|
|
109
112
|
| `--restore-session PATH` | — | continue a specific previous session |
|
|
110
113
|
| `-l`, `--load-last-session` | off | continue the session recorded in the `.mini` pointer |
|
|
111
|
-
| `--all` | off | `--plan --enable-subagents --enable-shell --auto-mode --sudo` |
|
|
114
|
+
| `--all` | off | `--plan --enable-subagents --enable-shell --skills --auto-mode --sudo` |
|
|
112
115
|
| `--all-last` | off | `--all` + `--load-last-session` |
|
|
113
116
|
| `--verbose` | off | print full detail (default: user/assistant turns, token usage, tool calls only) |
|
|
114
117
|
| `-h`, `--help` | — | show the built-in help |
|
|
@@ -151,8 +154,10 @@ mini-code --enable-subagents # the available sub-agents then show up in /h
|
|
|
151
154
|
|
|
152
155
|
> [!NOTE]
|
|
153
156
|
> A sub-agent's `tools`, `enable_shell` and `max_steps` are always **intersected with the
|
|
154
|
-
> parent's** permissions, so it can never do anything the main agent could not.
|
|
155
|
-
>
|
|
157
|
+
> parent's** permissions, so it can never do anything the main agent could not. The `tools`
|
|
158
|
+
> allowlist is enforced on the nested session itself (both the schemas offered to the model and
|
|
159
|
+
> the dispatch table), not merely described in its prompt. Sub-agents compose with `--plan`:
|
|
160
|
+
> each keeps its own `CURRENT_PLAN.md` / `CURRENT_GOAL.md`.
|
|
156
161
|
|
|
157
162
|
<details>
|
|
158
163
|
<summary><b>Adding your own sub-agent</b></summary>
|
|
@@ -190,9 +195,16 @@ to the model automatically when `--enable-subagents` is set. See
|
|
|
190
195
|
| `/reset [<n>]` | rewind to the end of turn `n` (`last` works too); drops everything after it |
|
|
191
196
|
| `/clear` | clear the screen (keeps the conversation history) |
|
|
192
197
|
| `/plan` | show the current goal + plan (plan mode only) |
|
|
198
|
+
| `/context` | show how the context window is used: tokens and percentages by category (system prompt, user/assistant messages, tool calls/outputs, reasoning, overhead) |
|
|
199
|
+
| `/skip-plan <prompt>` | send `<prompt>` once without generating or reviewing a plan |
|
|
193
200
|
| `/help` | show this help |
|
|
194
201
|
| `/quit`, `/exit` | save the session and exit |
|
|
195
202
|
|
|
203
|
+
**Multi-line input:** press `Shift+Enter` (or `Ctrl-J`) to insert a newline; plain
|
|
204
|
+
`Enter` sends the turn. This works in the session prompt and the startup tip
|
|
205
|
+
reminds you. Terminals that report `Shift+Enter` as a CSI-u/modifyOtherKeys
|
|
206
|
+
sequence are recognised; elsewhere `Ctrl-J` inserts the newline.
|
|
207
|
+
|
|
196
208
|
> [!NOTE]
|
|
197
209
|
> `/history` and `/reset` are driven by `summary_history.json`, a flat recorder that maps every
|
|
198
210
|
> turn to the `history_{n}.json` segment and message index it lives in — so no full history is
|
|
@@ -251,6 +263,9 @@ command into one of three tiers:
|
|
|
251
263
|
| **ASK** | `rm file`, `sudo ...`, `chmod`, `curl ... \| sh` | requires your confirmation |
|
|
252
264
|
| **ALLOW** | `ls`, `cat`, `git status` | runs without prompting |
|
|
253
265
|
|
|
266
|
+
`--sudo` removes the confirmation prompts (ASK tier and `--ask-permission`); DENY commands are
|
|
267
|
+
still refused. With no flags, an ASK-tier command prompts and an ALLOW-tier one runs unaided.
|
|
268
|
+
|
|
254
269
|
> [!WARNING]
|
|
255
270
|
> The classifier is **always enforced** — even in auto-mode and with `--sudo` — so the agent
|
|
256
271
|
> cannot run destructive commands unattended. It is a heuristic, not a sandbox: use it with care.
|
|
@@ -261,13 +276,34 @@ command into one of three tiers:
|
|
|
261
276
|
The loop keeps two human-readable tracking files in the session directory: `CURRENT_GOAL.md`
|
|
262
277
|
(your latest instruction) and `CURRENT_PLAN.md` (a step-by-step plan for that goal, marked
|
|
263
278
|
finished when it is done). They are authored by the *loop*, not the agent, live outside
|
|
264
|
-
`--allowed-dir`, and can be inspected any time with `/plan`.
|
|
279
|
+
`--allowed-dir`, and can be inspected any time with `/plan`. The generated plan is
|
|
280
|
+
also printed as a box right after planning, so you can see it without asking.
|
|
281
|
+
Use `/skip-plan <prompt>` to send one prompt without planning it (plan mode stays
|
|
282
|
+
on for later turns).
|
|
283
|
+
|
|
284
|
+
`--plan-strategy` selects how planning is wired:
|
|
285
|
+
|
|
286
|
+
| Strategy | What happens |
|
|
287
|
+
| --- | --- |
|
|
288
|
+
| `plan-verify-step` (default) | Current behaviour: author a plan, review it once the work settles, then run one extra step and keep whatever that step says. |
|
|
289
|
+
| `plan-verify` | Same plan + review, but the post-review step is kept only when it calls a tool. A no-tool answer is shown to you and ends the turn without being appended to the transcript. |
|
|
290
|
+
| `open-plan` | The agent owns a plan document at `.mini/PLAN.md` inside `--allowed-dir`, reads and updates it with the normal file tools, and the loop neither authors nor reviews a plan. |
|
|
265
291
|
|
|
266
292
|
> [!NOTE]
|
|
267
293
|
> Plan mode also changes **history compaction**: after the transcript is compacted to a summary,
|
|
268
294
|
> `CURRENT_PLAN.md` and `CURRENT_GOAL.md` are re-injected, so the agent keeps working against the
|
|
269
|
-
> same goal.
|
|
270
|
-
> before the agent returns
|
|
295
|
+
> same goal. With `open-plan`, the agent's `.mini/PLAN.md` is re-injected instead. When the work
|
|
296
|
+
> looks done the plan is reviewed and any outstanding task is re-queued before the agent returns
|
|
297
|
+
> to you (except with `open-plan`).
|
|
298
|
+
|
|
299
|
+
### Scratchpad — `--scratchpad`
|
|
300
|
+
|
|
301
|
+
With `--scratchpad`, the loop creates `.mini/SCRATCHPAD.md` inside `--allowed-dir` and tells the
|
|
302
|
+
agent that it may read and write that file freely, and may create additional scratch files in the
|
|
303
|
+
same directory (for example `SCRATCH-NOTES.md`, `SCRATCH-IDEAS.md`). The scratchpad is ordinary
|
|
304
|
+
state inside the sandbox, so the normal `read_file` / `write_file` / `edit` tools work; no special
|
|
305
|
+
tool is registered. It is meant for the agent's own thoughts, plans, learnings and open questions,
|
|
306
|
+
and survives a history compaction because it lives on disk.
|
|
271
307
|
|
|
272
308
|
### Sessions — resume, or start fresh
|
|
273
309
|
|
|
@@ -315,6 +351,20 @@ waiting on) is kept verbatim after the summary. So a compaction that fires just
|
|
|
315
351
|
instruction cannot swallow it — the model still answers what you asked, and the turn stays in
|
|
316
352
|
the session file, in `/history` and in a later restore.
|
|
317
353
|
|
|
354
|
+
`--compaction-strategy` chooses what else survives besides the summary:
|
|
355
|
+
|
|
356
|
+
| Strategy | Messages after compaction |
|
|
357
|
+
| --- | --- |
|
|
358
|
+
| `summarise` (default) | `system`, `summary`, `plan`, `current turn` |
|
|
359
|
+
| `predict-files` | `system`, `summary`, predicted read-only tool calls + results, `plan`, `current turn` |
|
|
360
|
+
| `predict-messages` | `system`, `summary`, original messages the model names by index, `plan`, `current turn` |
|
|
361
|
+
|
|
362
|
+
`predict-files` asks the model which files it needs to re-read and executes only the read-only
|
|
363
|
+
tools (`read_file`, `grep`, `glob`) it predicts; `predict-messages` asks for a JSON array of
|
|
364
|
+
0-based message indexes to keep verbatim. Both predictions are one extra tool-free (or
|
|
365
|
+
read-only-tool) LLM call, are billed normally, and are capped so they cannot refill the context
|
|
366
|
+
they just freed. A failed prediction degrades to the plain summary.
|
|
367
|
+
|
|
318
368
|
Because a rollover leaves no trace in the transcript (the old turns really are gone), the
|
|
319
369
|
console says in plain terms what happened — all of it without `--verbose`:
|
|
320
370
|
|
|
@@ -379,7 +429,7 @@ If you use `mini-code-cli` in your research or writing, please cite it:
|
|
|
379
429
|
author = {Rozanov, Nikolai},
|
|
380
430
|
title = {mini-code-cli: A minimal, dependency-light coding agent},
|
|
381
431
|
year = {2026},
|
|
382
|
-
version = {0.1.1.
|
|
432
|
+
version = {0.1.1.4},
|
|
383
433
|
howpublished = {\url{https://github.com/ai-nikolai/mini-code-cli}},
|
|
384
434
|
note = {A no-bloat, dependency-light agent CLI for experimenting.}
|
|
385
435
|
}
|
|
@@ -48,7 +48,7 @@ mini-code --url "https://api.deepseek.com" --model "deepseek-v4-flash"
|
|
|
48
48
|
**3 — The shortcuts** (plan mode, sub-agents, shell, auto-mode, no permission prompts):
|
|
49
49
|
|
|
50
50
|
```bash
|
|
51
|
-
mini-code --all # = --plan --enable-subagents --enable-shell --auto-mode --sudo
|
|
51
|
+
mini-code --all # = --plan --enable-subagents --enable-shell --skills --auto-mode --sudo
|
|
52
52
|
mini-code --all-last # ...and continue your last session
|
|
53
53
|
```
|
|
54
54
|
|
|
@@ -76,20 +76,23 @@ given a reference implementation.
|
|
|
76
76
|
| `--prompt TEXT` | — | initial user prompt |
|
|
77
77
|
| `-a`, `--auto-mode` | off | keep querying the model and running tools until no tool calls remain |
|
|
78
78
|
| `--agent-md FILE` | — | append an `agent.md` file after the system prompt (e.g. `./skill.md`) |
|
|
79
|
-
| `--ask-permission` | off | ask before every tool call
|
|
79
|
+
| `--ask-permission` | off | ask before **every** tool call, including an ALLOW-tier shell command (`--sudo` disables all prompts) |
|
|
80
80
|
| `--sudo` | off | **dangerous:** never ask. DENY-tier commands are still refused |
|
|
81
81
|
| `--allowed-dir DIR` | `./` | sandbox for **file** tools (does not restrict the shell) |
|
|
82
82
|
| `-s`, `--enable-shell` | off | allow shell execution (classifier always applies) |
|
|
83
83
|
| `-g`, `--enable-subagents` | off | expose sub-agents as tools |
|
|
84
|
-
| `--skills` | off | enable the `.mini` skills directory (`skill.md`s, `SKILLS.md`, runnable scripts) |
|
|
85
|
-
| `-p`, `--plan` | off | plan mode (`CURRENT_GOAL.md` / `CURRENT_PLAN.md`, `/plan`) |
|
|
84
|
+
| `--skills` | off | enable the `.mini` skills directory (`skill.md`s, `SKILLS.md`, runnable scripts). **`run_skill` executes those Python scripts — arbitrary code execution, even without `--enable-shell`**; only enable it for a directory you trust |
|
|
85
|
+
| `-p`, `--plan` | off | plan mode (`CURRENT_GOAL.md` / `CURRENT_PLAN.md`, printed plan, `/plan`, `/skip-plan`) |
|
|
86
|
+
| `--plan-strategy NAME` | `plan-verify-step` | `plan-verify-step`, `plan-verify` or `open-plan` (implies `--plan`) |
|
|
87
|
+
| `--scratchpad` | off | give the agent a free-form `.mini/SCRATCHPAD.md` (plus further scratch files) for thoughts, plans and learnings |
|
|
88
|
+
| `--compaction-strategy NAME` | `summarise` | `summarise`, `predict-files` or `predict-messages` |
|
|
86
89
|
| `--llm-timeout S` | `500` | HTTP timeout for LLM requests |
|
|
87
90
|
| `--tool-timeout S` | `120` | timeout for a single tool call |
|
|
88
91
|
| `--max-context-tokens N` | derived | input-token budget before the history is compacted |
|
|
89
92
|
| `--cache-dir DIR` | `~/.cache/mini/sessions/` | where session histories are stored |
|
|
90
93
|
| `--restore-session PATH` | — | continue a specific previous session |
|
|
91
94
|
| `-l`, `--load-last-session` | off | continue the session recorded in the `.mini` pointer |
|
|
92
|
-
| `--all` | off | `--plan --enable-subagents --enable-shell --auto-mode --sudo` |
|
|
95
|
+
| `--all` | off | `--plan --enable-subagents --enable-shell --skills --auto-mode --sudo` |
|
|
93
96
|
| `--all-last` | off | `--all` + `--load-last-session` |
|
|
94
97
|
| `--verbose` | off | print full detail (default: user/assistant turns, token usage, tool calls only) |
|
|
95
98
|
| `-h`, `--help` | — | show the built-in help |
|
|
@@ -132,8 +135,10 @@ mini-code --enable-subagents # the available sub-agents then show up in /h
|
|
|
132
135
|
|
|
133
136
|
> [!NOTE]
|
|
134
137
|
> A sub-agent's `tools`, `enable_shell` and `max_steps` are always **intersected with the
|
|
135
|
-
> parent's** permissions, so it can never do anything the main agent could not.
|
|
136
|
-
>
|
|
138
|
+
> parent's** permissions, so it can never do anything the main agent could not. The `tools`
|
|
139
|
+
> allowlist is enforced on the nested session itself (both the schemas offered to the model and
|
|
140
|
+
> the dispatch table), not merely described in its prompt. Sub-agents compose with `--plan`:
|
|
141
|
+
> each keeps its own `CURRENT_PLAN.md` / `CURRENT_GOAL.md`.
|
|
137
142
|
|
|
138
143
|
<details>
|
|
139
144
|
<summary><b>Adding your own sub-agent</b></summary>
|
|
@@ -171,9 +176,16 @@ to the model automatically when `--enable-subagents` is set. See
|
|
|
171
176
|
| `/reset [<n>]` | rewind to the end of turn `n` (`last` works too); drops everything after it |
|
|
172
177
|
| `/clear` | clear the screen (keeps the conversation history) |
|
|
173
178
|
| `/plan` | show the current goal + plan (plan mode only) |
|
|
179
|
+
| `/context` | show how the context window is used: tokens and percentages by category (system prompt, user/assistant messages, tool calls/outputs, reasoning, overhead) |
|
|
180
|
+
| `/skip-plan <prompt>` | send `<prompt>` once without generating or reviewing a plan |
|
|
174
181
|
| `/help` | show this help |
|
|
175
182
|
| `/quit`, `/exit` | save the session and exit |
|
|
176
183
|
|
|
184
|
+
**Multi-line input:** press `Shift+Enter` (or `Ctrl-J`) to insert a newline; plain
|
|
185
|
+
`Enter` sends the turn. This works in the session prompt and the startup tip
|
|
186
|
+
reminds you. Terminals that report `Shift+Enter` as a CSI-u/modifyOtherKeys
|
|
187
|
+
sequence are recognised; elsewhere `Ctrl-J` inserts the newline.
|
|
188
|
+
|
|
177
189
|
> [!NOTE]
|
|
178
190
|
> `/history` and `/reset` are driven by `summary_history.json`, a flat recorder that maps every
|
|
179
191
|
> turn to the `history_{n}.json` segment and message index it lives in — so no full history is
|
|
@@ -232,6 +244,9 @@ command into one of three tiers:
|
|
|
232
244
|
| **ASK** | `rm file`, `sudo ...`, `chmod`, `curl ... \| sh` | requires your confirmation |
|
|
233
245
|
| **ALLOW** | `ls`, `cat`, `git status` | runs without prompting |
|
|
234
246
|
|
|
247
|
+
`--sudo` removes the confirmation prompts (ASK tier and `--ask-permission`); DENY commands are
|
|
248
|
+
still refused. With no flags, an ASK-tier command prompts and an ALLOW-tier one runs unaided.
|
|
249
|
+
|
|
235
250
|
> [!WARNING]
|
|
236
251
|
> The classifier is **always enforced** — even in auto-mode and with `--sudo` — so the agent
|
|
237
252
|
> cannot run destructive commands unattended. It is a heuristic, not a sandbox: use it with care.
|
|
@@ -242,13 +257,34 @@ command into one of three tiers:
|
|
|
242
257
|
The loop keeps two human-readable tracking files in the session directory: `CURRENT_GOAL.md`
|
|
243
258
|
(your latest instruction) and `CURRENT_PLAN.md` (a step-by-step plan for that goal, marked
|
|
244
259
|
finished when it is done). They are authored by the *loop*, not the agent, live outside
|
|
245
|
-
`--allowed-dir`, and can be inspected any time with `/plan`.
|
|
260
|
+
`--allowed-dir`, and can be inspected any time with `/plan`. The generated plan is
|
|
261
|
+
also printed as a box right after planning, so you can see it without asking.
|
|
262
|
+
Use `/skip-plan <prompt>` to send one prompt without planning it (plan mode stays
|
|
263
|
+
on for later turns).
|
|
264
|
+
|
|
265
|
+
`--plan-strategy` selects how planning is wired:
|
|
266
|
+
|
|
267
|
+
| Strategy | What happens |
|
|
268
|
+
| --- | --- |
|
|
269
|
+
| `plan-verify-step` (default) | Current behaviour: author a plan, review it once the work settles, then run one extra step and keep whatever that step says. |
|
|
270
|
+
| `plan-verify` | Same plan + review, but the post-review step is kept only when it calls a tool. A no-tool answer is shown to you and ends the turn without being appended to the transcript. |
|
|
271
|
+
| `open-plan` | The agent owns a plan document at `.mini/PLAN.md` inside `--allowed-dir`, reads and updates it with the normal file tools, and the loop neither authors nor reviews a plan. |
|
|
246
272
|
|
|
247
273
|
> [!NOTE]
|
|
248
274
|
> Plan mode also changes **history compaction**: after the transcript is compacted to a summary,
|
|
249
275
|
> `CURRENT_PLAN.md` and `CURRENT_GOAL.md` are re-injected, so the agent keeps working against the
|
|
250
|
-
> same goal.
|
|
251
|
-
> before the agent returns
|
|
276
|
+
> same goal. With `open-plan`, the agent's `.mini/PLAN.md` is re-injected instead. When the work
|
|
277
|
+
> looks done the plan is reviewed and any outstanding task is re-queued before the agent returns
|
|
278
|
+
> to you (except with `open-plan`).
|
|
279
|
+
|
|
280
|
+
### Scratchpad — `--scratchpad`
|
|
281
|
+
|
|
282
|
+
With `--scratchpad`, the loop creates `.mini/SCRATCHPAD.md` inside `--allowed-dir` and tells the
|
|
283
|
+
agent that it may read and write that file freely, and may create additional scratch files in the
|
|
284
|
+
same directory (for example `SCRATCH-NOTES.md`, `SCRATCH-IDEAS.md`). The scratchpad is ordinary
|
|
285
|
+
state inside the sandbox, so the normal `read_file` / `write_file` / `edit` tools work; no special
|
|
286
|
+
tool is registered. It is meant for the agent's own thoughts, plans, learnings and open questions,
|
|
287
|
+
and survives a history compaction because it lives on disk.
|
|
252
288
|
|
|
253
289
|
### Sessions — resume, or start fresh
|
|
254
290
|
|
|
@@ -296,6 +332,20 @@ waiting on) is kept verbatim after the summary. So a compaction that fires just
|
|
|
296
332
|
instruction cannot swallow it — the model still answers what you asked, and the turn stays in
|
|
297
333
|
the session file, in `/history` and in a later restore.
|
|
298
334
|
|
|
335
|
+
`--compaction-strategy` chooses what else survives besides the summary:
|
|
336
|
+
|
|
337
|
+
| Strategy | Messages after compaction |
|
|
338
|
+
| --- | --- |
|
|
339
|
+
| `summarise` (default) | `system`, `summary`, `plan`, `current turn` |
|
|
340
|
+
| `predict-files` | `system`, `summary`, predicted read-only tool calls + results, `plan`, `current turn` |
|
|
341
|
+
| `predict-messages` | `system`, `summary`, original messages the model names by index, `plan`, `current turn` |
|
|
342
|
+
|
|
343
|
+
`predict-files` asks the model which files it needs to re-read and executes only the read-only
|
|
344
|
+
tools (`read_file`, `grep`, `glob`) it predicts; `predict-messages` asks for a JSON array of
|
|
345
|
+
0-based message indexes to keep verbatim. Both predictions are one extra tool-free (or
|
|
346
|
+
read-only-tool) LLM call, are billed normally, and are capped so they cannot refill the context
|
|
347
|
+
they just freed. A failed prediction degrades to the plain summary.
|
|
348
|
+
|
|
299
349
|
Because a rollover leaves no trace in the transcript (the old turns really are gone), the
|
|
300
350
|
console says in plain terms what happened — all of it without `--verbose`:
|
|
301
351
|
|
|
@@ -360,7 +410,7 @@ If you use `mini-code-cli` in your research or writing, please cite it:
|
|
|
360
410
|
author = {Rozanov, Nikolai},
|
|
361
411
|
title = {mini-code-cli: A minimal, dependency-light coding agent},
|
|
362
412
|
year = {2026},
|
|
363
|
-
version = {0.1.1.
|
|
413
|
+
version = {0.1.1.4},
|
|
364
414
|
howpublished = {\url{https://github.com/ai-nikolai/mini-code-cli}},
|
|
365
415
|
note = {A no-bloat, dependency-light agent CLI for experimenting.}
|
|
366
416
|
}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
"""Agent-owned files kept in ``--allowed-dir/.mini``.
|
|
2
|
+
|
|
3
|
+
Two opt-in features put a file the *agent* may read and write there, rather
|
|
4
|
+
than in the session directory the loop owns:
|
|
5
|
+
|
|
6
|
+
* the **scratchpad** (``--scratchpad``): a free-form note file for thoughts,
|
|
7
|
+
plans and learnings, plus as many additional scratch files as the agent
|
|
8
|
+
wants to create;
|
|
9
|
+
* the **open plan** (``--plan-strategy open-plan``): a plan document the
|
|
10
|
+
agent maintains itself with the normal file tools.
|
|
11
|
+
|
|
12
|
+
Both live under the same ``.mini`` directory as the skills folder and the
|
|
13
|
+
latest-session pointer, so they are inside the ``--allowed-dir`` sandbox and
|
|
14
|
+
the normal ``read_file`` / ``write_file`` / ``edit`` tools can reach them. The
|
|
15
|
+
directory name is read from :mod:`mini_code_cli.persistence` at call time, so
|
|
16
|
+
the test suite can redirect it globally (exactly like the session pointer).
|
|
17
|
+
"""
|
|
18
|
+
|
|
19
|
+
import os
|
|
20
|
+
|
|
21
|
+
from . import persistence
|
|
22
|
+
|
|
23
|
+
SCRATCHPAD_FILENAME = "SCRATCHPAD.md"
|
|
24
|
+
OPEN_PLAN_FILENAME = "PLAN.md"
|
|
25
|
+
|
|
26
|
+
_SCRATCHPAD_HEADER = """# Scratchpad
|
|
27
|
+
|
|
28
|
+
This file belongs to the agent. It may read and write it freely and may create
|
|
29
|
+
additional scratch files in the same directory. Use it for thoughts, plans,
|
|
30
|
+
learnings and notes that should survive a compaction.
|
|
31
|
+
"""
|
|
32
|
+
|
|
33
|
+
_OPEN_PLAN_HEADER = """# Agent Plan
|
|
34
|
+
|
|
35
|
+
This plan document belongs to the agent. Read it before continuing, keep it up
|
|
36
|
+
to date as work progresses, and mark steps done or outstanding.
|
|
37
|
+
"""
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
def mini_dir(allowed_dir):
|
|
41
|
+
"""The ``.mini`` directory inside ``allowed_dir`` (not created)."""
|
|
42
|
+
return os.path.join(os.path.abspath(allowed_dir), persistence.SESSION_DIRNAME)
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
def scratchpad_path(allowed_dir):
|
|
46
|
+
"""Path to the main scratch-pad file."""
|
|
47
|
+
return os.path.join(mini_dir(allowed_dir), SCRATCHPAD_FILENAME)
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
def open_plan_path(allowed_dir):
|
|
51
|
+
"""Path to the agent-authored plan document."""
|
|
52
|
+
return os.path.join(mini_dir(allowed_dir), OPEN_PLAN_FILENAME)
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
def ensure_scratchpad(allowed_dir):
|
|
56
|
+
"""Create the main scratch-pad file (and its directory) if missing."""
|
|
57
|
+
return _ensure_file(scratchpad_path(allowed_dir), _SCRATCHPAD_HEADER)
|
|
58
|
+
|
|
59
|
+
|
|
60
|
+
def ensure_open_plan(allowed_dir):
|
|
61
|
+
"""Create the agent plan document (and its directory) if missing."""
|
|
62
|
+
return _ensure_file(open_plan_path(allowed_dir), _OPEN_PLAN_HEADER)
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
def read_text(path, limit=None):
|
|
66
|
+
"""Read ``path`` as text, returning ``""`` when it cannot be read.
|
|
67
|
+
|
|
68
|
+
``limit`` caps the returned characters (the open-plan re-injection after a
|
|
69
|
+
compaction should not be able to re-fill the context with the document).
|
|
70
|
+
"""
|
|
71
|
+
try:
|
|
72
|
+
with open(path, "r", encoding="utf-8", errors="replace") as handle:
|
|
73
|
+
text = handle.read()
|
|
74
|
+
except OSError:
|
|
75
|
+
return ""
|
|
76
|
+
if limit is not None and len(text) > limit:
|
|
77
|
+
return text[:limit] + "\n[... truncated ...]\n"
|
|
78
|
+
return text
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
def _ensure_file(path, header):
|
|
82
|
+
"""Best-effort create-with-header; never raises, always returns ``path``."""
|
|
83
|
+
try:
|
|
84
|
+
if not os.path.isfile(path):
|
|
85
|
+
os.makedirs(os.path.dirname(path), exist_ok=True)
|
|
86
|
+
with open(path, "w", encoding="utf-8") as handle:
|
|
87
|
+
handle.write(header)
|
|
88
|
+
except OSError:
|
|
89
|
+
pass
|
|
90
|
+
return path
|