aiterm-mcp 0.27.8 → 0.27.9
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.ja.md +6 -6
- package/README.md +1 -1
- package/dist/core.js +4 -3
- package/dist/index.js +2 -1
- package/dist/tmux-runtime.js +12 -0
- package/package.json +1 -1
package/README.ja.md
CHANGED
|
@@ -151,7 +151,7 @@ runtime-error store は canonical dotagents config の `collection.enabled: true
|
|
|
151
151
|
場合だけ収集し、既定OFF、network送信は行いません。tag起点CIのnpm provenance(OIDC Trusted
|
|
152
152
|
Publishing)で公開し、GitHub Release が Official MCP Registry を再登録します。
|
|
153
153
|
|
|
154
|
-
**状態:** 開発継続中 · この分野では新参で、別の形に賭けている([既存手段との比較](#既存手段との比較)参照)· 動作対象は Linux · WSL2 · macOS · Windows ネイティブ(
|
|
154
|
+
**状態:** 開発継続中 · この分野では新参で、別の形に賭けている([既存手段との比較](#既存手段との比較)参照)· 動作対象は Linux · WSL2 · macOS · Windows ネイティブ(4 launcher と相関付き完了を含む)· MIT · [変更履歴](CHANGELOG.md)。
|
|
155
155
|
|
|
156
156
|
## なぜ今
|
|
157
157
|
|
|
@@ -430,7 +430,7 @@ handoff contextを前置きできる。この任意経路は`throughline >= 0.9.
|
|
|
430
430
|
|
|
431
431
|
### 完了検出(5 層)
|
|
432
432
|
|
|
433
|
-
`pty_read({ wait: true })`は通常PTY
|
|
433
|
+
`pty_read({ wait: true })`は通常PTYを、process終了/`mark:true` sentinel/`until`一致/shell復帰を伴う出力静止/timeoutの5層で判定する。`mark`はPOSIX shellでは終了コード、PowerShellでは成功`0`/失敗`1`を出力する。fish/csh/tcshはどちらの状態取得構文にも従わないため送信前に拒否する。agent sessionは第6の正確な層を使う。Codexは通常rolloutの`task_complete`、Grok/Composerは通常sessionの`turn_ended`、Claudeは通常settingsへ加算したlaunch相関Stop eventを`aiterm-wait --cursor`が観測する。親はブロックもポーリングもしない。Grok/Composerは`mcp_init_completed`確認前に入力欄が見えても送信しない。
|
|
434
434
|
|
|
435
435
|
### トークン削減
|
|
436
436
|
|
|
@@ -442,18 +442,18 @@ handoff contextを前置きできる。この任意経路は`throughline >= 0.9.
|
|
|
442
442
|
|
|
443
443
|
`pty_send` は送信前に破壊的コマンド(`rm -rf /`, `mkfs`, `dd of=/dev/…`, `DROP TABLE` 等)を遮断し(`force: true` で越える)、ESC・ブラケットペースト終端などをサニタイズする。`pty_read` は既定で制御文字を無害化して返す(`raw: true` はバイトをそのまま返す)。これは**サンドボックスではなく tripwire**([既知の制約](#既知の制約バグではなく仕様)参照)。
|
|
444
444
|
|
|
445
|
-
1回の `pty_send` が受理する本文はUTF-8で最大64KiB。同一sessionへの送信はaiterm processをまたいで直列化し、chunk
|
|
445
|
+
1回の `pty_send` が受理する本文はUTF-8で最大64KiB。同一sessionへの送信はaiterm processをまたいで直列化し、chunk同士の混線を防ぐ。全OSで長いPTY入力の欠落を避けるためUTF-8境界を壊さない256-byte単位でpasteし、chunk間に10msのdrain間隔を置く。POSIX shellが前面にいる時のsanitize済み複数行は、改行を含まない単一の`eval`入力へ符号化する。shellがscript全体を所有してから先頭行を実行するため、途中で起動したpager/REPLが後続行を対話キーとして奪わない。単一行、`raw:true`、非shell前面は従来どおり直接PTYへpasteする。agent dispatch の paste はさらに tmux bracketed paste(`paste-buffer -p`)を使う: bracketed paste mode を要求している pane(vendor TUI)へは各 chunk を `ESC[200~/201~` で包んで届け、チャンク投入中のキー解釈による語中文字化け・submit 取り落としを抑える。途中chunkが失敗した場合は部分送信済みであることを明示し、自動でEnterを押さない。送信processの異常終了でlockが残った場合は送信前にfail-closedする。そのsessionを `pty_close` して作り直すか、全sessionを破棄できる場合だけ `pty_kill_all` で安全に掃除する。
|
|
446
446
|
|
|
447
447
|
## 人が覗く
|
|
448
448
|
|
|
449
|
-
セッションは共有 tmux
|
|
449
|
+
セッションは共有 tmux socket(Windows nativeはpsmux namespace)上にある。`pty_open`(および各エージェント起動ツール)の戻り値に表示される `tmux -S … attach -t <id>`、Windowsでは`psmux -L … attach -t <id>`で人間が同じ端末に入って介入できる(抜けるのは `Ctrl-b d`)——起動した Claude/Codex/Grok/Composer のセッションを見たり、途中でキーボードを引き取ったりもできる。
|
|
450
450
|
|
|
451
451
|
## 要件
|
|
452
452
|
|
|
453
453
|
- **Node.js >= 18**
|
|
454
|
-
- **tmux
|
|
454
|
+
- **tmux または psmux**(実行時の前提)
|
|
455
455
|
- **macOS / Linux / WSL2** は tmux を直接使う。macOS は同梱されないので `brew install tmux` で導入する。MCP クライアントがターミナルでなく **GUI から起動**された場合、Homebrew の bin(Apple Silicon: `/opt/homebrew/bin`、Intel: `/usr/local/bin`)が `PATH` に入らないことがある。その場合 aiterm が自動で探索するか、**`AITERM_TMUX=/path/to/tmux`** で明示指定する。
|
|
456
|
-
- **Windows
|
|
456
|
+
- **Windows ネイティブ**は WSL を使わず、tmux CLI互換の [psmux](https://github.com/psmux/psmux) **3.3.8以上**を直接使う(`winget install marlocarlo.psmux`)。pane shell用に Git for Windows も必要。解決先は **`AITERM_PSMUX`**/**`AITERM_BASH`** で上書きできる。Windows toolはSSHと同じく入れ子で握れ、`pty_send "powershell.exe"`でPowerShellへ入れる。
|
|
457
457
|
- **エージェント起動ツール**を使う場合: 対応するベンダー CLI が導入・認証済みであること——`claude_agent` は `claude`、`codex_agent` は `codex`、`grok_agent` / `composer_agent` は `grok`。portable forkだけは追加で`throughline >= 0.9.0`が必要だが、通常のclean launchには不要。(PTY ツールだけ使うなら不要。)
|
|
458
458
|
- 任意: [`rtk`](https://github.com/rtk-ai/rtk) バイナリ(`pty_send` の `rtk: true` 委譲で使う。無くても動く)
|
|
459
459
|
|
package/README.md
CHANGED
|
@@ -461,7 +461,7 @@ When an agent's answer is longer than the on-screen tail (pane height ≈ 24 lin
|
|
|
461
461
|
|
|
462
462
|
### Completion detection (5 layers)
|
|
463
463
|
|
|
464
|
-
`pty_read({ wait: true })` decides "is the command done?" via five layers: process exit / a `mark:true` sentinel / an `until` match / output quiescence with shell return / timeout. When `mark` or `until` is active, that requested evidence takes precedence and a momentarily quiet shell cannot complete the read as quiescent. Agent sessions add a sixth exact layer: Codex observes normal rollout `task_complete`; Grok/Composer observe normal session `turn_ended`; Claude observes its additive launch-correlated Stop event. `aiterm-wait --cursor` performs that vendor-specific observation without the parent blocking or polling. Pre-send readiness failures are MCP errors, and late completion remains recoverable without resending.
|
|
464
|
+
`pty_read({ wait: true })` decides "is the command done?" via five layers: process exit / a `mark:true` sentinel / an `until` match / output quiescence with shell return / timeout. `mark` emits the shell's exit status on POSIX shells and `0` (success) or `1` (failure) on PowerShell; fish/csh/tcsh are rejected before send because they do not share either status syntax. When `mark` or `until` is active, that requested evidence takes precedence and a momentarily quiet shell cannot complete the read as quiescent. Agent sessions add a sixth exact layer: Codex observes normal rollout `task_complete`; Grok/Composer observe normal session `turn_ended`; Claude observes its additive launch-correlated Stop event. `aiterm-wait --cursor` performs that vendor-specific observation without the parent blocking or polling. Pre-send readiness failures are MCP errors, and late completion remains recoverable without resending.
|
|
465
465
|
|
|
466
466
|
### Completion push for parent agents (`aiterm-wait`)
|
|
467
467
|
|
package/dist/core.js
CHANGED
|
@@ -13,7 +13,7 @@ import * as path from "node:path";
|
|
|
13
13
|
import { createHash, randomBytes } from "node:crypto";
|
|
14
14
|
import * as rtk from "./rtk.js";
|
|
15
15
|
import { AitermError, telemetryOwnedFailure, ownTelemetryFailure } from "./errors.js";
|
|
16
|
-
import { isWin, SOCKDIR, tmuxCommand, loadPtyBufferChunk, pasteBufferBaseArgs, TMUX_EMPTY_CONFIG, attachCommand, normalizePaneCommand, settlePaneLog, paneCwdArgument, } from "./tmux-runtime.js";
|
|
16
|
+
import { isWin, SOCKDIR, tmuxCommand, loadPtyBufferChunk, pasteBufferBaseArgs, TMUX_EMPTY_CONFIG, attachCommand, normalizePaneCommand, appendMarkSentinel, settlePaneLog, paneCwdArgument, } from "./tmux-runtime.js";
|
|
17
17
|
import { sleep, currentUid, runtimeStateBase, safeStatSize, readFileRange, writeJson0600, createEmpty0600, shq, LAUNCH_ID_RE, AGENT_DONE_POLL_MS, AGENT_EVENT_MAX_BYTES, assertSessionName, agentsDir, agentEventPath, agentMetadataPath, writeAgentMetadata, AGENT_EVENT_TAIL_BYTES, agentLabel, agentLineageFields, } from "./agent-shared.js";
|
|
18
18
|
import { GROK_MODEL_DEFAULTS, realGrokHome, resolveAndValidateGrokAuth, assertGrokModelAvailable, grokEventsTranscript, latestGrokCompletion, grokInitializationComplete, observeGrokDone, buildGrokAgentCmd, grokLaunchNote, grokEnvTokens, grokTuiReady, GROK_COMPOSER_MARKER_RE, grokFooterHasConfiguration, grokTranscriptText, createGrokAgentMetadata, } from "./vendors/grok.js";
|
|
19
19
|
import { bindCodexTranscriptSession, latestCodexCompletion, observeCodexDone, buildCodexAgentCmd, codexLaunchNote, codexTuiReady, CODEX_COMPOSER_MARKER_RE, codexModelChoice, codexEffortChoice, codexMoreReasoningChoice, codexTranscriptText, createCodexAgentMetadata, } from "./vendors/codex.js";
|
|
@@ -651,10 +651,11 @@ export function send(name, text, o = {}) {
|
|
|
651
651
|
assertInitialPromptNotPendingForSend(name, !!o.force);
|
|
652
652
|
assertManagedClaudeCredentialCommandNotSent(name, text);
|
|
653
653
|
text = prepareSendText(text, o);
|
|
654
|
+
let fg = "";
|
|
654
655
|
if (o.mark) {
|
|
655
656
|
// mark の sentinel は POSIX シェル構文。前面が fish/csh/tcsh 等の非 POSIX 対話シェルだと "$?" が
|
|
656
657
|
// 壊れて sentinel が成立しない。黙って壊れた完了検出を作らず、明示エラーで until を促す(B8)。
|
|
657
|
-
|
|
658
|
+
fg = paneCurrentCommand(name);
|
|
658
659
|
if (NON_POSIX_MARK_SHELLS.has(fg)) {
|
|
659
660
|
throw new AitermError(`mark は POSIX シェル(bash/sh/zsh/dash)前提です。前面が ${fg} のため sentinel の "$?" が` +
|
|
660
661
|
`正しく展開されません。until で完了パターンを指定してください。`, 2);
|
|
@@ -675,7 +676,7 @@ export function send(name, text, o = {}) {
|
|
|
675
676
|
if (o.rtk && !o.force)
|
|
676
677
|
assertNotDestructive(text, 3, "rtk 変換後: ");
|
|
677
678
|
if (o.mark)
|
|
678
|
-
text = text
|
|
679
|
+
text = appendMarkSentinel(text, fg);
|
|
679
680
|
assertSendTextSize(text, o.rtk || o.mark ? "変換後の送信文字列" : "送信文字列");
|
|
680
681
|
const reportedText = text;
|
|
681
682
|
if (!o.raw && text.includes("\n") && ATOMIC_MULTILINE_SHELLS.has(paneCurrentCommand(name))) {
|
package/dist/index.js
CHANGED
|
@@ -112,7 +112,8 @@ server.registerTool("pty_send", {
|
|
|
112
112
|
.boolean()
|
|
113
113
|
.default(false)
|
|
114
114
|
.describe("完了 sentinel(終了コード付き)で包む。pty_read(wait:true) が until 無しでも自動検出して" +
|
|
115
|
-
"
|
|
115
|
+
"完了確定する(POSIX shell と PowerShell に対応。PowerShell の rc は成功0/失敗1。" +
|
|
116
|
+
"fish/csh/tcsh は未対応として送信前に拒否)。" +
|
|
116
117
|
" enter:false と併用すると sentinel が実行されず完了検出が発火しない(送信後に pty_key(\"Enter\") で実行される)。"),
|
|
117
118
|
force: z
|
|
118
119
|
.boolean()
|
package/dist/tmux-runtime.js
CHANGED
|
@@ -165,6 +165,18 @@ export function normalizePaneCommand(cmd) {
|
|
|
165
165
|
return cmd;
|
|
166
166
|
return path.basename(cmd).replace(/\.exe$/i, "").toLowerCase();
|
|
167
167
|
}
|
|
168
|
+
// mark sentinel のOS差は端末runtimeが所有する。Windows native paneでPowerShellが前面なら
|
|
169
|
+
// PowerShellの状態構文を使い、それ以外は既存のPOSIX形式を維持する。
|
|
170
|
+
const WINDOWS_POWERSHELL_COMMANDS = new Set(["powershell", "pwsh"]);
|
|
171
|
+
export function appendMarkSentinel(text, foreground) {
|
|
172
|
+
if (isWin && WINDOWS_POWERSHELL_COMMANDS.has(foreground)) {
|
|
173
|
+
// command echoに完成済みrc=<数字>を含めない。{0}を実行時formatして早期誤完了を防ぐ。
|
|
174
|
+
return text +
|
|
175
|
+
"; if ($?) { [Console]::WriteLine([Environment]::NewLine + ('<<<AITERM_DONE rc={0}>>>' -f 0)) }" +
|
|
176
|
+
" else { [Console]::WriteLine([Environment]::NewLine + ('<<<AITERM_DONE rc={0}>>>' -f 1)) }";
|
|
177
|
+
}
|
|
178
|
+
return text + `; printf '\\n<<<AITERM_DONE rc=%d>>>\\n' "$?"`;
|
|
179
|
+
}
|
|
168
180
|
// Windows の fs.Stats.mode は POSIX permission bit を持たず、常に 666/777 相当を報告する
|
|
169
181
|
// (NTFS ACL は別体系)。既知制約の明示的受容として、Windows では group/other bit 検証を
|
|
170
182
|
// 常に「問題なし」とする。isFile・nlink・owner・size 等の共通検証は呼び手が維持する。
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "aiterm-mcp",
|
|
3
|
-
"version": "0.27.
|
|
3
|
+
"version": "0.27.9",
|
|
4
4
|
"mcpName": "io.github.kitepon/aiterm-mcp",
|
|
5
5
|
"description": "Persistent tmux terminal MCP for launching and driving Claude, Codex, Grok, or Composer from any MCP client, cross-vendor or same-vendor. Also runs durable PTY sessions for SSH, containers, and REPLs.",
|
|
6
6
|
"keywords": [
|