@knightcodeai/cli-linux-x64 0.6.2 → 0.8.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/bin/CHANGELOG.md +63 -0
- package/bin/docs/custom-provider.md +11 -5
- package/bin/docs/docs.json +4 -0
- package/bin/docs/environment-variables.md +1 -0
- package/bin/docs/extensions.md +12 -32
- package/bin/docs/models.md +1 -1
- package/bin/docs/remote.md +87 -0
- package/bin/docs/sdk.md +2 -2
- package/bin/docs/session-format.md +23 -7
- package/bin/docs/settings.md +2 -0
- package/bin/docs/usage.md +33 -1
- package/bin/knightcode +2 -2
- package/bin/package.json +11 -7
- package/package.json +1 -1
package/bin/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,68 @@
|
|
|
1
1
|
# @knightcodeai/cli
|
|
2
2
|
|
|
3
|
+
## 0.8.0
|
|
4
|
+
|
|
5
|
+
### Added
|
|
6
|
+
|
|
7
|
+
- Added `allowedFallbackModels` to Anthropic model overrides in `models.json`, so you can choose which models the server may fall back to — or set an empty array to turn server-side fallback off.
|
|
8
|
+
|
|
9
|
+
- Added webfetch and websearch tools — a page as pageable, greppable markdown, and results from DuckDuckGo or Brave Search — off until enabled with the new `/tools` command, which turns each built-in tool off, on for the session, or on by default, and for websearch also picks the provider and stores the Brave API key.
|
|
10
|
+
|
|
11
|
+
### Changed
|
|
12
|
+
|
|
13
|
+
- Changed the system prompt and tool set to live in the transcript instead of being rewritten behind it. A session records when its instructions changed or tools became available, resuming or moving between branches restores that state, and providers that support it keep their cached prompt prefix across the change. Extensions can replace individual prompt sections through `systemPromptOptions.sections`, and the deferred-tool loading path is replaced by mid-conversation tool additions on the models that accept them.
|
|
14
|
+
|
|
15
|
+
- Changed a failed copy to say why: instead of a bare "Copy failed" flash, the message now names the missing clipboard backend — `wl-clipboard`, `xclip`/`xsel` or the Termux API package — and stays on screen for five seconds.
|
|
16
|
+
|
|
17
|
+
### Fixed
|
|
18
|
+
|
|
19
|
+
- Fixed a `user_bash` handler that throws or returns a malformed result silently falling back to the local shell — the command is now reported as failed instead of running somewhere the extension meant to prevent. A handler must return `undefined`, exactly one of `{ operations }` or `{ result }`, and nothing else.
|
|
20
|
+
|
|
21
|
+
- Fixed Baseten requests to carry session-affinity headers so a conversation keeps hitting the same replica and benefits from automatic prompt caching.
|
|
22
|
+
|
|
23
|
+
- Fixed Bedrock cost reporting to bill one-hour cache writes at their higher rate instead of charging every cache write at the five-minute rate.
|
|
24
|
+
|
|
25
|
+
- Fixed a local copy reporting success when no clipboard backend actually took the text: the terminal-escape fallback now only counts in a remote session, where it is the terminal that owns the clipboard.
|
|
26
|
+
|
|
27
|
+
- Fixed the package's public types so extension authors can import the event and result types their hooks receive, such as `ModelSelectEvent`, `ThinkingLevelSelectEvent` and the `*Result` types, instead of redeclaring them.
|
|
28
|
+
|
|
29
|
+
- Fixed the thinking levels offered for Gemini models: they now follow the reasoning efforts each model actually advertises instead of a version-number guess, so newer Flash and Pro models expose their real low/medium/high range.
|
|
30
|
+
|
|
31
|
+
- Fixed resuming a session by its exact ID reading every transcript in the session directory first, which made startup slow in directories with long histories.
|
|
32
|
+
|
|
33
|
+
## 0.7.0
|
|
34
|
+
|
|
35
|
+
### Added
|
|
36
|
+
|
|
37
|
+
- Added a `knightcode-engine` binary: a headless local server that owns inference for the desktop IDE, with OpenAI-shaped chat and fill-in-the-middle endpoints. It shares the CLI's `auth.json`, so signing in to either product signs in to both.
|
|
38
|
+
|
|
39
|
+
- Added reopening saved sessions to `knightcode-engine`, so the desktop IDE restores its threads after a restart instead of failing with "Loading or resuming sessions is not supported by this agent".
|
|
40
|
+
|
|
41
|
+
Its ACP agent now:
|
|
42
|
+
|
|
43
|
+
- loads a session, replaying its history;
|
|
44
|
+
- resumes, lists, deletes and forks saved sessions;
|
|
45
|
+
- lists extension commands, prompt templates and skills under `/`;
|
|
46
|
+
- after an engine restart, reopens a session it no longer holds and retries the prompt.
|
|
47
|
+
|
|
48
|
+
- Added native deferred tool loading for Fireworks models on the Messages API. Name the loader tool `ToolSearch` or `tool_search` so Fireworks keeps the deferred schemas out of the cached tool prefix.
|
|
49
|
+
|
|
50
|
+
- Added a /remote command that publishes the running session to the web for the signed-in account, with a phone-first app at remote.knightcode.dev that lists live and past sessions, opens every tool call, and runs slash commands in the terminal.
|
|
51
|
+
|
|
52
|
+
### Fixed
|
|
53
|
+
|
|
54
|
+
- Fixed the full-output file of a truncated `!` bash command sometimes being empty when read straight away: the command now finishes writing that file before its result, and the file's path, are returned.
|
|
55
|
+
|
|
56
|
+
- Fixed the desktop IDE's open threads offering stale model choices after signing in or out: `knightcode-engine` now refreshes them when an account or the model catalog changes.
|
|
57
|
+
|
|
58
|
+
- Fixed API keys in a project's `.env` showing up in the desktop IDE as signed-in providers that signing out could not remove: `knightcode-engine` no longer reads a `.env` or `bunfig.toml` from the directory the IDE was launched in.
|
|
59
|
+
|
|
60
|
+
- Fixed `/` listing no commands in a new, loaded, resumed or forked thread in the desktop IDE: `knightcode-engine` sent the list before the IDE had registered the session, and the IDE dropped it.
|
|
61
|
+
|
|
62
|
+
- Fixed errors from OpenAI-compatible providers on the Responses API always being labelled as OpenAI errors: the message now names the provider that actually failed.
|
|
63
|
+
|
|
64
|
+
- Fixed Tab predictions in the desktop IDE repeating the code after the cursor: `knightcode-engine`'s `/v1/completions` now shows the model your code with the cursor marked in place, and strips code fences from the answer.
|
|
65
|
+
|
|
3
66
|
## 0.6.2
|
|
4
67
|
|
|
5
68
|
### Added
|
|
@@ -406,25 +406,31 @@ For providers with non-standard APIs, implement `streamSimple`. Study the existi
|
|
|
406
406
|
|
|
407
407
|
### Stream Pattern
|
|
408
408
|
|
|
409
|
-
All providers follow the same pattern:
|
|
409
|
+
All providers follow the same pattern. The context is a normalized transcript: the system prompt and tool declarations live in its system messages, so read them with `getCurrentSystemPrompt(context.messages)` and `getCurrentTools(context.messages)` rather than expecting `context.systemPrompt` or `context.tools`. Models that accept system messages mid-conversation can send them in place; otherwise call `collapseSystemMessages(context)` first to fold later system messages into the leading one.
|
|
410
410
|
|
|
411
411
|
```typescript
|
|
412
412
|
import {
|
|
413
413
|
type AssistantMessage,
|
|
414
414
|
type AssistantMessageEventStream,
|
|
415
|
-
type Context,
|
|
416
415
|
type Model,
|
|
417
416
|
type SimpleStreamOptions,
|
|
417
|
+
type TranscriptContext,
|
|
418
418
|
calculateCost,
|
|
419
|
+
collapseSystemMessages,
|
|
419
420
|
createAssistantMessageEventStream,
|
|
421
|
+
getCurrentSystemPrompt,
|
|
422
|
+
getCurrentTools,
|
|
420
423
|
} from "@knightcode/ai";
|
|
421
424
|
|
|
422
425
|
function streamMyProvider(
|
|
423
426
|
model: Model<any>,
|
|
424
|
-
context:
|
|
427
|
+
context: TranscriptContext,
|
|
425
428
|
options?: SimpleStreamOptions
|
|
426
429
|
): AssistantMessageEventStream {
|
|
427
430
|
const stream = createAssistantMessageEventStream();
|
|
431
|
+
const transcript = collapseSystemMessages(context);
|
|
432
|
+
const systemPrompt = getCurrentSystemPrompt(transcript.messages);
|
|
433
|
+
const tools = getCurrentTools(transcript.messages);
|
|
428
434
|
|
|
429
435
|
(async () => {
|
|
430
436
|
// Initialize output message
|
|
@@ -668,10 +674,10 @@ interface ProviderConfig {
|
|
|
668
674
|
/** API type for streaming. Required at provider or model level when defining models. */
|
|
669
675
|
api?: Api;
|
|
670
676
|
|
|
671
|
-
/** Custom streaming implementation for non-standard APIs. */
|
|
677
|
+
/** Custom streaming implementation for non-standard APIs. Receives a normalized transcript. */
|
|
672
678
|
streamSimple?: (
|
|
673
679
|
model: Model<Api>,
|
|
674
|
-
context:
|
|
680
|
+
context: TranscriptContext,
|
|
675
681
|
options?: SimpleStreamOptions
|
|
676
682
|
) => AssistantMessageEventStream;
|
|
677
683
|
|
package/bin/docs/docs.json
CHANGED
|
@@ -93,6 +93,7 @@ These variables are read by KnightCode itself:
|
|
|
93
93
|
| `KNIGHTCODE_IMAGE_PROTOCOL` | Override inline image detection with `kitty`, `iterm2`, `none`, or `auto` |
|
|
94
94
|
| `KNIGHTCODE_TRUE_COLOR` | Override truecolor detection with `1`, `0`, or `auto` |
|
|
95
95
|
| `KNIGHTCODE_TUI_ESC_TIMEOUT` | How long to wait after a lone ESC before treating it as Escape, in milliseconds; defaults to `100` over SSH and `10` otherwise. Increase if Alt-key input is misread as Escape |
|
|
96
|
+
| `BRAVE_API_KEY` | Brave Search key for `websearch` when none is stored with `/tools`; see [Web tools](usage.md#web-tools) |
|
|
96
97
|
| `VISUAL`, `EDITOR` | External editor fallback when `externalEditor` is unset |
|
|
97
98
|
| `HTTP_PROXY`, `HTTPS_PROXY` | Proxy outbound HTTP requests |
|
|
98
99
|
|
package/bin/docs/extensions.md
CHANGED
|
@@ -538,10 +538,13 @@ knightcode.on("before_agent_start", async (event, ctx) => {
|
|
|
538
538
|
// event.systemPrompt - current chained system prompt for this handler
|
|
539
539
|
// (includes changes from earlier before_agent_start handlers)
|
|
540
540
|
// event.systemPromptOptions - structured options used to build the system prompt
|
|
541
|
-
// .customPrompt -
|
|
541
|
+
// .customPrompt - exact prompt prefix from --system-prompt, SYSTEM.md, or custom templates
|
|
542
|
+
// .forceSystemPrompt - optional exact replacement for the complete prompt
|
|
542
543
|
// .selectedTools - tools currently active in the prompt
|
|
543
544
|
// .toolSnippets - one-line descriptions for each tool
|
|
544
|
-
// .
|
|
545
|
+
// .toolGuidelines - guideline bullets keyed by tool name
|
|
546
|
+
// .promptGuidelines - additional custom guideline bullets
|
|
547
|
+
// .sections - custom XML-wrapped sections keyed by tag name
|
|
545
548
|
// .appendSystemPrompt - text from --append-system-prompt flags
|
|
546
549
|
// .cwd - working directory
|
|
547
550
|
// .contextFiles - AGENTS.md files and other loaded context files
|
|
@@ -560,7 +563,7 @@ knightcode.on("before_agent_start", async (event, ctx) => {
|
|
|
560
563
|
});
|
|
561
564
|
```
|
|
562
565
|
|
|
563
|
-
The `systemPromptOptions` field gives extensions access to the same structured data KnightCode uses to build the system prompt.
|
|
566
|
+
The `systemPromptOptions` field gives extensions access to the same structured data KnightCode uses to build the system prompt. Collections are mutable. Prefer changing `sections`, `selectedTools`, or `promptGuidelines`: KnightCode diffs the resulting prompt sections against what the model already has and appends one system message patching only the changed sections. Returning `systemPrompt`, or setting `forceSystemPrompt`, replaces the whole prompt with a single untagged `preamble` section. Tool selection changes update both the prompt contributions and executable provider tools; calling `knightcode.setActiveTools()` inside the handler has the same effect as editing `selectedTools`. Models that accept system messages mid-conversation receive the patch in place and keep their cached prefix; other models get the replayed prompt as their system prompt, which is a cache miss once per change.
|
|
564
567
|
|
|
565
568
|
Inside `before_agent_start`, `event.systemPrompt` and `ctx.getSystemPrompt()` both reflect the chained system prompt as of the current handler. Later `before_agent_start` handlers can still modify it again.
|
|
566
569
|
|
|
@@ -906,6 +909,8 @@ knightcode.on("user_bash", (event, ctx) => {
|
|
|
906
909
|
});
|
|
907
910
|
```
|
|
908
911
|
|
|
912
|
+
Returning `undefined` continues to the next handler, then local execution if none handles the event. A valid result stops propagation: `operations` executes the command through the supplied backend, while `result` records the completed command without executing it.
|
|
913
|
+
|
|
909
914
|
### Input Events
|
|
910
915
|
|
|
911
916
|
#### input
|
|
@@ -1125,7 +1130,7 @@ const options = ctx.getSystemPromptOptions();
|
|
|
1125
1130
|
const contextPaths = options.contextFiles?.map((file) => file.path) ?? [];
|
|
1126
1131
|
```
|
|
1127
1132
|
|
|
1128
|
-
This has the same shape and mutability as `before_agent_start` `event.systemPromptOptions`: custom prompt, active tools, tool snippets,
|
|
1133
|
+
This has the same shape and mutability as `before_agent_start` `event.systemPromptOptions`: custom or forced prompt, active tools, tool snippets, per-tool and custom rules, custom sections, appended prompt text, cwd, loaded context files, and loaded skills. It may include full context file contents, so treat it as sensitive extension-local data and avoid exposing it through command lists, logs, or autocomplete metadata.
|
|
1129
1134
|
|
|
1130
1135
|
This reports the current base prompt inputs. It does not include per-turn `before_agent_start` chained system-prompt changes, later `context` event message mutations, or `before_provider_request` payload rewrites.
|
|
1131
1136
|
|
|
@@ -2370,38 +2375,13 @@ If a slot renderer is not defined or throws:
|
|
|
2370
2375
|
|
|
2371
2376
|
### Dynamic Tool Loading
|
|
2372
2377
|
|
|
2373
|
-
Extensions can register many tools while keeping only a small initial set active. A tool can then
|
|
2374
|
-
|
|
2375
|
-
This works with every model. Models with native deferred-loading support preserve the stable prompt prefix and load the new definitions at the tool-result position. Other models use the fallback described below.
|
|
2378
|
+
Extensions can register many tools while keeping only a small initial set active. A tool can then change the active set with `knightcode.setActiveTools()` during execution. KnightCode stores the initial prompt and tool loadout in the transcript's first system message, then appends tool and prompt deltas before the next model request. Providers that cannot represent a transition receive a complete transcript checkpoint, which may invalidate the cached prefix.
|
|
2376
2379
|
|
|
2377
2380
|
The lifecycle is:
|
|
2378
2381
|
|
|
2379
2382
|
1. Register every tool with `knightcode.registerTool()` so it appears in `knightcode.getAllTools()`.
|
|
2380
2383
|
2. Keep loader tools, such as `search_tools`, active and leave searchable tools inactive.
|
|
2381
|
-
3. During loader execution, call `knightcode.setActiveTools(
|
|
2382
|
-
4. KnightCode records which tools were added on the loader's tool result.
|
|
2383
|
-
5. Before the next model response, KnightCode exposes the added definitions using native deferred loading when supported, or the normal active tool list otherwise.
|
|
2384
|
-
|
|
2385
|
-
You do not need to return provider-specific tool references or mark the loader as a special search tool. The active-tool change is the signal. Names passed to `knightcode.setActiveTools()` must already be registered; unknown names are ignored.
|
|
2386
|
-
|
|
2387
|
-
#### Models with native deferred loading
|
|
2388
|
-
|
|
2389
|
-
- **Anthropic**
|
|
2390
|
-
- **Models:** Sonnet, Opus, Fable version 4.5 or newer (without Haiku)
|
|
2391
|
-
- **Native representation:** Deferred definitions use `defer_loading`; the load point uses `tool_reference` content.
|
|
2392
|
-
- **OpenAI**
|
|
2393
|
-
- **Models:** `gpt-5.4` and newer family
|
|
2394
|
-
- **Native representation:** KnightCode adds completed client `tool_search_call` and `tool_search_output` items at the load point.
|
|
2395
|
-
|
|
2396
|
-
For a verified custom model or proxy, native handling can be enabled with `compat.supportsToolReferences: true` for `anthropic-messages`, or `compat.supportsToolSearch: true` for `openai-responses` and `openai-codex-responses`. Leave these disabled unless the endpoint and model accept the corresponding native protocol.
|
|
2397
|
-
|
|
2398
|
-
#### Fallback behavior
|
|
2399
|
-
|
|
2400
|
-
For all other models and providers, dynamic activation still works: KnightCode sends the complete current active tool list normally on the next request. The model can call the newly activated tools, but adding their definitions may invalidate the provider's cached prompt prefix.
|
|
2401
|
-
|
|
2402
|
-
KnightCode also uses this safe fallback when the active set is not purely additive, such as replacing one group of tools with another. Tool removals therefore work, but they do not use deferred loading.
|
|
2403
|
-
|
|
2404
|
-
For the best cache behavior, keep the loader tool active for the whole session and add tools instead of replacing the active set. Also note that activating a tool with `promptSnippet` or `promptGuidelines` rebuilds the system prompt; that system-prompt change can invalidate the prefix even when the provider supports deferred schemas. Lazily loaded tools should usually rely on their tool `description` and omit active-only prompt metadata.
|
|
2384
|
+
3. During loader execution, call `knightcode.setActiveTools()` with the desired active tool names. Names must already be registered; unknown names are ignored.
|
|
2405
2385
|
|
|
2406
2386
|
#### Search tool example
|
|
2407
2387
|
|
|
@@ -2503,7 +2483,7 @@ export default function (knightcode: ExtensionAPI) {
|
|
|
2503
2483
|
}
|
|
2504
2484
|
```
|
|
2505
2485
|
|
|
2506
|
-
When `search_tools` adds a match, the model receives
|
|
2486
|
+
When `search_tools` adds a match, the model receives the complete updated tool list on the immediately following request.
|
|
2507
2487
|
|
|
2508
2488
|
## Custom UI
|
|
2509
2489
|
|
package/bin/docs/models.md
CHANGED
|
@@ -436,6 +436,7 @@ Built-in Anthropic models enable `supportsStrictTools` in their model metadata.
|
|
|
436
436
|
| `supportsMidConvoEffort` | Whether the exact Claude model transport supports per-turn effort system messages and thinking binding controls. KnightCode persists native effort levels and always sends `drop_block` when enabled. Default: `false`. |
|
|
437
437
|
| `allowEmptySignature` | Whether to replay empty thinking signatures as `signature: ""` instead of converting thinking to text. Default: `false`. |
|
|
438
438
|
| `supportsStrictTools` | Whether the provider accepts strict JSON-schema tool definitions. Default: `false`; built-in Anthropic models enable it in generated metadata. |
|
|
439
|
+
| `allowedFallbackModels` | Up to three server-side fallback models, each with `provider`, `model`, and complete `cost` metadata. An empty array disables fallback. |
|
|
439
440
|
|
|
440
441
|
## OpenAI Compatibility
|
|
441
442
|
|
|
@@ -482,7 +483,6 @@ For providers with partial OpenAI compatibility, use the `compat` field.
|
|
|
482
483
|
| `sessionAffinityFormat` | For `openai-completions` and `openai-responses`, the session-affinity header format: `openai` sends `session_id`/`x-client-request-id` (completions also `x-session-affinity`), `openai-nosession` omits the underscore-containing `session_id` header, `openrouter` sends `x-session-id`. Does not affect the `prompt_cache_key` body param. Default: auto-detected. |
|
|
483
484
|
| `supportsStrictMode` | Whether the provider accepts strict JSON-schema function tool definitions. Defaults depend on the API; built-in OpenAI models carry explicit capability metadata. |
|
|
484
485
|
| `supportsOpenAIGrammarTools` | Whether OpenAI-compatible APIs emit custom Lark/regex grammar tools. When `false`, grammar-constrained tools fall back to normal function tools. Default: `false`; the built-in model catalog enables it for GPT-5+ models on OpenAI, OpenAI Codex, Azure OpenAI, GitHub Copilot, opencode, and Cloudflare AI Gateway. |
|
|
485
|
-
| `deferredToolsMode` | Use provider-specific deferred tool serialization. Currently only `"kimi"` is supported for Kimi's OpenAI-compatible Chat Completions format. |
|
|
486
486
|
| `supportsLongCacheRetention` | Whether the provider accepts long cache retention when cache retention is `long`: `prompt_cache_options.ttl: "30m"` for GPT-5.6+ Responses models, `prompt_cache_retention: "24h"` for earlier OpenAI models, or `cache_control.ttl: "1h"` when `cacheControlFormat` is `anthropic`. Default: `true`. |
|
|
487
487
|
| `openRouterRouting` | OpenRouter provider routing preferences. This object is sent as-is in the `provider` field of the [OpenRouter API request](https://openrouter.ai/docs/guides/routing/provider-selection). |
|
|
488
488
|
| `vercelGatewayRouting` | Vercel AI Gateway routing config for provider selection (`only`, `order`) |
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
# Remote sessions
|
|
2
|
+
|
|
3
|
+
`/remote` publishes the session running in your terminal to the web, so you can
|
|
4
|
+
watch it and reply from another device. The terminal keeps working normally.
|
|
5
|
+
|
|
6
|
+
## Getting started
|
|
7
|
+
|
|
8
|
+
Run `/remote`. The first time, a sign-in screen opens your browser on the
|
|
9
|
+
approval page and shows an eight-character code: sign in with GitHub, check the
|
|
10
|
+
page shows the same code, and approve. Escape cancels. The credential is stored
|
|
11
|
+
in `~/.knightcode/remote-auth.json` and reused afterwards, and the screen also
|
|
12
|
+
prints the URL for a headless box where nothing launched. Once the browser
|
|
13
|
+
approves, the screen confirms it and continues on enter, or by itself a few
|
|
14
|
+
seconds later.
|
|
15
|
+
|
|
16
|
+
Once signed in, `/remote` prints a link. You do not have to copy it: open
|
|
17
|
+
<https://remote.knightcode.dev> on your phone and the session appears in the
|
|
18
|
+
list.
|
|
19
|
+
|
|
20
|
+
## The web app
|
|
21
|
+
|
|
22
|
+
The list shows every session you have published, newest first, with its state:
|
|
23
|
+
**Working** while a turn is running in the terminal, **Connected** while the
|
|
24
|
+
terminal is attached and idle, **Disconnected** once it has gone. Filter it to
|
|
25
|
+
active or past sessions from the menu on the right.
|
|
26
|
+
|
|
27
|
+
Open a session to read the transcript. Runs of tool calls are folded into one
|
|
28
|
+
line such as _Ran 2 commands, created a file_; tap it to list the calls, and
|
|
29
|
+
tap a call to see what it did — the command and its output, the file and its
|
|
30
|
+
content, the diff an edit made.
|
|
31
|
+
|
|
32
|
+
The composer sends replies to the terminal. Type `/` to list the slash commands
|
|
33
|
+
the terminal can run from a message: extension commands, skills and prompt
|
|
34
|
+
templates. Built-in commands that open a terminal UI, such as `/model`, are not
|
|
35
|
+
offered.
|
|
36
|
+
|
|
37
|
+
The menu in the session's top-right corner copies the link or deletes the
|
|
38
|
+
session from the relay.
|
|
39
|
+
|
|
40
|
+
## Commands
|
|
41
|
+
|
|
42
|
+
| Command | Effect |
|
|
43
|
+
| --- | --- |
|
|
44
|
+
| `/remote` | Toggle publishing: start and print the link, or pause. Pausing keeps the room readable, and the next `/remote` resumes the same link |
|
|
45
|
+
| `/remote status` | Show the link and how many viewers are connected |
|
|
46
|
+
| `/remote stop` | Stop publishing and delete the room |
|
|
47
|
+
| `/remote logout` | Revoke the stored account credential and delete it locally |
|
|
48
|
+
|
|
49
|
+
`/remote` runs in the interactive terminal only. In `--print`, RPC and JSON
|
|
50
|
+
modes it reports that and does nothing.
|
|
51
|
+
|
|
52
|
+
## What the remote can and cannot do
|
|
53
|
+
|
|
54
|
+
A viewer can read the transcript, send prompts, run the slash commands listed
|
|
55
|
+
above, and stop the current turn. Prompts arrive as ordinary user messages and
|
|
56
|
+
appear in your terminal; `/remote` itself is never offered to a viewer.
|
|
57
|
+
|
|
58
|
+
A viewer cannot end your session, quit KnightCode, switch sessions, or change
|
|
59
|
+
model. Closing the browser tab, losing signal, or losing the relay does nothing
|
|
60
|
+
to the terminal. Your session ends only when you end it.
|
|
61
|
+
|
|
62
|
+
If the relay becomes unreachable the command does not fail: it reconnects with
|
|
63
|
+
backoff indefinitely, the footer shows `remote retrying`, and the agent carries
|
|
64
|
+
on working.
|
|
65
|
+
|
|
66
|
+
## Privacy and retention
|
|
67
|
+
|
|
68
|
+
Room contents pass through and are briefly stored by the relay so a device that
|
|
69
|
+
reconnects can catch up. That includes tool output, which can contain secrets if
|
|
70
|
+
a command prints them. Nothing is redacted: anything visible in your terminal is
|
|
71
|
+
visible in the room while it lives. Only the account that created a room can
|
|
72
|
+
read it.
|
|
73
|
+
|
|
74
|
+
A room stays readable as a past session for 30 days after the terminal
|
|
75
|
+
disconnects, and is deleted then, on `/remote stop`, or when you delete it from
|
|
76
|
+
the web app. Stored history is capped at 8 MB per room; older content is
|
|
77
|
+
dropped as the session grows. Images are not mirrored in either direction — an
|
|
78
|
+
image in the transcript appears as a placeholder recording its type and size.
|
|
79
|
+
|
|
80
|
+
## Configuration
|
|
81
|
+
|
|
82
|
+
| Environment variable | Default | Effect |
|
|
83
|
+
| --- | --- | --- |
|
|
84
|
+
| `KNIGHTCODE_REMOTE_RELAY` | `https://remote.knightcode.dev` | Relay origin to publish to |
|
|
85
|
+
| `KNIGHTCODE_REMOTE_CONFIG_DIR` | `~/.knightcode` | Directory holding `remote-auth.json` |
|
|
86
|
+
|
|
87
|
+
`/remote` refuses to start when `KNIGHTCODE_OFFLINE` is set.
|
package/bin/docs/sdk.md
CHANGED
|
@@ -246,8 +246,8 @@ const state = session.agent.state;
|
|
|
246
246
|
// state.messages: AgentMessage[] - conversation history
|
|
247
247
|
// state.model: Model - current model
|
|
248
248
|
// state.thinkingLevel: ThinkingLevel - current thinking level
|
|
249
|
-
// state.systemPrompt: string - system
|
|
250
|
-
// state.tools: AgentTool[] -
|
|
249
|
+
// state.systemPrompt: string - read-only, replayed from the transcript's system messages
|
|
250
|
+
// state.tools: AgentTool[] - executable tools; changes are declared to the model before the next request
|
|
251
251
|
// state.streamingMessage?: AgentMessage - current partial assistant message
|
|
252
252
|
// state.errorMessage?: string - latest assistant error
|
|
253
253
|
|
|
@@ -77,6 +77,14 @@ interface ToolCall {
|
|
|
77
77
|
### Base Message Types (from @knightcode/ai)
|
|
78
78
|
|
|
79
79
|
```typescript
|
|
80
|
+
interface SystemMessage {
|
|
81
|
+
role: "system";
|
|
82
|
+
content: string | TextContent[];
|
|
83
|
+
toolsAdded?: Tool[];
|
|
84
|
+
toolsRemoved?: Array<{ name: string }>;
|
|
85
|
+
timestamp: number; // Unix ms
|
|
86
|
+
}
|
|
87
|
+
|
|
80
88
|
interface UserMessage {
|
|
81
89
|
role: "user";
|
|
82
90
|
content: string | (TextContent | ImageContent)[];
|
|
@@ -109,7 +117,6 @@ interface ToolResultMessage {
|
|
|
109
117
|
content: (TextContent | ImageContent)[];
|
|
110
118
|
details?: any; // Tool-specific metadata
|
|
111
119
|
usage?: Usage; // Nested LLM work performed by the tool
|
|
112
|
-
addedToolNames?: string[];
|
|
113
120
|
isError: boolean;
|
|
114
121
|
timestamp: number;
|
|
115
122
|
}
|
|
@@ -177,6 +184,7 @@ interface CompactionSummaryMessage {
|
|
|
177
184
|
|
|
178
185
|
```typescript
|
|
179
186
|
type AgentMessage =
|
|
187
|
+
| SystemMessage
|
|
180
188
|
| UserMessage
|
|
181
189
|
| AssistantMessage
|
|
182
190
|
| ToolResultMessage
|
|
@@ -217,7 +225,14 @@ For sessions with a parent (created via `/fork`, `/clone`, or `newSession({ pare
|
|
|
217
225
|
|
|
218
226
|
### SessionMessageEntry
|
|
219
227
|
|
|
220
|
-
A message in the conversation. The `message` field contains an `AgentMessage`.
|
|
228
|
+
A message in the conversation. The `message` field contains an `AgentMessage`. System messages carry the prompt and tool loadout: the first request of a session persists one with every prompt section and tool declaration, and later changes persist as system messages that patch `sections` by name (`null` removes one) and list `toolsAdded`/`toolsRemoved`. Replaying them in order yields the current prompt and tools; there is no separate prompt state entry.
|
|
229
|
+
|
|
230
|
+
```json
|
|
231
|
+
{"type":"message","id":"a0b1c2d3","parentId":null,"timestamp":"2024-12-03T14:00:00.000Z","message":{"role":"system","content":"","sections":{"preamble":"You are an expert coding assistant...","tools":"<tools>\n- read: ...\n</tools>","cwd":"/project"},"toolsAdded":[{"name":"read","description":"...","parameters":{}}],"timestamp":1733234400000}}
|
|
232
|
+
{"type":"message","id":"d4e5f6g7","parentId":"c3d4e5f6","timestamp":"2024-12-03T14:04:00.000Z","message":{"role":"system","content":"","sections":{"skills":"<skills>...</skills>"},"toolsRemoved":[{"name":"write"}],"timestamp":1733234640000}}
|
|
233
|
+
```
|
|
234
|
+
|
|
235
|
+
Sessions created before system messages existed have no leading system message; the first request declares the current prompt as a later system message, which replays the same way.
|
|
221
236
|
|
|
222
237
|
```json
|
|
223
238
|
{"type":"message","id":"a1b2c3d4","parentId":"prev1234","timestamp":"2024-12-03T14:00:01.000Z","message":{"role":"user","content":"Hello","timestamp":1733234401000}}
|
|
@@ -243,15 +258,16 @@ Emitted when the user changes the thinking/reasoning level.
|
|
|
243
258
|
|
|
244
259
|
### CompactionEntry
|
|
245
260
|
|
|
246
|
-
Created when context is compacted. Stores a summary of earlier messages.
|
|
261
|
+
Created when context is compacted. Stores a summary of earlier messages and a complete system prompt/tool checkpoint.
|
|
247
262
|
|
|
248
263
|
```json
|
|
249
|
-
{"type":"compaction","id":"f6g7h8i9","parentId":"e5f6g7h8","timestamp":"2024-12-03T14:10:00.000Z","summary":"User discussed X, Y, Z...","firstKeptEntryId":"c3d4e5f6","tokensBefore":50000}
|
|
264
|
+
{"type":"compaction","id":"f6g7h8i9","parentId":"e5f6g7h8","timestamp":"2024-12-03T14:10:00.000Z","summary":"User discussed X, Y, Z...","firstKeptEntryId":"c3d4e5f6","tokensBefore":50000,"systemMessage":{"role":"system","content":"You are a coding assistant.","toolsAdded":[],"timestamp":1733235000000}}
|
|
250
265
|
```
|
|
251
266
|
|
|
252
267
|
`firstKeptEntryId` is required. It identifies the first entry retained from before the compaction entry. When rebuilding context, KnightCode replaces older summarized entries with the compaction summary and keeps the range beginning at this entry.
|
|
253
268
|
|
|
254
269
|
Optional fields:
|
|
270
|
+
- `systemMessage`: The replayed prompt sections and tool declarations at the compaction boundary; it becomes the leading system message of the compacted context, and system messages among the kept entries are dropped in its favor. It is absent on older session entries.
|
|
255
271
|
- `usage`: LLM usage from generating the summary; included in session token and cost totals
|
|
256
272
|
- `details`: Implementation-specific data (e.g., `{ readFiles: string[], modifiedFiles: string[] }` for default, or custom data for extensions)
|
|
257
273
|
- `fromHook`: `true` if generated by an extension, `false`/`undefined` if knightcode-generated (legacy field name)
|
|
@@ -336,7 +352,7 @@ Entries normally form one tree, but navigation APIs can create multiple roots:
|
|
|
336
352
|
1. Collects all entries on the path
|
|
337
353
|
2. If one or more `CompactionEntry` values are on the path, uses the latest one:
|
|
338
354
|
- Includes the compaction entry first
|
|
339
|
-
- Includes entries from `firstKeptEntryId` up to, but not including, the compaction entry
|
|
355
|
+
- Includes non-system entries from `firstKeptEntryId` up to, but not including, the compaction entry
|
|
340
356
|
- Includes entries after the compaction entry
|
|
341
357
|
3. Preserves non-message entries in the selected range so interactive mode can render them
|
|
342
358
|
|
|
@@ -345,12 +361,12 @@ Entries normally form one tree, but navigation APIs can create multiple roots:
|
|
|
345
361
|
1. Extracts current model and thinking level settings from the full path
|
|
346
362
|
2. Converts selected entries to messages:
|
|
347
363
|
- `message` -> stored `AgentMessage`
|
|
348
|
-
- `compaction` -> `compactionSummary`
|
|
364
|
+
- `compaction` -> complete system checkpoint followed by `compactionSummary`
|
|
349
365
|
- `branch_summary` -> `branchSummary`
|
|
350
366
|
- `custom_message` -> `CustomMessage`
|
|
351
367
|
- `custom` -> no context message
|
|
352
368
|
|
|
353
|
-
The compaction summary replaces entries before `firstKeptEntryId`.
|
|
369
|
+
The compaction summary replaces entries before `firstKeptEntryId`. Pre-compaction system messages are folded into the complete checkpoint rather than replayed from the retained range. Retained non-system entries and all entries after the compaction remain available to the LLM.
|
|
354
370
|
|
|
355
371
|
## Parsing Example
|
|
356
372
|
|
package/bin/docs/settings.md
CHANGED
|
@@ -279,6 +279,8 @@ On Windows, select `powershell` instead of `bash`, or include both:
|
|
|
279
279
|
|
|
280
280
|
An empty array starts with no built-in tools while preserving extension and SDK custom tools. `--tools` replaces this behavior with a strict allowlist for all tools, `--no-tools` disables all tools, and `--no-builtin-tools` disables the built-in defaults. `--exclude-tools` filters the resulting list. A project `defaultTools` array replaces the global array.
|
|
281
281
|
|
|
282
|
+
The [web tools](usage.md#web-tools) `webfetch` and `websearch` are not part of `defaultTools`. `/tools` turns them on and stores their settings, including the search provider and Brave key, in `~/.knightcode/agent/tools.json`.
|
|
283
|
+
|
|
282
284
|
### Sessions
|
|
283
285
|
|
|
284
286
|
| Setting | Type | Default | Description |
|
package/bin/docs/usage.md
CHANGED
|
@@ -42,6 +42,7 @@ Type `/` in the editor to open command completion. Extensions can register custo
|
|
|
42
42
|
| `/thinking` | Switch thinking level; Ctrl+S or Ctrl+D in the picker saves the startup default |
|
|
43
43
|
| `/scoped-models` | Enable/disable models for Ctrl+P cycling |
|
|
44
44
|
| `/settings` | Theme, message delivery, transport, and other preferences |
|
|
45
|
+
| [`/tools`](#web-tools) | Turn `webfetch` and `websearch` off, on for this session, or on by default; pick the search provider and store its key |
|
|
45
46
|
| `/resume` | Pick from previous sessions |
|
|
46
47
|
| `/new` | Start a new session |
|
|
47
48
|
| `/name <name>` | Set session display name |
|
|
@@ -60,6 +61,37 @@ Type `/` in the editor to open command completion. Extensions can register custo
|
|
|
60
61
|
| `/changelog` | Display version history |
|
|
61
62
|
| `/quit` | Quit knightcode |
|
|
62
63
|
|
|
64
|
+
## Web Tools
|
|
65
|
+
|
|
66
|
+
Two tools give the agent read access to the web. Both ship disabled; turn them on with `/tools`.
|
|
67
|
+
|
|
68
|
+
| Tool | What it does |
|
|
69
|
+
|------|--------------|
|
|
70
|
+
| `webfetch` | Fetches a URL and returns the page as markdown, 400 lines at a time. The agent pages with `offset`/`limit` like `read`, or passes `grep` to get only matching lines. Responses are cached for 15 minutes, capped at 5 MB, and time out after 30 seconds. Private, loopback, and link-local addresses are refused. |
|
|
71
|
+
| `websearch` | Searches the web and returns up to 10 results (default 5) as title, URL, and snippet. DuckDuckGo needs no key but may rate-limit; Brave Search needs an API key. |
|
|
72
|
+
|
|
73
|
+
`/tools` lists each tool with its current state; pick one to open its settings panel. **Status** cycles through three states:
|
|
74
|
+
|
|
75
|
+
| State | Effect |
|
|
76
|
+
|-------|--------|
|
|
77
|
+
| Disabled | The tool is not offered to the model |
|
|
78
|
+
| Enabled for this session | On until knightcode exits, including across `/new`, `/resume`, and `/fork`; nothing is written to disk |
|
|
79
|
+
| Enabled by default | On in every session |
|
|
80
|
+
|
|
81
|
+
The `websearch` panel adds two rows: **Provider** (`duckduckgo` or `brave`) and **Brave API key**. Choosing Brave without a stored key opens the key prompt at once. Get a key at https://brave.com/search/api/; the free plan is enough. The key is also read from `BRAVE_API_KEY` when none is stored, but the provider only switches to Brave when you pick it. Keys show masked in the panel.
|
|
82
|
+
|
|
83
|
+
The same changes work without the panel:
|
|
84
|
+
|
|
85
|
+
```bash
|
|
86
|
+
/tools websearch on # this session
|
|
87
|
+
/tools webfetch always # every session
|
|
88
|
+
/tools webfetch off
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
Settings are stored in `~/.knightcode/agent/tools.json`, owner-readable only because it can hold the Brave key. `--tools` and `--exclude-tools` still apply: a tool excluded on the command line stays off whatever `/tools` says.
|
|
92
|
+
|
|
93
|
+
Fetched pages and search results are marked as untrusted in the tool output so the model treats instructions inside them as data, but treat the tools like any other network access: a fetched page can still influence what the agent does next.
|
|
94
|
+
|
|
63
95
|
## Message Queue
|
|
64
96
|
|
|
65
97
|
You can submit messages while the agent is still working:
|
|
@@ -212,7 +244,7 @@ cat README.md | knightcode -p "Summarize this text"
|
|
|
212
244
|
| `--no-builtin-tools`, `-nbt` | Disable built-in tools but keep extension/custom tools enabled |
|
|
213
245
|
| `--no-tools`, `-nt` | Disable all tools |
|
|
214
246
|
|
|
215
|
-
Built-in tools: `read`, `bash`, `powershell` (Windows), `edit`, `write`, `grep`, `find`, `ls`.
|
|
247
|
+
Built-in tools: `read`, `bash`, `powershell` (Windows), `edit`, `write`, `grep`, `find`, `ls`. The [web tools](#web-tools) `webfetch` and `websearch` are off until enabled with `/tools`.
|
|
216
248
|
|
|
217
249
|
### Resource Options
|
|
218
250
|
|
package/bin/knightcode
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
[diffend] Oversized file quarantined before diffing.
|
|
2
2
|
name: package/bin/knightcode
|
|
3
|
-
size:
|
|
4
|
-
sha256:
|
|
3
|
+
size: 117447166 bytes
|
|
4
|
+
sha256: 7d7e0678a4920ce09880c0016816a1a91fd224d7f3e2e110851deb0939894967
|
package/bin/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@knightcodeai/cli",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.8.0",
|
|
4
4
|
"description": "KnightCode — a local, BYOK terminal coding agent powered by OpenRouter.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"repository": {
|
|
@@ -37,17 +37,20 @@
|
|
|
37
37
|
"test": "vitest --run"
|
|
38
38
|
},
|
|
39
39
|
"optionalDependencies": {
|
|
40
|
-
"@knightcodeai/cli-linux-x64": "0.
|
|
41
|
-
"@knightcodeai/cli-linux-arm64": "0.
|
|
42
|
-
"@knightcodeai/cli-darwin-x64": "0.
|
|
43
|
-
"@knightcodeai/cli-darwin-arm64": "0.
|
|
44
|
-
"@knightcodeai/cli-win32-x64": "0.
|
|
40
|
+
"@knightcodeai/cli-linux-x64": "0.8.0",
|
|
41
|
+
"@knightcodeai/cli-linux-arm64": "0.8.0",
|
|
42
|
+
"@knightcodeai/cli-darwin-x64": "0.8.0",
|
|
43
|
+
"@knightcodeai/cli-darwin-arm64": "0.8.0",
|
|
44
|
+
"@knightcodeai/cli-win32-x64": "0.8.0"
|
|
45
45
|
},
|
|
46
46
|
"devDependencies": {
|
|
47
|
+
"@agentclientprotocol/sdk": "1.4.0",
|
|
47
48
|
"@knightcode/agent": "workspace:*",
|
|
48
49
|
"@knightcode/ai": "workspace:*",
|
|
49
50
|
"@knightcode/client": "workspace:*",
|
|
50
51
|
"@knightcode/protocol": "workspace:*",
|
|
52
|
+
"@knightcode/remote": "workspace:*",
|
|
53
|
+
"@knightcode/tools": "workspace:*",
|
|
51
54
|
"@knightcode/server": "workspace:*",
|
|
52
55
|
"@knightcode/session-backend-sqlite": "workspace:*",
|
|
53
56
|
"@knightcode/tui": "workspace:*",
|
|
@@ -70,6 +73,7 @@
|
|
|
70
73
|
"semver": "7.8.5",
|
|
71
74
|
"typebox": "1.3.27",
|
|
72
75
|
"undici": "8.10.2",
|
|
73
|
-
"yaml": "2.9.0"
|
|
76
|
+
"yaml": "2.9.0",
|
|
77
|
+
"zod": "4.4.3"
|
|
74
78
|
}
|
|
75
79
|
}
|