Skip to content

feat(jj-workspace): 非 colocated workspace の gh 全損を GIT_DIR 自動注入で解消 + GH_REPO guard (順位251) - #239

Merged
aloekun merged 1 commit into
masterfrom
fix/jj-workspace-gitdir-inject
Jul 3, 2026
Merged

feat(jj-workspace): 非 colocated workspace の gh 全損を GIT_DIR 自動注入で解消 + GH_REPO guard (順位251)#239
aloekun merged 1 commit into
masterfrom
fix/jj-workspace-gitdir-inject

Conversation

@aloekun

@aloekun aloekun commented Jul 3, 2026

Copy link
Copy Markdown
Owner

概要

PR #238 の監視・マージで実観測した「非 colocated jj workspace での gh 全損」(順位 251) を構造的に解消する。ADR-045 §恒久対策の候補 1 (GIT_DIR 自動注入) の実装 + 場当たり env 対処への防御 preset + 監視 parse / recovery の独立防御 2 層。

変更内容

(a) GIT_DIR 自動注入 — lib_jj_helpers::inject_git_dir_for_gh 新設

  • .git 不在 + GIT_DIR 未設定のとき、.jj/repo (secondary workspace では main store への相対パスを格納したファイル) → store/git_target の順に辿って main の .git を導出し、プロセス env に設定 (子プロセス gh 全体へ伝播)
  • cli-pr-monitor / cli-merge-pipeline / check-ci-coderabbit の main() 冒頭で注入。既存 env 尊重・colocated 環境では no-op・導出失敗は warning + 続行 (fail-soft)
  • tempdir 疑似 layout の unit test 6 件 + 実 jj (init --colocate + workspace add) の #[ignore] 統合テスト (jj 0.42.0 の実レイアウトで検証)

(d) gh-repo-env-guard preset (hooks-pre-tool-validate、恒久)

(b) checker 出力の stdout/stderr 分離 — run_cmd_capture 新設

  • invoke_checker は stdout のみを JSON parse し、stderr は log 転送。checker の fail-soft stderr 警告が JSON に連結され「trailing characters」で監視停止した回帰の防止
  • run_cmd_direct は capture 版への委譲に refactor (既存挙動保持のテスト付き)、cmd 実プロセスの regression test 3 件

(c) owner_repo 検出失敗時の .failed marker — AiStepContext::SkipWithMarker

  • 従来は marker なしで skip し L2 recovery (ADR-030) が発火せず feedback が silent 消失した。skip でも marker を書き recovery 可能に (unit test 4 件更新/追加)

docs

  • ADR-045 改訂: 候補 1 実装済み化、手動 GIT_DIR 前置を fallback に格下げ、コマンド対応表更新、GH_REPO 不可の明記
  • todo13.md / todo-summary.md 順位 251 現在地更新 (順位 225 の dogfood 観測開始日 2026-07-03 記入を含む)

検証

  • cargo clippy --workspace -- -D warnings PASS / cargo test 全 29 suite PASS / cargo test -- --ignored --test-threads=1 15 件 PASS / pnpm lint:docs OK
  • pre-push review: simplicity-review / security-review ともに approved

Dogfood 証跡 (本 PR 自体が実地テスト)

  1. GIT_DIR 自動注入: rebuild 後の check-ci-coderabbit.exe を env 前置なしで実行 → [env] GIT_DIR 自動注入 (非 colocated jj workspace): C:\Users\owner\work\claude-code-hook-test\.git が stderr に出力され、従来の「初期化エラー: リポジトリ取得失敗」が消滅。本 PR の push / PR 作成 / 監視もすべて素のコマンドで実行
  2. gh-repo-env-guard: GH_REPO=... gh api ... を意図的に実行 → 誘導メッセージ付きで block を確認
  3. 観測された FP と回避: commit message 本文に GH_REPO= の字面を含めた際に guard が発火 (text-scanning hook の既知 FP クラス)。字面を避ける表現に修正して回避 — 発生頻度は低く運用で許容と判断

