@openviking/openclaw-plugin 2026.5.10-dev.3 → 2026.5.21

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/INSTALL-AGENT.md CHANGED
@@ -9,14 +9,14 @@ User-facing docs:
9
9
 
10
10
  ## Identity
11
11
 
12
- This package is the OpenClaw plugin `@openclaw/openviking`.
12
+ This package is the OpenClaw plugin `@openviking/openclaw-plugin`.
13
13
 
14
14
  | User intent | Command |
15
15
  | --- | --- |
16
- | Fresh install, latest | `openclaw plugins install @openclaw/openviking` |
17
- | Upgrade plugin to latest | `openclaw plugins install @openclaw/openviking` |
16
+ | Fresh install, latest | `openclaw plugins install clawhub:@openviking/openclaw-plugin` |
17
+ | Upgrade plugin to latest | `openclaw plugins install clawhub:@openviking/openclaw-plugin` |
18
18
  | Install or upgrade a specific release | Use the published ClawHub package selector if available; otherwise ask before using backup `ov-install --plugin-version=<REF>` |
19
- | Upgrade only the plugin | `openclaw plugins install @openclaw/openviking` |
19
+ | Upgrade only the plugin | `openclaw plugins install clawhub:@openviking/openclaw-plugin` |
20
20
  | Show installed plugins | `openclaw plugins list` |
21
21
  | Backup install when ClawHub is unavailable | `npx -y openclaw-openviking-setup-helper@latest --base-url <URL> [--api-key <KEY>]` |
22
22
  | Operate on a specific OpenClaw instance | add `--workdir <path>` |
@@ -31,7 +31,7 @@ clawhub install openviking
31
31
  That installs an AgentSkill, not the plugin. The plugin install command is:
32
32
 
33
33
  ```bash
34
- openclaw plugins install @openclaw/openviking
34
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
35
35
  ```
36
36
 
37
37
  ## Required Inputs
@@ -53,7 +53,7 @@ Never silently replace another context engine.
53
53
  Use this workflow for normal installs and upgrades from published packages.
54
54
 
55
55
  ```bash
56
- openclaw plugins install @openclaw/openviking
56
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
57
57
  openclaw openviking setup --base-url <OPENVIKING_URL> --api-key <API_KEY> --json
58
58
  openclaw gateway restart
59
59
  openclaw openviking status --json
@@ -62,7 +62,7 @@ openclaw openviking status --json
62
62
  If the registry prefix is required:
63
63
 
64
64
  ```bash
