@kin-tio/cli 0.6.2 → 0.7.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/.env.example CHANGED
@@ -28,8 +28,10 @@ WECOM_AUTH_CONFIRMATION=Code accepted. You can continue the conversation.
28
28
  # WECOM_MCP_OBSERVE_MS=5000
29
29
  # SHUTDOWN_TIMEOUT_MS=10000
30
30
 
31
- # Optional Weixin iLink channel. Generate a 32-byte base64url key and keep it in
32
- # the deployment secret store; Bot and context tokens are encrypted with it.
31
+ # Enable Weixin iLink inside the combined `kintio start` runtime. Standalone
32
+ # `kintio ilink login` and `kintio ilink start` do not require this flag.
33
+ # Generate a 32-byte base64url key and keep it in the deployment secret store;
34
+ # Bot and context tokens are encrypted with it.
33
35
  ILINK_ENABLED=false
34
36
  # Prefer a deployment-secret value. If omitted, the service creates a private
35
37
  # 0600 key file beside SQLite; never register that key with a chat Agent.
package/CHANGELOG.md CHANGED
@@ -4,6 +4,40 @@ This file records important user-visible changes after the first public release.
4
4
 
5
5
  ## Unreleased
6
6
 
7
+ ## 0.7.1
8
+
9
+ - Made `kintio ilink start` use the managed background daemon by default while
10
+ retaining `--foreground` for external service managers, simplified
11
+ `kintio ilink list` to reusable provider account IDs, rejected Node.js below
12
+ 24 before application startup, and added sanitized Codex request diagnostics
13
+ ([#65](https://github.com/Gkxie/kintio/issues/65)).
14
+
15
+ ## 0.7.0
16
+
17
+ - Added `kintio ilink login`, which reuses the iLink enrollment state machine
18
+ while rendering its five-minute QR code directly in an interactive terminal;
19
+ no WeChat KF conversation or Agent turn is required. Accounts
20
+ enrolled locally receive host-level Agent access and inherit the host runtime
21
+ configuration, while remotely offered iLink accounts remain restricted
22
+ ([#54](https://github.com/Gkxie/kintio/issues/54)).
23
+ - Added an explicit `--qr-output <file>` view for `kintio ilink login`, allowing
24
+ graphical and non-terminal callers to consume a temporary raw PNG directly
25
+ from the QR payload without parsing ANSI terminal output. The file is created
26
+ exclusively and removed when the login attempt ends
27
+ ([#57](https://github.com/Gkxie/kintio/issues/57)).
28
+ - Made iLink a standalone lifecycle: `kintio ilink login` now initializes and
29
+ persists an account without setup, an environment file, Hono, or a running
30
+ Worker, while safely delegating to a running instance when present;
31
+ `kintio ilink start` starts polling and the host Agent in the foreground without
32
+ a public HTTP listener. The iLink Runtime configuration no longer contains a
33
+ synthetic WeChat KF adapter
34
+ ([#59](https://github.com/Gkxie/kintio/issues/59)).
35
+ - Added per-account `kintio ilink list`, `start`, `stop`, and confirmed `delete`
36
+ lifecycle commands. One Runtime can reconcile multiple selected listeners;
37
+ complete deletion atomically purges the selected account and all Kintio data
38
+ scoped to it while preserving unrelated accounts and channels
39
+ ([#60](https://github.com/Gkxie/kintio/issues/60)).
40
+
7
41
  ## 0.6.2
8
42
 
9
43
  - Added a custom Kintio wordmark and its circular-safe TIO avatar to the English
package/README.md CHANGED
@@ -67,33 +67,68 @@ Prerequisites:
67
67
 
68
68
  ```bash
69
69
  npm install --global @kin-tio/cli
70
- kintio setup
71
70
  codex login status
72
71
  ```
73
72
 
74
- `kintio setup` creates a private instance under `~/.kintio`, installs the bundled Agent
75
- skill, and writes the channel configuration template. POSIX systems use mode `0600`;
76
- Windows keeps the instance inside the current user's profile. No adapter is enabled
77
- by default. Follow the [setup guide](https://github.com/Gkxie/kintio/blob/master/docs/setup.md)
78
- and edit `~/.kintio/.env` to configure one adapter:
73
+ For an iLink-only instance, no setup file or public HTTP listener is required:
79
74
 
80
- - For WeChat KF API, set its callback token, EncodingAESKey, CorpID, and secret. A temporary
81
- `WECOM_AUTH_TRIGGER` can authorize the first user without knowing their
82
- `external_userid` in advance.
83
- - For an existing Weixin iLink binding, set `ILINK_ENABLED=true`. Creating a new binding
84
- currently starts from an authorized WeChat KF conversation.
75
+ ```bash
76
+ kintio ilink login
77
+ kintio ilink start
78
+ ```
85
79
 
86
- Start Kintio:
80
+ `ilink login` performs one encrypted enrollment, starts no listener, and exits. `ilink start` then runs provider
81
+ polling and the host Agent through the background daemon without Hono or a TCP listener.
82
+ Use `--foreground` only when a service manager needs to own the process. Both commands
83
+ use `~/.kintio` by default and accept `--home`. With multiple accounts, use `ilink list`
84
+ and pass the displayed provider ID or account key through `--account`. Repeated `start`
85
+ commands add accounts to the live runtime; `stop` removes one.
86
+
87
+ For a callback-based adapter, create and edit the deployment configuration instead:
87
88
 
88
89
  ```bash
90
+ kintio setup
89
91
  kintio start
90
92
  kintio status
91
93
  kintio logs --lines 100
92
94
  ```
93
95
 
94
- After startup, confirm that `kintio logs` contains `Hono server is listening on port 8888`.
95
- Complete the callback or binding checks described in the setup guide before sending traffic.
96
- Use `kintio run` when a foreground process is preferable to the native daemon.
96
+ `kintio setup` creates a private instance under `~/.kintio`, installs the managed Agent
97
+ skill, and writes the channel configuration template. Follow the
98
+ [setup guide](https://github.com/Gkxie/kintio/blob/master/docs/setup.md):
99
+
100
+ - For WeChat KF API, set its callback token, EncodingAESKey, CorpID, and secret. A temporary
101
+ `WECOM_AUTH_TRIGGER` can authorize the first user without knowing their
102
+ `external_userid` in advance.
103
+ - A combined callback + iLink deployment may additionally set `ILINK_ENABLED=true`.
104
+
105
+ For a graphical or non-terminal caller, select a temporary raw PNG instead of ANSI blocks:
106
+
107
+ ```bash
108
+ kintio ilink login --qr-output ~/.kintio/ilink-login.png
109
+ ```
110
+
111
+ The target must be directly inside the selected Kintio instance directory and must not
112
+ already exist. Kintio removes the PNG when login succeeds, expires, is cancelled, or fails;
113
+ the QR payload is never printed. Without `--qr-output`, the command
114
+ requires an interactive terminal. Both forms stop waiting after five minutes and never
115
+ start an Agent turn. The resulting iLink identity represents
116
+ the local operator and inherits the host Agent configuration without Kintio's untrusted-
117
+ channel capability restrictions. Show this QR code only to someone authorized to control
118
+ the host Agent. Run `kintio ilink start` after enrollment to process messages without Hono.
119
+
120
+ To permanently remove an account and every Kintio record scoped to it, use:
121
+
122
+ ```bash
123
+ kintio ilink delete --account <provider-id-or-account-key> --yes
124
+ ```
125
+
126
+ The explicit confirmation is mandatory. Credentials, conversations, messages, media,
127
+ delivery records, and enrollment audit rows for that account are deleted atomically.
128
+
129
+ For callback deployments, confirm that `kintio logs` contains
130
+ `Hono server is listening on port 8888`. Use `kintio run` when a foreground process is
131
+ preferable to the native daemon.
97
132
  Existing source-based deployments can keep their current state after the one-time
98
133
  process-manager migration described in the setup guide.
99
134
 
@@ -111,6 +146,9 @@ Source builds and contributor setup are documented in
111
146
  Hono route; every action still requires a short-lived conversation capability.
112
147
  - Project-level Agent capability restrictions are not an operating-system sandbox. Use a
113
148
  dedicated system account and additional isolation appropriate to the Agent's real powers.
149
+ - An iLink account enrolled by `kintio ilink login` is explicitly host-authorized; its owner
150
+ receives the capabilities allowed by the host Agent configuration. Accounts enrolled from
151
+ a remote adapter remain restricted, and chat input cannot change this persisted trust level.
114
152
  - A provider accepting an outbound request does not prove that a client displayed it;
115
153
  uncertain outcomes remain explicit to avoid duplicate delivery.
116
154
 
package/README.zh-CN.md CHANGED
@@ -43,25 +43,50 @@
43
43
 
44
44
  ```bash
45
45
  npm install --global @kin-tio/cli
46
- kintio setup
47
46
  codex login status
48
47
  ```
49
48
 
50
- `kintio setup` 会在 `~/.kintio` 创建私有实例目录、安装内置 Agent Skill,并生成渠道配置
51
- 模板 `.env`。macOS/Linux 使用 `0600`,Windows 则限定在当前用户目录的 ACL
52
- 边界内。默认不启用任何适配器;请按英文
53
- [部署指南](https://github.com/Gkxie/kintio/blob/master/docs/setup.md)配置 WeChat KF API,或为已有 Weixin iLink 绑定设置
54
- `ILINK_ENABLED=true`。
49
+ iLink 可以完全独立使用,不需要 `setup`、`.env` 或公网 HTTP:
55
50
 
56
51
  ```bash
52
+ kintio ilink login
53
+ kintio ilink start
54
+ ```
55
+
56
+ `ilink login` 完成一次扫码、加密保存凭据后退出,不会自行启动监听;`ilink start` 不启动 Hono 或 TCP 端口,
57
+ 而是通过后台守护进程运行 iLink 长轮询和宿主 Agent。由外部进程管理器托管时可显式使用
58
+ `--foreground`。两者默认使用 `~/.kintio`。
59
+ 存在多个账号时,先用 `kintio ilink list` 查看账号,再通过 `--account` 指定
60
+ `start`、`stop` 或 `delete` 的目标;正在运行时可继续执行 `start` 增加监听账号。
61
+
62
+ 需要部署公网回调渠道时,再使用:
63
+
64
+ ```bash
65
+ kintio setup
57
66
  kintio start
58
67
  kintio status
59
68
  kintio logs --lines 100
60
69
  ```
61
70
 
62
- 启动后应确认 `kintio logs` 包含 `Hono server is listening on port 8888`;投入使用前仍需按
63
- 部署指南完成回调或绑定验证。需要前台进程时使用 `kintio run`;现有源码目录部署可以在完成
64
- 部署指南中的一次性进程管理器迁移后,继续使用原数据库和配置。
71
+ 具体配置见英文[部署指南](https://github.com/Gkxie/kintio/blob/master/docs/setup.md)。
72
+
73
+ 图形界面或非交互调用方可以显式选择临时的原始 PNG,而不是解析终端字符:
74
+
75
+ ```bash
76
+ kintio ilink login --qr-output ~/.kintio/ilink-login.png
77
+ ```
78
+
79
+ 目标文件必须直接位于所选 Kintio 实例目录中且不能预先存在;登录成功、过期、取消或失败后,Kintio 会自动删除该文件,并且
80
+ 不会打印二维码原始内容。二维码五分钟后过期;该命令不会唤醒 Agent。通过本机命令建立的 iLink 身份代表宿主机
81
+ 所有者的明确授权,后续对话直接继承宿主 Agent 配置,不再套用不可信渠道的能力限制。
82
+ 只应让获准控制宿主 Agent 的人扫描该二维码。登录后运行 `kintio ilink start` 即可在不
83
+ 启动 Hono 的情况下处理消息。
84
+
85
+ `kintio ilink delete --account <账号> --yes` 会不可恢复地删除该账号及其在 Kintio
86
+ 中的凭据、会话、消息、媒体、发送记录和登录审计;`--yes` 为强制确认参数。
87
+
88
+ 公网回调部署启动后,应确认 `kintio logs` 包含
89
+ `Hono server is listening on port 8888`。
65
90
  源码构建与贡献者开发环境见英文
66
91
  [贡献指南](https://github.com/Gkxie/kintio/blob/master/CONTRIBUTING.md)。
67
92
 
package/bin/kintio.js CHANGED
@@ -1,3 +1,13 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- await import('../dist/cli.js');
3
+ const currentNode = process.versions.node;
4
+ const nodeMajor = Number.parseInt(currentNode.split('.')[0] || '', 10);
5
+ if (!Number.isSafeInteger(nodeMajor) || nodeMajor < 24) {
6
+ process.stderr.write(
7
+ `Kintio requires Node.js 24 or newer; current runtime is v${currentNode}.\n` +
8
+ 'Install Node.js 24+, then reinstall @kin-tio/cli in that Node environment.\n',
9
+ );
10
+ process.exitCode = 1;
11
+ } else {
12
+ await import('../dist/cli.js');
13
+ }
package/dist/daemon.js CHANGED
@@ -4,13 +4,18 @@ import { resolveProjectRoot } from './src/config.js';
4
4
  import { runNativeDaemon } from './src/runtime/native-daemon.js';
5
5
  const home = process.env.KINTIO_HOME;
6
6
  const configFile = process.env.KINTIO_CONFIG_FILE;
7
+ const mode = process.env.KINTIO_DAEMON_MODE || 'service';
7
8
  if (!home || !configFile) {
8
9
  throw new Error('KINTIO_HOME and KINTIO_CONFIG_FILE are required for daemon mode');
9
10
  }
11
+ if (mode !== 'service' && mode !== 'ilink') {
12
+ throw new Error(`Unsupported Kintio daemon mode: ${mode}`);
13
+ }
10
14
  try {
11
15
  await runNativeDaemon({
12
16
  home: path.resolve(home),
13
17
  configFile: path.resolve(configFile),
18
+ mode,
14
19
  packageRoot: resolveProjectRoot(import.meta.url),
15
20
  });
16
21
  }
package/dist/ilink.js ADDED
@@ -0,0 +1,53 @@
1
+ import { KINTIO_PACKAGE_ROOT, loadIlinkRuntimeConfig, } from './src/config.js';
2
+ import { startIlinkCliRuntime } from './src/ilink/cli-start.js';
3
+ import { installManagedSkill } from './src/runtime/managed-skill.js';
4
+ const config = loadIlinkRuntimeConfig();
5
+ installManagedSkill({
6
+ packageRoot: KINTIO_PACKAGE_ROOT,
7
+ workingDirectory: config.codex.workingDirectory,
8
+ });
9
+ const controller = new AbortController();
10
+ let resolveParentShutdown;
11
+ const parentShutdown = new Promise((resolve) => { resolveParentShutdown = resolve; });
12
+ const shutdown = () => {
13
+ controller.abort();
14
+ resolveParentShutdown();
15
+ };
16
+ process.once('SIGINT', shutdown);
17
+ process.once('SIGTERM', shutdown);
18
+ const handleMessage = (message) => {
19
+ if (message === 'shutdown')
20
+ shutdown();
21
+ };
22
+ process.on('message', handleMessage);
23
+ process.once('disconnect', shutdown);
24
+ if (process.env.KINTIO_MANAGED_WORKER === '1' && !process.connected)
25
+ shutdown();
26
+ try {
27
+ const result = await startIlinkCliRuntime({
28
+ background: true,
29
+ config,
30
+ signal: controller.signal,
31
+ stdout: (text) => process.stdout.write(text),
32
+ onStarted() {
33
+ process.send?.({ type: 'ready', pid: process.pid });
34
+ },
35
+ });
36
+ if (result === 0 && process.connected) {
37
+ process.send?.({ type: 'shutdown-request', pid: process.pid });
38
+ await parentShutdown;
39
+ }
40
+ process.exitCode = result === 130 ? 0 : result;
41
+ }
42
+ catch (error) {
43
+ console.error('[ilink] process failed', error);
44
+ process.exitCode = 1;
45
+ }
46
+ finally {
47
+ process.off('SIGINT', shutdown);
48
+ process.off('SIGTERM', shutdown);
49
+ process.off('disconnect', shutdown);
50
+ process.off('message', handleMessage);
51
+ if (process.connected)
52
+ process.disconnect();
53
+ }