🤖 Generated with Claude Code

Summary by CodeRabbit

  • 新機能

    • 非 colocated な workspace でも、gh 関連コマンドで必要な環境設定を自動補完しやすくなりました。
    • GH_REPO の直接利用を避ける案内が追加されました。
  • バグ修正

    • 監視・CI チェックで、標準エラー出力の混入により JSON 解析が失敗する問題を改善しました。
    • 条件不一致時でも失敗マーカーが残るようになり、後続の回復処理につながりやすくなりました。
  • ドキュメント

    • 並列セッション運用や実行手順に関する説明を更新しました。

…位251)

PR #238 で実観測した 3 欠陥 (repo 検出失敗 / checker JSON parse 停止 /
post-merge feedback silent 消失) と、GH_REPO による場当たり対処の部分故障を
構造的に解消する (ADR-045 恒久対策候補 1 の実装 + 防御 preset)。

(a) GIT_DIR 自動注入 (lib-jj-helpers::inject_git_dir_for_gh):
- .git 不在 + GIT_DIR 未設定のとき .jj/repo (secondary workspace では
  main store への相対パスファイル) → store/git_target を辿って main の
  .git を導出し、プロセス env に設定 (子プロセス gh 全体へ伝播)
- cli-pr-monitor / cli-merge-pipeline / check-ci-coderabbit の main() で
  注入。既存 env 尊重・導出失敗は warning + 続行 (fail-soft)
- tempdir 疑似 layout の unit test 6 件 + 実 jj (init --colocate +
  workspace add) の #[ignore] 統合テスト

(d) gh-repo-env-guard preset (hooks-pre-tool-validate、恒久):
- Bash / PowerShell の GH_REPO 環境変数代入を block し GIT_DIR / 自動注入 /
  repo 指定フラグへ誘導 (PowerShell 構文は matcher 拡張に備え先行)
- GH_REPO は引数なし gh repo view に効かず silent 部分故障を招くため

(b) checker 出力の stdout/stderr 分離 (run_cmd_capture 新設):
- invoke_checker は stdout のみ JSON parse、stderr は log 転送。checker の
  fail-soft stderr 警告が JSON に連結され trailing characters で監視停止
  した回帰の防止 (cmd 実プロセスの regression test 付き)

(c) owner_repo 検出失敗時の .failed marker (AiStepContext::SkipWithMarker):
- 従来は marker なしで skip し L2 recovery (ADR-030) が発火しなかった。
  skip でも marker を書き recovery 可能に

docs: ADR-045 改訂 (候補 1 実装済み化、手動 GIT_DIR を fallback に格下げ、
コマンド対応表更新)、todo13/todo-summary 順位 251 現在地更新 (dogfood 記録
と順位 225 dogfood 開始日記入を含む)

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jul 3, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

非colocated jj workspaceでのgh呼び出し失敗に対応するため、lib-jj-helpersにGIT_DIR解決・注入APIを新設し、cli-pr-monitor / cli-merge-pipeline / check-ci-coderabbitに組み込んだ。checker出力のstdout/stderr分離、marker付きAIステップスキップ、GH_REPOをブロックするhooksプリセット、関連ドキュメント更新も含む。

Changes

GIT_DIR自動注入とGH_REPOガード