65
- openclaw plugins install clawhub:@openclaw/openviking
65
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
66
66
  ```
67
67
 
68
68
  ## Setup JSON Contract
@@ -157,7 +157,7 @@ Requirements:
157
157
 
158
158
  Version boundaries:
159
159
 
160
- - `2026.4.8` is the minimum supported OpenClaw version for the current `@openclaw/openviking` plugin.
160
+ - `2026.4.8` is the minimum supported OpenClaw version for the current `@openviking/openclaw-plugin` plugin.
161
161
  - `2026.5.3` starts requiring compiled JavaScript runtime output during package install when a plugin package declares TypeScript entries.
162
162
  - `2026.5.4` and later no longer fall back to `.ts` source for installed/global plugin runtime loading when the compiled JavaScript output is missing; the plugin may be skipped.
163
163
  - Published ClawHub packages are built before release and include `dist/*.js`, so normal users do not need to build locally.
@@ -220,7 +220,7 @@ openclaw plugins list
220
220
  Fresh install:
221
221
 
222
222
  ```bash
223
- openclaw plugins install @openclaw/openviking
223
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
224
224
  openclaw openviking setup --base-url <OPENVIKING_URL> --api-key <API_KEY> --json
225
225
  openclaw gateway restart
226
226
  openclaw openviking status --json
@@ -307,7 +307,7 @@ Same plugin ID (openviking, >= 0.3.x):
307
307
 
308
308
  ```bash
309
309
  rm -rf ~/.openclaw/extensions/openviking/
310
- openclaw plugins install @openclaw/openviking
310
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
311
311
  openclaw openviking setup --reconfigure
312
312
  openclaw gateway restart
313
313
  openclaw openviking status --json
@@ -319,7 +319,7 @@ Old plugin ID (memory-openviking, < 0.3.x):
319
319
  openclaw plugins uninstall memory-openviking 2>/dev/null || true
320
320
  openclaw config set plugins.slots.memory none
321
321
  rm -rf ~/.openclaw/extensions/memory-openviking/
322
- openclaw plugins install @openclaw/openviking
322
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
323
323
  openclaw openviking setup --base-url <OPENVIKING_URL> --api-key <API_KEY> --json
324
324
  openclaw gateway restart
325
325
  openclaw openviking status --json
@@ -333,7 +333,7 @@ Existing config fields are preserved during migration. The new plugin reads old
333
333
 
334
334
  ## Backup Path: ov-install
335
335
 
336
- `ov-install` is the backup path, not the primary user install path. Use it when `openclaw plugins install @openclaw/openviking` cannot reach ClawHub, is rate-limited, or when the user explicitly wants a source ref / Git branch install.
336
+ `ov-install` is the backup path, not the primary user install path. Use it when `openclaw plugins install clawhub:@openviking/openclaw-plugin` cannot reach ClawHub, is rate-limited, or when the user explicitly wants a source ref / Git branch install.
337
337
 
338
338
  Backup install:
339
339
 
@@ -352,4 +352,4 @@ Backup/source commands:
352
352
  | Show helper-tracked version | `ov-install --current-version` |
353
353
  | Update helper-managed install | `ov-install --update` |
354
354
 
355
- For user installs, always try `openclaw plugins install @openclaw/openviking` first. Choose `ov-install` only as the backup path.
355
+ For user installs, always try `openclaw plugins install clawhub:@openviking/openclaw-plugin` first. Choose `ov-install` only as the backup path.
package/INSTALL-ZH.md CHANGED
@@ -1,12 +1,12 @@
1
1
  # 为 OpenClaw 安装 OpenViking
2
2
 
3
- OpenViking 通过 `@openclaw/openviking` 插件为 OpenClaw 提供长期记忆、知识库检索、语义搜索和 RAG 上下文能力。
3
+ OpenViking 通过 `@openviking/openclaw-plugin` 插件为 OpenClaw 提供长期记忆、知识库检索、语义搜索和 RAG 上下文能力。
4
4
 
5
5
  这份文档同时面向用户和自动化 agent:用户可以按步骤执行,agent 可以按命令和 JSON 结果判断下一步。
6
6
 
7
7
  ## 不要把插件和 Skill 装混
8
8
 
9
- `@openclaw/openviking` 是 OpenClaw 插件。
9
+ `@openviking/openclaw-plugin` 是 OpenClaw 插件。
10
10
 
11
11
  不要用下面这个命令安装本插件:
12
12
 
@@ -19,7 +19,7 @@ clawhub install openviking
19
19
  安装插件应使用:
20
20
 
21
21
  ```bash
22
- openclaw plugins install @openclaw/openviking
22
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
23
23
  ```
24
24
 
25
25
  ## 前置要求
@@ -36,7 +36,7 @@ OpenClaw 插件包版本边界:
36
36
  - `2026.4.8` 是当前插件支持的最低 OpenClaw 版本。
37
37
  - `2026.5.3` 开始,OpenClaw 在安装包时会校验 TypeScript 插件入口是否有编译后的 JavaScript 产物。
38
38
  - `2026.5.4` 及之后,已安装/全局插件如果缺少编译后的 JavaScript,运行时不再回退加载 `.ts` 源码,插件可能被跳过。
39
- - 推荐的 `openclaw plugins install @openclaw/openviking` 会安装已经发布并包含 `dist/*.js` 的插件包,普通用户不需要本地编译。
39
+ - 推荐的 `openclaw plugins install clawhub:@openviking/openclaw-plugin` 会安装已经发布并包含 `dist/*.js` 的插件包,普通用户不需要本地编译。
40
40
  - `ov-install` 是备用/源码安装路径。当 ClawHub 或 OpenClaw 插件管理器路径不可用、被限流,或者明确需要测试源码 ref 时才使用。目标 OpenClaw `>= 2026.5.3` 时,它会在安装过程中编译插件。
41
41
 
42
42
  快速检查:
@@ -87,13 +87,13 @@ curl http://127.0.0.1:1933/health
87
87
  ### 1. 安装插件
88
88
 
89
89
  ```bash
90
- openclaw plugins install @openclaw/openviking
90
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
91
91
  ```
92
92
 
93
93
  如果你的 OpenClaw 环境需要显式 registry 前缀,使用:
94
94
 
95
95
  ```bash
96
- openclaw plugins install clawhub:@openclaw/openviking
96
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
97
97
  ```
98
98
 
99
99
  ### 2. 配置插件
@@ -271,7 +271,7 @@ python examples/openclaw-plugin/health_check_tools/ov-healthcheck.py
271
271
 
272
272
  ## 备用路径:ov-install
273
273
 
274
- `ov-install` 是备用路径,不是主安装方式。仅当 `openclaw plugins install @openclaw/openviking` 无法访问 ClawHub、被限流,或者你明确需要从 Git 分支/源码 ref 安装测试时使用。
274
+ `ov-install` 是备用路径,不是主安装方式。仅当 `openclaw plugins install clawhub:@openviking/openclaw-plugin` 无法访问 ClawHub、被限流,或者你明确需要从 Git 分支/源码 ref 安装测试时使用。
275
275
 
276
276
  先尝试 OpenClaw 插件管理器。如果该路径不可用,再执行:
277
277
 
@@ -285,14 +285,14 @@ ov-install
285
285
  | 参数 | 含义 |
286
286
  | --- | --- |
287
287
  | `--workdir PATH` | 指定 OpenClaw state 目录 |
288
- | `--version REF` | 指定 Git ref、tag、branch 或发布版本 |
288
+ | `--plugin-version=REF` | 指定插件版本:npm 版本、npm dist-tag 或 Git ref |
289
289
  | `--current-version` | 查看 helper 记录的当前版本 |
290
290
  | `--base-url URL` | OpenViking 服务器地址(启用非交互模式) |
291
291
  | `--api-key KEY` | OpenViking API key |
292
292
  | `--agent-prefix PREFIX` | Agent 路由前缀 |
293
293
  | `--update` | 更新 helper 管理的安装 |
294
294
 
295
- 面向用户的安装,请先使用 `openclaw plugins install @openclaw/openviking`。只有作为备用路径时才选择 `ov-install`。
295
+ 面向用户的安装,请先使用 `openclaw plugins install clawhub:@openviking/openclaw-plugin`。只有作为备用路径时才选择 `ov-install`。
296
296
 
297
297
  ## 从 ov-install 迁移到 openclaw plugin install
298
298
 
@@ -307,7 +307,7 @@ ov-install 的 context-engine 部署会将文件写入 `~/.openclaw/extensions/o
307
307
  rm -rf ~/.openclaw/extensions/openviking/
308
308
 
309
309
  # 通过 OpenClaw 插件管理器安装
310
- openclaw plugins install @openclaw/openviking
310
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
311
311
 
312
312
  # 重新配置(openclaw.json 中的已有配置会保留)
313
313
  openclaw openviking setup --reconfigure
@@ -330,7 +330,7 @@ openclaw config set plugins.slots.memory none
330
330
  rm -rf ~/.openclaw/extensions/memory-openviking/
331
331
 
332
332
  # 安装新插件
333
- openclaw plugins install @openclaw/openviking
333
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
334
334
  openclaw openviking setup --base-url <OPENVIKING_URL> --api-key <API_KEY> --json
335
335
  openclaw gateway restart
336
336
  openclaw openviking status --json
package/INSTALL.md CHANGED
@@ -1,12 +1,12 @@
1
1
  # Install OpenViking for OpenClaw
2
2
 
3
- OpenViking provides long-term memory, knowledge base search, semantic retrieval, and RAG-style context for OpenClaw through the `@openclaw/openviking` plugin.
3
+ OpenViking provides long-term memory, knowledge base search, semantic retrieval, and RAG-style context for OpenClaw through the `@openviking/openclaw-plugin` plugin.
4
4
 
5
5
  This guide describes the current plugin install flow. It is written for both people and automation agents.
6
6
 
7
7
  ## Do Not Install The Skill By Mistake
8
8
 
9
- `@openclaw/openviking` is an OpenClaw plugin.
9
+ `@openviking/openclaw-plugin` is an OpenClaw plugin.
10
10
 
11
11
  Do not use this command for plugin installation:
12
12
 
@@ -19,7 +19,7 @@ That command installs an AgentSkill named `openviking`, not the OpenClaw plugin.
19
19
  Use this plugin command instead:
20
20
 
21
21
  ```bash
22
- openclaw plugins install @openclaw/openviking
22
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
23
23
  ```
24
24
 
25
25
  ## Requirements
@@ -36,7 +36,7 @@ OpenClaw plugin package boundaries:
36
36
  - `2026.4.8` is the minimum supported OpenClaw version for the current plugin.
37
37
  - `2026.5.3` starts validating package installs so TypeScript plugin entries need compiled JavaScript output.
38
38
  - `2026.5.4` and later stop falling back to `.ts` source for installed/global plugin runtime loading when compiled JavaScript is missing.
39
- - The recommended `openclaw plugins install @openclaw/openviking` path installs a published package that already includes `dist/*.js`.
39
+ - The recommended `openclaw plugins install clawhub:@openviking/openclaw-plugin` path installs a published package that already includes `dist/*.js`.
40
40
  - `ov-install` is the backup/source install path. Use it when ClawHub or the OpenClaw plugin manager path is unavailable/rate-limited, or when explicitly testing a source ref. For OpenClaw `>= 2026.5.3`, it builds the plugin during installation.
41
41
 
42
42
  Quick check:
@@ -87,13 +87,13 @@ Use this path for normal users, production installs, and agent-assisted installs
87
87
  ### 1. Install The Plugin
88
88
 
89
89
  ```bash
90
- openclaw plugins install @openclaw/openviking
90
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
91
91
  ```
92
92
 
93
93
  If your OpenClaw installation requires an explicit registry prefix, use:
94
94
 
95
95
  ```bash
96
- openclaw plugins install clawhub:@openclaw/openviking
96
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
97
97
  ```
98
98
 
99
99
  ### 2. Configure The Plugin
@@ -253,7 +253,7 @@ This checks the Gateway to OpenViking path by injecting a real conversation and
253
253
 
254
254
  ## Backup Path: ov-install
255
255
 
256
- `ov-install` is the backup path, not the primary install path. Use it when `openclaw plugins install @openclaw/openviking` cannot reach ClawHub, is rate-limited, or when you explicitly need to install/test plugin files from a Git branch or source ref.
256
+ `ov-install` is the backup path, not the primary install path. Use it when `openclaw plugins install clawhub:@openviking/openclaw-plugin` cannot reach ClawHub, is rate-limited, or when you explicitly need to install/test plugin files from a Git branch or source ref.
257
257
 
258
258
  Try the OpenClaw plugin manager first. If that path is unavailable, run:
259
259
 
@@ -267,14 +267,14 @@ Useful backup/source flags:
267
267
  | Flag | Meaning |
268
268
  | --- | --- |
269
269
  | `--workdir PATH` | Target OpenClaw state directory |
270
- | `--version REF` | Git ref, tag, branch, or release version to install |
270
+ | `--plugin-version=REF` | Plugin version: npm version, npm dist-tag, or Git ref to install |
271
271
  | `--current-version` | Print the version tracked by the helper |
272
272
  | `--base-url URL` | OpenViking server URL (enables non-interactive mode) |
273
273
  | `--api-key KEY` | OpenViking API key |
274
274
  | `--agent-prefix PREFIX` | Agent routing prefix |
275
275
  | `--update` | Update an existing helper-managed install |
276
276
 
277
- For user-facing installs, use `openclaw plugins install @openclaw/openviking` first. Choose `ov-install` only as the backup path.
277
+ For user-facing installs, use `openclaw plugins install clawhub:@openviking/openclaw-plugin` first. Choose `ov-install` only as the backup path.
278
278
 
279
279
  ## Migrate From ov-install To openclaw plugin install
280
280
 
@@ -289,7 +289,7 @@ The ov-install context-engine deployment writes files to `~/.openclaw/extensions
289
289
  rm -rf ~/.openclaw/extensions/openviking/
290
290
 
291
291
  # Install via the OpenClaw plugin manager
292
- openclaw plugins install @openclaw/openviking
292
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
293
293
 
294
294
  # Reconfigure (your existing config in openclaw.json is preserved)
295
295
  openclaw openviking setup --reconfigure
@@ -347,7 +347,7 @@ openclaw config set plugins.slots.memory none
347
347
  rm -rf ~/.openclaw/extensions/memory-openviking/
348
348
 
349
349
  # Install new plugin
350
- openclaw plugins install @openclaw/openviking
350
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
351
351
  openclaw openviking setup --base-url <OPENVIKING_URL> --api-key <API_KEY> --json
352
352
  openclaw gateway restart
353
353
  openclaw openviking status --json
package/README.md CHANGED
@@ -1,59 +1,78 @@
1
- # @openclaw/openviking — OpenViking OpenClaw Plugin
1
+ # OpenViking for OpenClaw
2
2
 
3
- OpenClaw context-engine plugin for OpenViking remote memory, context database, RAG and semantic retrieval.
3
+ Use [OpenViking](https://github.com/volcengine/OpenViking) as OpenClaw's long-term context engine: automatic recall, session archive, memory extraction, semantic search, and RAG over a remote OpenViking server.
4
4
 
5
- ## Important: Plugin vs Skill
5
+ ## Quick Start
6
6
 
7
- This page is for the **OpenClaw plugin package**:
8
-
9
- ```
10
- @openclaw/openviking
7
+ ```bash
8
+ openclaw plugins install clawhub:@openviking/openclaw-plugin
9
+ openclaw openviking setup --base-url http://my-server:1933 --api-key sk-xxx --json
10
+ openclaw gateway restart
11
+ openclaw openviking status --json
11
12
  ```
12
13
 
13
- **Do NOT** install the plugin with `clawhub install openviking` — that installs the `openviking` AgentSkill (under `skills/openviking`), which is a different thing.
14
+ That's it. The `setup` command activates the context-engine slot and validates the connection.
14
15
 
15
- For **agent-assisted plugin setup**, ask the agent to follow [INSTALL-AGENT.md](./INSTALL-AGENT.md). The primary install path is still `openclaw plugins install @openclaw/openviking`.
16
+ ### Or ask your agent
16
17
 
17
- ## Install (Natural Language)
18
+ > Install the OpenClaw plugin @openviking/openclaw-plugin for OpenViking remote memory. My server is at `http://my-server:1933` and my API key is `sk-xxx`.
18
19
 
19
- Ask your agent:
20
+ The agent runs install → setup → restart → verify automatically. See [INSTALL-AGENT.md](./INSTALL-AGENT.md).
20
21
 
21
- > Install the OpenClaw plugin @openclaw/openviking for OpenViking remote memory. My server is at `http://my-server:1933` and my API key is `sk-xxx`.
22
+ ## How It Works
22
23
 
23
- Or in Chinese:
24
+ | Stage | What happens |
25
+ |-------|-------------|
26
+ | **Every turn** (`afterTurn`) | Your messages are archived into an OpenViking session |
27
+ | **On `/compact`** (`compact`) | Archived messages are extracted into long-term memories |
28
+ | **Before each reply** (`assemble`) | Relevant memories are auto-retrieved and injected into context |
24
29
 
25
- > 帮我安装 OpenViking 远程记忆插件 @openclaw/openviking。我的服务器地址是 `http://my-server:1933`,API key 是 `sk-xxx`。
30
+ ## Tools
26
31
 
27
- The agent will automatically run install → setup → restart → verify. No manual steps needed.
32
+ Once installed, the plugin provides these agent tools:
28
33
 
29
- ## Install (Command Line)
34
+ | Tool | Purpose |
35
+ |------|---------|
36
+ | `memory_recall` | Explicit long-term memory search |
37
+ | `memory_store` | Persist important information immediately |
38
+ | `memory_forget` | Delete memories by URI or query |
39
+ | `ov_archive_search` | Search across archives by keyword |
40
+ | `ov_archive_expand` | Expand an archive back to raw messages |
41
+ | `add_resource` | Import documents, URLs, or Git repos |
42
+ | `add_skill` | Import agent skills |
43
+ | `memory_search` | Search imported resources and skills |
30
44
 
31
- ```bash
32
- openclaw plugins install @openclaw/openviking
33
- openclaw openviking setup --base-url http://my-server:1933 --api-key sk-xxx --json
34
- openclaw gateway restart
35
- openclaw openviking status --json
36
- ```
45
+ ## Data Flow & Privacy
37
46
 
38
- The `setup` command automatically activates the context-engine slot and validates the server connection.
47
+ - **What is sent**: User/assistant message text from each turn (after stripping injected memory blocks and metadata noise).
48
+ - **Where it goes**: Your configured OpenViking server (`baseUrl`). The plugin only sends data to that server; downstream model/provider data handling (embedding, VLM) depends on the server's configuration.
49
+ - **Storage**: All data lives on your OpenViking server under `viking://user/*`, `viking://agent/*`, and `viking://session/*`.
50
+ - **API Key**: Sent as `X-OpenViking-Key` header over your configured connection. Never logged or forwarded.
51
+ - **Multi-tenant isolation**: Supports `accountId`, `userId`, and `agent_prefix` for per-tenant scoping.
39
52
 
40
- ## Search Keywords
53
+ ## Verify
41
54
 
42
- @openclaw/openviking, openclaw openviking plugin, openviking remote memory plugin, OpenViking Context Database plugin, install-openviking-memory.
55
+ ```bash
56
+ openclaw openviking status --json # one-shot health check
57
+ openclaw config get plugins.slots.contextEngine # should output: openviking
58
+ ```
43
59
 
44
60
  ## Documentation
45
61
 
46
- - Install and upgrade: [INSTALL.md](./INSTALL.md)
47
- - Chinese design and install guide: [INSTALL-ZH.md](./INSTALL-ZH.md)
48
- - Agent-oriented operator guide: [INSTALL-AGENT.md](./INSTALL-AGENT.md)
62
+ | Doc | Description |
63
+ |-----|-------------|
64
+ | [INSTALL.md](./INSTALL.md) | Full install, upgrade, and uninstall guide |
65
+ | [INSTALL-ZH.md](./INSTALL-ZH.md) | Chinese install guide |
66
+ | [INSTALL-AGENT.md](./INSTALL-AGENT.md) | Agent-oriented operator guide |
49
67
 
50
- ---
68
+ > **Plugin vs Skill**: This page is for `@openviking/openclaw-plugin` (the context-engine plugin). Do **not** use `clawhub install openviking` — that installs a different AgentSkill.
51
69
 
52
- ## Technical Overview
70
+ ---
53
71
 
54
- Use [OpenViking](https://github.com/volcengine/OpenViking) as the long-term memory backend for [OpenClaw](https://github.com/openclaw/openclaw). In OpenClaw, this plugin is registered as the `openviking` context engine.
72
+ <details>
73
+ <summary><b>Technical Overview (for integrators and engineers)</b></summary>
55
74
 
56
- The remainder of this document is an implementation-focused design note for integrators and engineers.
75
+ This plugin is registered as the `openviking` context engine in OpenClaw.
57
76
 
58
77
  ## Design Positioning
59
78
 
@@ -315,3 +334,5 @@ ov tui
315
334
  ---
316
335
 
317
336
  For installation, upgrade, and uninstall operations, use [INSTALL.md](./INSTALL.md).
337
+
338
+ </details>
package/client.ts CHANGED
@@ -67,6 +67,24 @@ export type OVMessagePart = {
67
67
  tool_output?: string;
68
68
  tool_status?: string;
69
69
  skill_uri?: string;
70
+ duration_ms?: number;
71
+ prompt_tokens?: number;
72
+ completion_tokens?: number;
73
+ tool_output_ref?: string;
74
+ tool_output_truncated?: boolean;
75
+ tool_output_original_chars?: number;
76
+ tool_output_preview_chars?: number;
77
+ tool_output_sha256?: string;
78
+ tool_output_storage_uri?: string;
79
+ tool_output_mime_type?: string;
80
+ tool_output_source_ref?: string;
81
+ tool_output_source_offset?: number;
82
+ tool_output_source_limit?: number;
83
+ tool_output_externalization_error?: string;
84
+ tool_output_group_id?: string;
85
+ tool_output_externalized_reason?: string;
86
+ tool_output_group_original_chars?: number;
87
+ tool_output_group_budget_chars?: number;
70
88
  };
71
89
 
72
90
  export type OVMessage = {
@@ -96,6 +114,30 @@ export type SessionContextResult = {
96
114
  };
97
115
  };
98
116
 
117
+ export type ToolResultReadResult = {
118
+ tool_result_id: string;
119
+ content: string;
120
+ offset: number;
121
+ limit: number;
122
+ offset_unit: "unicode_code_point";
123
+ total_chars: number;
124
+ has_more: boolean;
125
+ metadata?: Record<string, unknown>;
126
+ };
127
+
128
+ export type ToolResultSearchResult = {
129
+ tool_result_id: string;
130
+ matches: Array<{
131
+ offset: number;
132
+ offset_unit: "unicode_code_point";
133
+ snippet: string;
134
+ }>;
135
+ };
136
+
137
+ export type ToolResultListResult = {
138
+ tool_results: Array<Record<string, unknown>>;
139
+ };
140
+
99
141
  export type SessionArchiveResult = {
100
142
  archive_id: string;
101
143
  abstract: string;
@@ -433,6 +475,61 @@ export class OpenVikingClient {
433
475
  );
434
476
  }
435
477
 
478
+ async readToolResult(
479
+ sessionId: string,
480
+ toolResultId: string,
481
+ options?: { offset?: number; limit?: number; includeMetadata?: boolean },
482
+ agentId?: string,
483
+ ): Promise<ToolResultReadResult> {
484
+ const params = new URLSearchParams();
485
+ if (options?.offset !== undefined) params.set("offset", String(options.offset));
486
+ if (options?.limit !== undefined) params.set("limit", String(options.limit));
487
+ if (options?.includeMetadata !== undefined) {
488
+ params.set("include_metadata", String(options.includeMetadata));
489
+ }
490
+ const query = params.toString();
491
+ return this.request<ToolResultReadResult>(
492
+ `/api/v1/sessions/${encodeURIComponent(sessionId)}/tool-results/${encodeURIComponent(toolResultId)}${query ? `?${query}` : ""}`,
493
+ {},
494
+ agentId,
495
+ );
496
+ }
497
+
498
+ async searchToolResult(
499
+ sessionId: string,
500
+ toolResultId: string,
501
+ queryText: string,
502
+ options?: { limit?: number; contextChars?: number },
503
+ agentId?: string,
504
+ ): Promise<ToolResultSearchResult> {
505
+ const params = new URLSearchParams({ q: queryText });
506
+ if (options?.limit !== undefined) params.set("limit", String(options.limit));
507
+ if (options?.contextChars !== undefined) {
508
+ params.set("context_chars", String(options.contextChars));
509
+ }
510
+ return this.request<ToolResultSearchResult>(
511
+ `/api/v1/sessions/${encodeURIComponent(sessionId)}/tool-results/${encodeURIComponent(toolResultId)}/search?${params.toString()}`,
512
+ {},
513
+ agentId,
514
+ );
515
+ }
516
+
517
+ async listToolResults(
518
+ sessionId: string,
519
+ options?: { toolName?: string; limit?: number },
520
+ agentId?: string,
521
+ ): Promise<ToolResultListResult> {
522
+ const params = new URLSearchParams();
523
+ if (options?.toolName) params.set("tool_name", options.toolName);
524
+ if (options?.limit !== undefined) params.set("limit", String(options.limit));
525
+ const query = params.toString();
526
+ return this.request<ToolResultListResult>(
527
+ `/api/v1/sessions/${encodeURIComponent(sessionId)}/tool-results${query ? `?${query}` : ""}`,
528
+ {},
529
+ agentId,
530
+ );
531
+ }
532
+
436
533
  async uploadTempFile(filePath: string, agentId?: string): Promise<string> {
437
534
  const fileBytes = await readFile(filePath);
438
535
  const form = new FormData();
@@ -614,6 +711,20 @@ export class OpenVikingClient {
614
711
  tool_status?: string;
615
712
  tool_input?: Record<string, unknown>;
616
713
  tool_id?: string;
714
+ tool_output_ref?: string;
715
+ tool_output_truncated?: boolean;
716
+ tool_output_original_chars?: number;
717
+ tool_output_preview_chars?: number;
718
+ tool_output_sha256?: string;
719
+ tool_output_storage_uri?: string;
720
+ tool_output_mime_type?: string;
721
+ tool_output_source_ref?: string;
722
+ tool_output_source_offset?: number;
723
+ tool_output_source_limit?: number;
724
+ tool_output_group_id?: string;
725
+ tool_output_externalized_reason?: string;
726
+ tool_output_group_original_chars?: number;
727
+ tool_output_group_budget_chars?: number;
617
728
  uri?: string;
618
729
  abstract?: string;
619
730
  context_type?: "memory" | "resource" | "skill";
package/context-engine.ts CHANGED
@@ -25,6 +25,8 @@ type AgentMessage = {
25
25
  timestamp?: unknown;
26
26
  };
27
27
 
28
+ type ExtractedTurnMessage = ReturnType<typeof extractNewTurnMessages>["messages"][number];
29
+
28
30
  type ContextEngineInfo = {
29
31
  id: string;
30
32
  name: string;
@@ -153,10 +155,6 @@ function allocateContextBudget(totalBudget: number, instructionTokens = 0): Cont
153
155
  return { archiveMemory, sessionContext, reserved };
154
156
  }
155
157
 
156
- function estimateTokens(messages: AgentMessage[]): number {
157
- return Math.max(1, messages.length * 80);
158
- }
159
-
160
158
  function roughEstimate(messages: AgentMessage[]): number {
161
159
  return Math.ceil(JSON.stringify(messages).length / 4);
162
160
  }
@@ -407,6 +405,10 @@ export function convertToAgentMessages(msg: { role: string; parts: unknown[] }):
407
405
  const toolName = typeof p.tool_name === "string" ? p.tool_name : undefined;
408
406
  const status = typeof p.tool_status === "string" ? p.tool_status : "unknown";
409
407
  const output = typeof p.tool_output === "string" ? p.tool_output : "";
408
+ const ref = typeof p.tool_output_ref === "string" ? p.tool_output_ref : "";
409
+ const originalChars = typeof p.tool_output_original_chars === "number"
410
+ ? p.tool_output_original_chars
411
+ : undefined;
410
412
 
411
413
  if (toolId) {
412
414
  // Structured path: emit canonical toolCall + toolResult pair (works for any role)
@@ -417,9 +419,15 @@ export function convertToAgentMessages(msg: { role: string; parts: unknown[] }):
417
419
  arguments: p.tool_input ?? {},
418
420
  });
419
421
 
420
- const resultText = (status === "completed" || status === "error")
422
+ let resultText = (status === "completed" || status === "error")
421
423
  ? (output || "(no output)")
422
424
  : "(interrupted — tool did not complete)";
425
+ if (ref && !resultText.includes(ref)) {
426
+ const suffix = originalChars !== undefined
427
+ ? `\n[tool-result-ref] ${ref} original_chars=${originalChars}`
428
+ : `\n[tool-result-ref] ${ref}`;
429
+ resultText += suffix;
430
+ }
423
431
  const resultPayload: Record<string, unknown> = {
424
432
  role: "toolResult",
425
433
  toolCallId: toolId,
@@ -474,6 +482,36 @@ export function convertToAgentMessages(msg: { role: string; parts: unknown[] }):
474
482
  return result;
475
483
  }
476
484
 
485
+ function isToolOnlyMessage(msg: ExtractedTurnMessage): boolean {
486
+ return msg.role === "user" && msg.parts.length > 0 && msg.parts.every((part) => part.type === "tool");
487
+ }
488
+
489
+ function coalesceConsecutiveToolMessages(messages: ExtractedTurnMessage[]): ExtractedTurnMessage[] {
490
+ const result: ExtractedTurnMessage[] = [];
491
+ let pendingTools: ExtractedTurnMessage | undefined;
492
+
493
+ const flush = () => {
494
+ if (pendingTools) {
495
+ result.push(pendingTools);
496
+ pendingTools = undefined;
497
+ }
498
+ };
499
+
500
+ for (const msg of messages) {
501
+ if (isToolOnlyMessage(msg)) {
502
+ if (!pendingTools) {
503
+ pendingTools = { role: "user", parts: [] };
504
+ }
505
+ pendingTools.parts.push(...msg.parts);
506
+ continue;
507
+ }
508
+ flush();
509
+ result.push(msg);
510
+ }
511
+ flush();
512
+ return result;
513
+ }
514
+
477
515
  function normalizeAssistantContent(messages: AgentMessage[]): void {
478
516
  for (let i = 0; i < messages.length; i++) {
479
517
  const msg = messages[i];
@@ -1279,7 +1317,8 @@ export function createMemoryOpenVikingContextEngine(params: {
1279
1317
  ? afterTurnParams.prePromptMessageCount
1280
1318
  : 0;
1281
1319
 
1282
- const { messages: extractedMessages, newCount } = extractNewTurnMessages(messages, start);
1320
+ const { messages: extractedMessagesRaw, newCount } = extractNewTurnMessages(messages, start);
1321
+ const extractedMessages = coalesceConsecutiveToolMessages(extractedMessagesRaw);
1283
1322
 
1284
1323
  if (extractedMessages.length === 0) {
1285
1324
  diag("afterTurn_skip", OVSessionId, {
@@ -1387,15 +1426,13 @@ export function createMemoryOpenVikingContextEngine(params: {
1387
1426
  `openviking: Phase2 memory extraction runs asynchronously on the server (task_id=${commitResult.task_id}). ` +
1388
1427
  "memories_extracted appears only after that task completes — not in this immediate response.",
1389
1428
  );
1390
- if (cfg.logFindRequests) {
1391
- void pollPhase2ExtractionOutcome(
1392
- getClient,
1393
- commitResult.task_id,
1394
- agentId,
1395
- logger,
1396
- OVSessionId,
1397
- );
1398
- }
1429
+ void pollPhase2ExtractionOutcome(
1430
+ getClient,
1431
+ commitResult.task_id,
1432
+ agentId,
1433
+ logger,
1434
+ OVSessionId,
1435
+ );
1399
1436
  }
1400
1437
  } catch (err) {
1401
1438
  logger.warn?.(`openviking: afterTurn failed: ${String(err)}`);