mio-agent-runtime 0.3.0 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,73 +1,79 @@
1
- # mio-agent-runtime
2
-
3
- Mio Agent Runtime 的可发布 CLI 包。
4
-
5
- 安装一次,所有 Agent 自动接入 Mio。
6
-
7
- ## Install
8
-
9
- ```bash
10
- npm install -g mio-agent-runtime
11
- ```
12
-
13
- ## Commands
14
-
15
- ```text
16
- mio init Initialize MIO_HOME
17
- mio mcp Start Mio MCP server (stdio)
18
- mio install <host> Install Mio into a host (codex|opencode|workbuddy)
19
- mio status Show runtime and adapter status
20
- mio agents List installed agents
21
- mio observe Watch WorkBuddy transcripts and auto-ingest task outcomes (foreground)
22
- mio observe --start|--stop|--status|--once Manage the background observer daemon
23
- mio --json status Machine-readable status
24
- mio --json agents Machine-readable agents
25
- ```
26
-
27
- ## Host notes
28
-
29
- - OpenCode uses `~/.config/opencode/opencode.json` for MCP registration and
30
- `~/.config/opencode/AGENTS.md` for global instructions. `mio install opencode`
31
- writes both files and injects Mio usage rules into `AGENTS.md` so OpenCode
32
- calls Mio memory/observer/policy automatically. If OpenCode is already
33
- running, restart it once so it reloads both files.
34
- - WorkBuddy uses `~/.workbuddy/mcp.json` and requires each custom MCP server to
35
- be approved in `~/.workbuddy/mcp-approvals.json`. `mio install workbuddy`
36
- writes both files and injects Mio usage rules into
37
- `~/.workbuddy/CODEBUDDY.md` (user-level memory rules, auto-loaded by
38
- WorkBuddy into every session; the CLI hardcodes the CodeBuddy product name, so the file is CODEBUDDY.md not WORKBUDDY.md) plus `<workspace>/AGENTS.md` (project-level).
39
- If WorkBuddy is already running, restart it once so it reloads the approval
40
- and memory rule files.
41
-
42
- ## Passive observer (`mio observe`)
43
-
44
- WorkBuddy 的默认模型不一定会主动调用 Mio MCP 工具,即使规则已注入
45
- (`CODEBUDDY.md` / `AGENTS.md`)。`mio observe` 是一个不依赖模型自觉的
46
- 兜底:它持续监听 `~/.workbuddy/projects/**/*.jsonl` 会话记录,把每个任务的
47
- 结果(`task_outcome`)、工具调用错误(`error`)以及完成任务的摘要自动写入
48
- `MIO_HOME/traces.jsonl` 和 `MIO_HOME/memory.jsonl`(与 MCP 服务同一套
49
- schema,`source=workbuddy-observer`)。
50
-
51
- - `mio install <host>` 会自动执行一次回填并启动后台观察器。
52
- - 已处理的文件偏移记录在 `MIO_HOME/observe-state.json`,不会重复写入。
53
- - 只回填最近 24h 内更新的会话,避免把历史记录灌入记忆库。
54
-
55
- ## MIO_HOME
56
-
57
- 默认 `~/.mio-intelligence`,可通过环境变量 `MIO_HOME` 覆盖。
58
-
59
- ## Package layout
60
-
61
- ```text
62
- packages/mio-cli
63
- ├── bin/mio.js
64
- ├── adapters/
65
- │ ├── codex.js
66
- │ ├── opencode.js
67
- │ └── workbuddy.js
68
- ├── observe/
69
- │ └── observer.js
70
- ├── server/
71
- │ └── mio-intelligence-mcp/index.js
72
- └── package.json
1
+ # mio-agent-runtime
2
+
3
+ Mio Agent Runtime 的可发布 CLI 包。
4
+
5
+ 安装一次,所有 Agent 自动接入 Mio。
6
+
7
+ ## Install
8
+
9
+ ```bash
10
+ npm install -g mio-agent-runtime
11
+ ```
12
+
13
+ ## Commands
14
+
15
+ ```text
16
+ mio init Initialize MIO_HOME
17
+ mio mcp Start Mio MCP server (stdio)
18
+ mio install <host> Install Mio into a host (codex|opencode|workbuddy)
19
+ mio status Show runtime and adapter status
20
+ mio agents List installed agents
21
+ mio observe Watch WorkBuddy transcripts and auto-ingest task outcomes (foreground)
22
+ mio observe --start|--stop|--status|--once Manage the background observer daemon
23
+ mio --json status Machine-readable status
24
+ mio --json agents Machine-readable agents
25
+ ```
26
+
27
+ ## Host notes
28
+
29
+ - OpenCode uses `~/.config/opencode/opencode.json` for MCP registration and
30
+ `~/.config/opencode/AGENTS.md` for global instructions. `mio install opencode`
31
+ writes both files and injects Mio usage rules into `AGENTS.md` so OpenCode
32
+ calls Mio memory/observer/policy automatically. If OpenCode is already
33
+ running, restart it once so it reloads both files.
34
+ - WorkBuddy uses `~/.workbuddy/mcp.json` and requires each custom MCP server to
35
+ be approved in `~/.workbuddy/mcp-approvals.json`. `mio install workbuddy`
36
+ writes both files and injects Mio usage rules into
37
+ `~/.workbuddy/CODEBUDDY.md` (user-level memory rules, auto-loaded by
38
+ WorkBuddy into every session; the CLI hardcodes the CodeBuddy product name, so the file is CODEBUDDY.md not WORKBUDDY.md) plus `<workspace>/AGENTS.md` (project-level).
39
+ If WorkBuddy is already running, restart it once so it reloads the approval
40
+ and memory rule files.
41
+
42
+ ## Passive observer (`mio observe`)
43
+
44
+ WorkBuddy 的默认模型不一定会主动调用 Mio MCP 工具,即使规则已注入
45
+ (`CODEBUDDY.md` / `AGENTS.md`)。`mio observe` 是一个不依赖模型自觉的
46
+ 兜底:它持续监听 `~/.workbuddy/projects/**/*.jsonl` 会话记录,把每个任务的
47
+ 结果(`task_outcome`)、工具调用错误(`error`)以及完成任务的摘要自动写入
48
+ `MIO_HOME/traces.jsonl` 和 `MIO_HOME/memory.jsonl`(与 MCP 服务同一套
49
+ schema,`source=workbuddy-observer`)。
50
+
51
+ - `mio install <host>` 会自动执行一次回填并启动后台观察器。
52
+
53
+ - 除了写入 `MIO_HOME`,观察器还会把任务摘要**写回 WorkBuddy 自己的记忆文件**
54
+ (`<workspace>/.workbuddy/memory/YYYY-MM-DD.md`,标为 `## Mio 自动摘要`)。
55
+ WorkBuddy 的系统提示要求模型每次会话维护并阅读这些文件,所以下一次会话
56
+ WorkBuddy 会**被动取到** Mio 记录的内容——单 Agent 的「存 + 取」闭环不依赖
57
+ 模型调用 Mio 工具。
58
+ - 已处理的文件偏移记录在 `MIO_HOME/observe-state.json`,不会重复写入。
59
+ - 只回填最近 24h 内更新的会话,避免把历史记录灌入记忆库。
60
+
61
+ ## MIO_HOME
62
+
63
+ 默认 `~/.mio-intelligence`,可通过环境变量 `MIO_HOME` 覆盖。
64
+
65
+ ## Package layout
66
+
67
+ ```text
68
+ packages/mio-cli
69
+ ├── bin/mio.js
70
+ ├── adapters/
71
+ │ ├── codex.js
72
+ │ ├── opencode.js
73
+ │ └── workbuddy.js
74
+ ├── observe/
75
+ │ └── observer.js
76
+ ├── server/
77
+ │ └── mio-intelligence-mcp/index.js
78
+ └── package.json
73
79
  ```
@@ -178,6 +178,7 @@ function createTurn(meta) {
178
178
  ts: null,
179
179
  project: meta.project,
180
180
  sessionId: meta.sessionId,
181
+ cwd: meta.cwd || null,
181
182
  toolCount: 0,
182
183
  errors: [],
183
184
  lastAssistant: null,
@@ -187,12 +188,14 @@ function createTurn(meta) {
187
188
  function feedWorkbuddyLine(turn, obj) {
188
189
  if (!obj || typeof obj !== 'object') return { finalized: null, next: turn }
189
190
  let finalized = null
191
+ if (obj.cwd) turn.cwd = obj.cwd
190
192
  if (obj.type === 'message') {
191
193
  if (obj.role === 'user') {
192
194
  finalized = turn
193
195
  const next = createTurn(turn)
194
196
  next.id = obj.id
195
197
  next.ts = obj.timestamp
198
+ next.cwd = obj.cwd || turn.cwd
196
199
  return { finalized, next: next }
197
200
  }
198
201
  if (obj.role === 'assistant') {
@@ -218,9 +221,35 @@ function feedWorkbuddyLine(turn, obj) {
218
221
  return { finalized: finalized, next: turn }
219
222
  }
220
223
 
224
+ function localDateKey(ts) {
225
+ const d = new Date(Number(ts) || Date.now())
226
+ const y = d.getFullYear()
227
+ const m = String(d.getMonth() + 1).padStart(2, '0')
228
+ const day = String(d.getDate()).padStart(2, '0')
229
+ return y + '-' + m + '-' + day
230
+ }
231
+
232
+ // Write a compact Mio digest back into WorkBuddy's own memory file
233
+ // (<workspace>/.workbuddy/memory/YYYY-MM-DD.md). WorkBuddy instructs its model
234
+ // to maintain and read these files every session, so the digest is
235
+ // 'retrieved' next session without any Mio tool call by the model.
236
+ function writeWorkbuddyDigest(turn, outcome, summary) {
237
+ if (!turn.cwd || !summary) return
238
+ const dir = path.join(turn.cwd, '.workbuddy', 'memory')
239
+ const file = path.join(dir, localDateKey(turn.ts) + '.md')
240
+ try {
241
+ fs.mkdirSync(dir, { recursive: true })
242
+ const time = new Date(Number(turn.ts) || Date.now()).toLocaleString('zh-CN', { hour12: false })
243
+ const entry =
244
+ '\n## Mio 自动摘要 (' + time + ')\n' +
245
+ '- outcome: ' + outcome + ' | tools: ' + turn.toolCount + ' | ' + summary.slice(0, 160) + '\n'
246
+ fs.appendFileSync(file, entry, 'utf8')
247
+ } catch (_) {}
248
+ }
249
+
221
250
  function emitWorkbuddyOutcome(turn, sinks) {
222
251
  const la = turn.lastAssistant
223
- if (!la) return
252
+ if (!la) return false
224
253
  let outcome
225
254
  if (la.status === 'completed') outcome = 'success'
226
255
  else if (la.error) outcome = 'failure'
@@ -256,6 +285,7 @@ function emitWorkbuddyOutcome(turn, sinks) {
256
285
  project: turn.project,
257
286
  source: 'workbuddy-observer',
258
287
  })
288
+ writeWorkbuddyDigest(turn, outcome, summary)
259
289
  }
260
290
 
261
291
  for (const err of turn.errors) {
@@ -276,6 +306,7 @@ function emitWorkbuddyOutcome(turn, sinks) {
276
306
  project: turn.project,
277
307
  })
278
308
  }
309
+ return true
279
310
  }
280
311
 
281
312
  // ---------------------------------------------------------------------------
@@ -338,8 +369,7 @@ function runCycle(home, state, sinks, opts) {
338
369
  }
339
370
  const result = feedWorkbuddyLine(turn, obj)
340
371
  if (result.finalized) {
341
- emitWorkbuddyOutcome(result.finalized, sinks)
342
- out.outcomes += 1
372
+ if (emitWorkbuddyOutcome(result.finalized, sinks)) out.outcomes += 1
343
373
  }
344
374
  turn = result.next
345
375
  }
@@ -347,8 +377,7 @@ function runCycle(home, state, sinks, opts) {
347
377
  }
348
378
 
349
379
  if (turn.lastAssistant && now - st.mtimeMs > IDLE_MS) {
350
- emitWorkbuddyOutcome(turn, sinks)
351
- out.outcomes += 1
380
+ if (emitWorkbuddyOutcome(turn, sinks)) out.outcomes += 1
352
381
  state.openTurns[file] = null
353
382
  } else if (turn.id) {
354
383
  state.openTurns[file] = turn
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mio-agent-runtime",
3
- "version": "0.3.0",
3
+ "version": "0.3.1",
4
4
  "description": "Mio Agent Runtime installer and MCP intelligence layer",
5
5
  "license": "MIT",
6
6
  "type": "commonjs",