Layer / File(s) Summary
GIT_DIR解決・注入ライブラリの新設
src/lib-jj-helpers/src/lib.rs, src/lib-jj-helpers/Cargo.toml
GitDirResolution型、resolve_git_dirinject_git_dir_for_ghを追加し、tempdirを用いたユニットテストと実jjを使う統合テストを実装。
各CLIへのGIT_DIR注入組み込み
src/cli-pr-monitor/src/main.rs, src/cli-merge-pipeline/src/main.rs, src/check-ci-coderabbit/src/main.rs, src/check-ci-coderabbit/Cargo.toml
各exeのmain開始時にinject_git_dir_for_ghを呼び出し、check-ci-coderabbitはstderrへログするコールバックを追加。
AIステップのスキップ処理とfailedマーカー
src/cli-merge-pipeline/src/pipeline.rs
AiStepContext(Ready/SkipSilent/SkipWithMarker)を導入し、owner_repo検出失敗時に.failedマーカーを書き込むよう変更、既存テストを更新。
checker実行のstdout/stderr分離とJSONパース
src/cli-pr-monitor/src/runner.rs, src/cli-pr-monitor/src/stages/poll/iteration.rs
CmdCapture/run_cmd_captureでstdout/stderrを分離し、invoke_checkerがstdoutのみをJSONパースするよう変更、回帰テストを追加。
gh-repo-env-guardプリセットの追加
src/hooks-pre-tool-validate/src/presets/gh.rs, .../mod.rs, .claude/hooks-config.toml
GH_REPO環境変数の使用をブロックしGIT_DIR/--repoへ誘導するpresetを追加し、dispatchテーブルと設定ファイルに組み込み。
関連ドキュメントの更新
docs/adr/adr-045-jj-workspace-parallel-sessions.md, docs/auto-push-gate-dogfood.md, docs/todo-summary.md, docs/todo13.md
GIT_DIR自動注入の実装状況、観測された障害連鎖、対応タスクと完了基準を記載。

Estimated code review effort: 4 (Complex) | ~60 minutes

Possibly related PRs

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed 非 colocated jj workspace への GIT_DIR 自動注入と GH_REPO guard 追加という主変更を的確に要約しています。
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
src/hooks-pre-tool-validate/src/presets/gh.rs (1)

57-70: 🔒 Security & Privacy | 🔵 Trivial | 💤 Low value

printf -v / read 経由の代入はすり抜ける可能性があります。

printf -v GH_REPO "..."read GH_REPO <<< ... のように = を伴わない代入方法は現状のパターンでは検出されません。ただし、本ファイルの他プリセット (gh-pr-create-guard 等) も同様に単純な正規表現ベースの検出方針を取っており、実運用上のリスクは低いと考えます。

Based on learnings, this repo's hook validator presets intentionally use single-pattern regex detection rather than tracking broader command semantics, so this is a minor, acceptable gap rather than a required fix.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/hooks-pre-tool-validate/src/presets/gh.rs` around lines 57 - 70, The
GH_REPO guard in preset_gh_repo_env_guard intentionally uses simple regex-based
matching, so this is not a functional bug to expand into command-semantic
parsing; keep the existing BlockedPattern rules consistent with the other gh
presets. If you want to address the comment, add a brief note near
preset_gh_repo_env_guard (or the GH_REPO_ENV_MSG usage) clarifying that forms
like printf -v and read are intentionally out of scope for this validator.

Source: Learnings

src/lib-jj-helpers/Cargo.toml (1)

12-14: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

tempfile はワークスペース依存関係経由での宣言を検討してください。

As per coding guidelines, **/Cargo.toml は "Integrate Rust packages through a Cargo workspace" を求めています。本変更は tempfile = "3" をこの crate の [dev-dependencies] に直接バージョン指定していますが、他の crate (下流ファイルの graph context 上でも tempfile への参照が示唆されている) と重複してバージョンが乖離するリスクがあります。ルートの [workspace.dependencies]tempfile を追加し、tempfile = { workspace = true } で参照する形に統一することを推奨します。

♻️ ワークスペース依存関係化の例 (ルート Cargo.toml が既にワークスペースの場合)
 [dev-dependencies]
-tempfile = "3"
+tempfile = { workspace = true }

以下のスクリプトでルート Cargo.toml[workspace.dependencies]tempfile が既に存在するか確認できます:

#!/bin/bash
echo "--- root workspace Cargo.toml の [workspace.dependencies] ---"
fd -HI '^Cargo\.toml$' -d 1 --exec cat {} \;

echo "--- 他 crate での tempfile 依存宣言方法 ---"
rg -n 'tempfile' --type=toml
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/lib-jj-helpers/Cargo.toml` around lines 12 - 14, The current
dev-dependency declaration for tempfile is hardcoded in this crate, so update it
to use the workspace-managed dependency instead. Check the root Cargo.toml for
[workspace.dependencies], add tempfile there if missing, and change this crate’s
[dev-dependencies] entry in the Cargo.toml for src/lib-jj-helpers to reference
tempfile with workspace = true. Keep the dependency name consistent with other
crates that use tempfile so version ownership stays centralized.

Source: Coding guidelines

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@src/hooks-pre-tool-validate/src/presets/gh.rs`:
- Around line 57-70: The GH_REPO guard in preset_gh_repo_env_guard intentionally
uses simple regex-based matching, so this is not a functional bug to expand into
command-semantic parsing; keep the existing BlockedPattern rules consistent with
the other gh presets. If you want to address the comment, add a brief note near
preset_gh_repo_env_guard (or the GH_REPO_ENV_MSG usage) clarifying that forms
like printf -v and read are intentionally out of scope for this validator.

In `@src/lib-jj-helpers/Cargo.toml`:
- Around line 12-14: The current dev-dependency declaration for tempfile is
hardcoded in this crate, so update it to use the workspace-managed dependency
instead. Check the root Cargo.toml for [workspace.dependencies], add tempfile
there if missing, and change this crate’s [dev-dependencies] entry in the
Cargo.toml for src/lib-jj-helpers to reference tempfile with workspace = true.
Keep the dependency name consistent with other crates that use tempfile so
version ownership stays centralized.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 9d0dc07b-be85-4f23-b6ff-cf571bf43424

📥 Commits

Reviewing files that changed from the base of the PR and between 27ab7ca and 1c55209.

⛔ Files ignored due to path filters (1)
  • Cargo.lock is excluded by !**/*.lock
📒 Files selected for processing (16)
  • .claude/hooks-config.toml
  • docs/adr/adr-045-jj-workspace-parallel-sessions.md
  • docs/auto-push-gate-dogfood.md
  • docs/todo-summary.md
  • docs/todo13.md
  • src/check-ci-coderabbit/Cargo.toml
  • src/check-ci-coderabbit/src/main.rs
  • src/cli-merge-pipeline/src/main.rs
  • src/cli-merge-pipeline/src/pipeline.rs
  • src/cli-pr-monitor/src/main.rs
  • src/cli-pr-monitor/src/runner.rs
  • src/cli-pr-monitor/src/stages/poll/iteration.rs
  • src/hooks-pre-tool-validate/src/presets/gh.rs
  • src/hooks-pre-tool-validate/src/presets/mod.rs
  • src/lib-jj-helpers/Cargo.toml
  • src/lib-jj-helpers/src/lib.rs

@aloekun
aloekun merged commit c063787 into master Jul 3, 2026
1 check passed
@aloekun
aloekun deleted the fix/jj-workspace-gitdir-inject branch July 3, 2026 05:03
aloekun added a commit that referenced this pull request Jul 3, 2026
…252/253 登録) (#240)

- 順位 251 (非 colocated jj workspace 対応) を完了削除: PR #239 で
  GIT_DIR 自動注入 + gh-repo-env-guard preset + stdout 分離 + skip 時
  marker として land、dogfood (監視完走 + post-merge feedback 復旧) を
  実運用確認済みのため entry + summary 行を削除
- 順位 252 登録: 部分効果 env var anti-pattern の文書化 (新 ADR、
  placeholder policy 適用、feedback T3-1 採用)
- 順位 253 登録: ADR-030 に feedback silent skip 実装記録を追記
  (feedback T3-2 採用)

Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant