Skip to content

feat: devbase up の機密の注入で SecretStore を持ち回り、サーバ backend の往復を設計の想定へ収める (PLAN55) - #177

Merged
takemi-ohama merged 14 commits into
mainfrom
feat/plan55-up-single-injection
Sep 14, 2026
Merged

takemi-ohama merged 14 commits into
mainfrom
feat/plan55-up-single-injection

Conversation

@takemi-ohama

@takemi-ohama takemi-ohama commented Sep 14, 2026 •

Copy link
Copy Markdown
Contributor

概要

devbase up 1 回のサーバ backend(OpenBao)への往復を、仕様「OpenBao との契約」の想定
「認証 1 回 + 参照ごとに取得 1 回」に収める。注入の 3 か所(dispatch 前 / 切替後 / 起動直前)と
_ensure_env_files が SecretStore を作り直していたのを、ライフサイクル操作 1 回の間
持ち回る形にした。要求と設計は issues/PLAN55_up-single-injection.md /
issues/PLAN55_up-single-injection-design.md(設計 PR #176 でマージ済み)。

関連 Issue

変更点

  • env/runtime.py: store_for(root) / release_store() を追加。resolve / inject / child_env は store=None のときこれを使う(明示的に渡した store は控えない)
  • commands/container.py: _ensure_env_files が持ち回った store で判定(GET 0)。env init の子プロセスから戻ったら release_store()(決定 5)。_dispatch_lifecycle の finally で release_store()(決定 2)
  • tui/dispatch.py: 委譲の入口 _preserve_cwd_env で release_store()(決定 3)
  • テスト: tests/env/test_runtime_store.py(規則の表)、tests/cli/test_up_roundtrips.py(3 経路の往復 + env init 後の読み直し)、tests/cli/tui/test_dispatch.py(入口で捨てる / env edit → up)、tests/conftest.py(autouse で捨てる)
  • 構造改善(cross-refactoring、3 ラウンド): 現状固定テスト 5 件(cmd_project / resolve / _inject_secrets の失敗系)、_resolve_project_name / _ensure_images の extract method、_build_resolved / cmd_login / _image_max_age_days の重複の統合。見送り 9 件の内訳は改修計画 feat: devbase up の機密の注入で SecretStore を持ち回り、サーバ backend の往復を設計の想定へ収める (PLAN55) #177 (comment)

往復の実測(偽サーバ): web の中で up = 認証 1 / GET 4、api の中で up web = 認証 1 / GET 6、projects/ の外で up web = 認証 1 / GET 4(変更前は認証 4 / GET 12〜14)。

検証結果

head 15a6baa。合否は終了コードで判定。

段階 コマンド 対象範囲 実行時刻 結果
限定的な検証 uv run pytest -q tests/cli/test_up_roundtrips.py tests/env/test_runtime_store.py tests/cli/tui/test_dispatch.py tests/cli/test_project_name_resolution.py tests/commands/test_container_up_order.py tests/commands/test_container_context.py 変更箇所と切替の回帰 2026-09-14 20:26 98 passed / exit=0
全体テスト uv run pytest -q tests/ 全体 2026-09-14 20:26 2233 passed / exit=0
静的解析 uvx ruff check --select=E9,F63,F7,F82 lib(CI と同じ選択) lib 2026-09-14 20:28 All checks passed / exit=0
ビルド python3 -m compileall -q lib bin lib bin 2026-09-14 20:28 exit=0
結合(CI) GitHub Actions run 34836641985 Python syntax 3.10/3.11/3.12 / Ruff lint / ShellCheck head 15a6baa 5 件 pass
レビュー cross-review(2 ラウンド) agy / kiro / codex — 全員 APPROVE、未解決 0 件

カバレッジツールの設定は無い(pyproject.toml に [tool.coverage] なし)ため閾値の判定は行わない。

受け入れ条件(PLAN55): 9/9 のうち 8 を満たす。

  • 1 web の中で up: 認証 1 / GET 4 → test_up_roundtrips.py::test_up_in_project
  • 2 api の中で up web: 認証 1 / GET ≤ 6、api 固有キーが残らない → ::test_up_other_project
  • 3 projects/ の外で up web: 認証 1 / GET 4 → ::test_up_from_outside
  • 4 _ensure_env_files が GET を出さない → ::test_ensure_env_files_reads_seen
  • 5 backend age で 3 経路の結果が同じ → 既存 test_project_name_resolution.py / test_container_up_order.py / test_container_context.py が変更なしで通る
  • 6 切替の回帰テストが通る → test_project_name_resolution.py を変更していない
  • 7 pytest / ruff / compileall → 上の表
  • 8 env init が書いた値で起動する → ::test_up_after_env_init_reads_written_values
  • 9 TUI で env edit → up が新しい値で起動する → tui/test_dispatch.py::test_lifecycle_after_env_edit_reads_written_values

未検証の項目: 実機(backend openbao の端末)で devbase --verbose up の認証の行が 1 回であること — リリース後テスト(PLAN53 の切り替え後)で行う
既存の失敗: なし
範囲外と判断したもの: なし(見送った構造改善 9 件は改修計画に残り、この PR の受け入れ条件の外)

補足

🤖 Generated with Claude Code

https://claude.ai/code/session_01S9okWVz1S7VGUsCQWVMhb3

takemi-ohama and others added 2 commits September 14, 2026 18:48
…照ごとに 1 回にする (PLAN55)

runtime.store_for / release_store を足し、resolve / inject / child_env と
_ensure_env_files が同じ SecretStore を使う。捨てる契機は _dispatch_lifecycle の
finally、TUI の委譲の入口、env init の子プロセスから戻った直後の 3 つ。

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01S9okWVz1S7VGUsCQWVMhb3
Add characterization coverage for stale secret caches after project dispatch errors, invalid UTF-8 project env files, missing DEVBASE_ROOT, and store release after project name resolution failure.

Item-Id: R1-001
Round: 1
Impl-Runtime: codex
Impl-Model: default
@takemi-ohama

takemi-ohama commented Sep 14, 2026 •

Copy link
Copy Markdown
Contributor Author

改修計画 — devbasex/devbase #177

/ndf:cross-refactoring が提案し、適用した改善項目の記録である。
理由と手順は提案の時点でしか残らないため、公開の直前に書き出している。

  • 対象範囲: lib/devbase/env/runtime.py, lib/devbase/commands/container.py, lib/devbase/tui/dispatch.py, tests/env, tests/cli, tests/conftest.py
  • 着手前のテスト: uv run pytest -q tests/

ラウンド 1(実装 codex / レビュー agy / kiro)

R1-001 — lib/devbase/commands/container.py#cmd_project

兆候・経路 手法・階層 重要度 提案元 状態 コミット
error unit — codex / agy 採用 1

なぜ: test_up_roundtrips.py は正常起動と env init 成功後の再読込を固定し、test_runtime_store.py は release_store 単体を固定している。一方、cmd_project の異常終了を挟んだ次の解決で、操作前の機密キャッシュが残らないことは固定されていない。対象範囲の release_store/store_for 利用箇所も検索して確認した。

手順: 1. openbao_root/openbao を使い、team/global に TOKEN=old を保存して runtime.resolve(root) で読み込む。
2. サーバ側を TOKEN=new に更新する。未知の subcommand、存在しないプロジェクト名、公開ハンドラ cmd_ps のスタブが RuntimeError を送出する場合を独立したケースにする。
3. cmd_project を公開入口として実行し、早期終了では戻り値 1、例外では RuntimeError の伝播という現状の結果を記録する。
4. release_store を明示的に呼ばず runtime.resolve(root) を実行し、TOKEN=new が得られることを固定する。ストアの同一性・内部フィールド・release_store の呼出回数は検証しない。
5. 後片付けは検証後に行い、fixture の解除処理で本体の解除漏れが隠れないようにする。

R1-002 — lib/devbase/env/runtime.py#resolve

兆候・経路 手法・階層 重要度 提案元 状態 コミット
error unit — codex / kiro 採用 1

なぜ: 既存テストは正常な非機密 env による上書き、環境変数にないキーの除外、四層の優先順位を固定しているが、非機密 env が不正 UTF-8 の場合の継続動作は固定していない。暗号化機密の不正 UTF-8 を検証する test_secret_store.py とは読込対象と結果が異なる。実ファイルと EnvFile のデコードをつなぐ経路として固定する。

手順: 1. 一時プロジェクトの env に TOKEN=override の有効な行と不正 UTF-8 バイトを含むデータを実際に書き、os.environ の TOKEN にも上書き候補値を設定する。
2. 既存の四層ストアの疑似実装で共通機密 TOKEN=secret とプロジェクト固有キーを与え、resolve(root, web, store=...) を公開入口として実行する。ファイル読込と EnvFile のデコードは差し替えない。
3. 例外を送出せず、非機密 env の上書きを全体として無視し、機密の values と由来別のキー集合が保たれる現状の出力を記録して固定する。有効な先頭行だけを部分適用しない点も TOKEN の値で確認する。
4. 表示・警告の完全一致や private 関数の直接呼出しは検証しない。

R1-003 — lib/devbase/commands/container.py#_inject_secrets

兆候・経路 手法・階層 重要度 提案元 状態 コミット
branch unit — kiro 採用 1

なぜ: _inject_secrets の DEVBASE_ROOT 未設定分岐 (root is None のとき inject を呼ばず空の SecretEnv を返す) が固定されていない。既存テストは inject をスタブ化するか required=True の再送出だけを覆い、root 未設定で早期に空を返す経路は未固定。

手順: 1. DEVBASE_ROOT を unset する
2. container._inject_secrets(required=True) を呼ぶ
3. 戻り値が偽な (空の) SecretEnv で、例外も出ないことを assert する
4. required=False でも同じく空を返すことを assert する

R1-004 — lib/devbase/commands/container.py#_inject_secrets

兆候・経路 手法・階層 重要度 提案元 状態 コミット
error unit — kiro 採用 1

なぜ: _inject_secrets の required=False での DevbaseError 握り潰し分岐 (warning を出して空の SecretEnv を返し、down/ps/logs を止めない) が固定されていない。required=True の再送出は test_container_up_order で固定済みだが、required=False で続行する経路は未固定。

手順: 1. DEVBASE_ROOT を一時ディレクトリへ設定する
2. runtime.inject を DevbaseError を投げるスタブへ差し替える
3. container._inject_secrets(required=False) を呼ぶ
4. 例外が伝播せず、戻り値が偽な (空の) SecretEnv であることを assert する
5. 同じ入力で required=True のときは DevbaseError が送出されることを assert し、分岐差を固定する

R1-005 — lib/devbase/commands/container.py#cmd_project

兆候・経路 手法・階層 重要度 提案元 状態 コミット
branch unit — agy 採用 1

なぜ: プロジェクト名解決(_resolve_project_name)に失敗して早期リターンする分岐で、finally 節により持ち回りの SecretStore が解放される経路が固定されていない

手順: 1. 事前に runtime.store_for で控えを生成した状態にする
2. 存在しないプロジェクト名を指定して cmd_project を呼び出し、戻り値が 1 となることを確認する
3. 実行後に runtime.store_for を呼び、以前の控えとは異なる新しいインスタンスが返ることを検証する

ラウンド 2(実装 agy / レビュー codex / kiro)

R2-001 — lib/devbase/commands/container.py#_resolve_project_name

兆候・経路 手法・階層 重要度 提案元 状態 コミット
long_method extract_method minor agy / kiro 採用 1

なぜ: 1 関数が projects_dir 解決・存在確認・already_there 判定・呼び出し元 env キーの記録と chdir・PWD 差し替え・切替先との差分 unset・env 反映・COMPOSE_PROJECT_NAME 上書きを通しで行う。切替時のクリーンアップ処理 (caller_env_keys の unset) が独立した段階として名前を持てる。

手順: 1. chdir 後に呼び出し元固有の env キーを落とす部分を _unset_caller_only_env_keys(caller_keys, target_dir) として抽出
2. _resolve_project_name は解決・chdir・抽出関数の呼び出し・env 反映の順に整理する
3. tests/cli/test_project_name_resolution.py を実行して chdir/PWD/unset の振る舞いが不変であることを確認

R2-002 — lib/devbase/commands/container.py#_ensure_images

兆候・経路 手法・階層 重要度 提案元 状態 コミット
duplication consolidate_duplication major agy 取り消し 1

なぜ: _ensure_images (L1428-1444) 内で docker compose config --format json を実行し JSON をパースして dev サービス定義を取得する処理が、同ファイル内の _resolve_dev_service (L1221-1234) と完全に重複している。

手順: 1. _ensure_images 内の docker compose config 実行と json.loads、services.get(...) 処理を _resolve_dev_service() の呼び出しに置き換える
2. _resolve_dev_service() が None を返した場合のエラーハンドリングを _run_build() へのフォールバックとして整理する

R2-003 — lib/devbase/commands/container.py#_ensure_images

兆候・経路 手法・階層 重要度 提案元 状態 コミット
long_method extract_method major kiro 採用 1

なぜ: 1 関数が compose config の取得・JSON 解析・dev サービスと image 名の取り出し・image inspect・4 分岐 (fetch/repull/build_with_expires) を通しで行い、全体を広い try/except Exception で包む。段階に名前が付けられ、部分だけをテストできない。

手順: 1. docker compose config --format json の実行と services 取得を _read_compose_services() として抽出
2. dev サービスから image 名・has_build を取り出す部分を _dev_image_spec(services) として抽出
3. image inspect と returncode 判定を通す残りの分岐は _ensure_images に残し、抽出した関数を呼ぶ形へ書き換える
4. tests/cli/test_base_image_staleness.py / test_rebuild.py を実行し挙動不変を確認

R2-004 — lib/devbase/commands/container.py#cmd_scale

兆候・経路 手法・階層 重要度 提案元 状態 コミット
long_method extract_method major agy 取り消し 1

なぜ: cmd_scale (L1030-1113, 84行) は引数検証、設定更新、ボリューム/ネットワーク準備、compose 生成、起動、待機、フック実行、ログ出力の全段階を1つの関数内で通しで行っており、cmd_up のような実行パイプラインの分離がなされていない。

手順: 1. ボリューム・ネットワーク確認、compose 生成、docker compose up、ready 待機を行う処理を _run_scale_pipeline として抽出する
2. cmd_scale 側を引数検証、設定更新、パイプライン呼び出し、後続処理(デプロイスクリプト実行、ログ出力)に整理する

R2-005 — lib/devbase/commands/container.py#_build_resolved

兆候・経路 手法・階層 重要度 提案元 状態 コミット
duplication consolidate_duplication minor kiro 採用 1

なぜ: ビルド実行後の終了コード変換 return 0 if _run_build(...) else 1 が同一関数内に 5 回並ぶ (no_cache 経路・expires None 経路・compose 読取り失敗・image 名なし・inspect 失敗)。bool → プロセス終了コードへの同じ変換が散り、片方だけ書き換わると挙動が食い違う。_build_with_expires への委譲行も同型。

手順: 1. bool を終了コードへ写す小ヘルパ (例: _exit_code(ok: bool) -> int) を module 内に追加する
2. _build_resolved 内の各 return 0 if <call> else 1 を return _exit_code(<call>) に置換する
3. 既存テスト (tests/cli/test_rebuild.py / test_base_image_staleness.py) を実行して終了コードが不変であることを確認する

ラウンド 3(実装 kiro / レビュー codex / agy)

R3-001 — lib/devbase/commands/container.py#_read_compose_services

兆候・経路 手法・階層 重要度 提案元 状態 コミット
duplication consolidate_duplication minor agy / kiro 取り消し 1

なぜ: _read_compose_services と _resolve_dev_service がどちらも docker compose config --format json を実行し stdout を json.loads して services を取り出す。コマンド文字列・失敗時の扱い・JSON パースが 2 箇所に分かれており、compose config の呼び方を変えると両方を直す必要がある。変わるときは必ず一緒に変わる同一由来の重複。

手順: 1. docker compose config --format json を実行し (returncode, services_dict) を返す 1 つの内部関数へ寄せる (現 _read_compose_services をこの形に保つ)
2. _resolve_dev_service をその関数の呼び出しへ書き換え、returncode!=0 / JSONDecodeError 時は None、成功時は services.get(get_dev_service_name(), {}) を返す薄い包みにする
3. json.JSONDecodeError の握り方を共通関数側に寄せ、両呼び出し元の挙動 (失敗時 None / (rc,{})) を現状のまま保つ
4. tests/cli/test_rebuild.py と tests/cli/test_base_image_staleness.py の該当経路を実行して現状の戻り値・分岐が不変であることを確認

R3-002 — lib/devbase/commands/container.py#cmd_login

兆候・経路 手法・階層 重要度 提案元 状態 コミット
duplication consolidate_duplication minor agy / kiro 採用 1

なぜ: cmd_login は _apply_context→_inject_secrets(required=False) の前処理と、.docker-compose.scale.yml の有無で -f を足す docker compose コマンド構築を _compose_run と重複して持つ。login は exec の index 指定だけが異なり、compose ファイルの付与規則と前処理は同一由来で一緒に変わる。

手順: 1. _compose_run に scale override の -f 付与規則があるので、compose ベース引数 (['docker','compose'] + 必要なら ['-f', scale_file]) を返す小さなヘルパへ切り出す
2. cmd_login はそのヘルパでベースを得た上で exec / --index の差分だけを足す形に書き換える (_apply_context + _inject_secrets の前処理もヘルパ側へ寄せられる範囲で共有)
3. scale override 有り (exec service-index) / 無し (exec --index=) の 2 経路の生成コマンドが現状と一致することを tests/cli の login 経路で確認する

R3-003 — lib/devbase/commands/container.py#_image_max_age_days

兆候・経路 手法・階層 重要度 提案元 状態 コミット
duplication consolidate_duplication minor agy / kiro 検証中 1

なぜ: _image_max_age_days と _snapshot_min_interval_minutes が同型の処理構造を持つ。環境変数の取得、未設定時の既定値返却、整数変換、負値の ValueError 送出による除外、不正値時の warning ログ出力と既定値フォールバックという一連のバリデーション・フォールバックのロジックが 2 箇所に重複している。

手順: 1. _env_non_negative_int(env_name, default) を導入し、read→未設定既定→int→負値 ValueError→warning+既定 の流れを 1 箇所へ寄せる
2. warning 文言を関数内で env 名・raw・default から組み立て、現行 2 種の文言と実質同等にする
3. _image_max_age_days / _snapshot_min_interval_minutes を新ヘルパへの委譲 (定数を渡すだけ) に置き換える
4. tests/cli の期限系テストを実行し、既定値・不正値フォールバック・負値拒否の現状挙動が不変か確認する (snapshot 側の挙動確認のため tests/cli に共有ヘルパの現状固定テストを 1 本足す)

見送った項目

ラウンド 対象 兆候・経路 理由
1 lib/devbase/env/runtime.py#inject error 1 ラウンドの採用上限 5 件を超えた
1 lib/devbase/env/runtime.py#resolve branch 1 ラウンドの採用上限 5 件を超えた
1 lib/devbase/env/runtime.py#store_for boundary 1 ラウンドの採用上限 5 件を超えた
1 lib/devbase/tui/dispatch.py#dispatch_group error 1 ラウンドの採用上限 5 件を超えた
1 lib/devbase/tui/dispatch.py#dispatch_lifecycle normal 1 ラウンドの採用上限 5 件を超えた
2 lib/devbase/commands/container.py#_ensure_env_files long_method 1 ラウンドの採用上限 5 件を超えた
2 lib/devbase/commands/container.py#_ensure_images duplication コミット 7add6cf にトレーラーが欠けています: Item-Id, Round, Impl-Runtime, Impl-Model
2 lib/devbase/commands/container.py#cmd_scale long_method 実差分 222 行が差分予算 165 行(見積 55 行 × 3)を超えました(範囲の逸脱)
3 lib/devbase/commands/container.py#_read_compose_services duplication コミット 3ad3fb9 にトレーラーが欠けています: Item-Id, Round, Impl-Runtime, Impl-Model

takemi-ohama and others added 12 commits September 14, 2026 19:10
Add characterization test verifying that DevbaseError is swallowed and returns an empty SecretEnv when required=False, while DevbaseError is re-raised when required=True.

Item-Id: R1-004
Round: 1
Impl-Runtime: agy
Impl-Model: default
…_project_name

project 切替時に呼び出し元固有の env キーを unset する段階を
_unset_caller_only_env_keys(caller_keys, target_dir) として抽出した。
_resolve_project_name は 解決 → chdir/PWD 差し替え → 抽出関数呼び出し →
env 反映 の順に整理され、クリーンアップ処理が独立した名前を持つ。
振る舞いは不変 (tests/cli/test_project_name_resolution.py を含む全テストが通過)。

Item-Id: R2-001
Round: 2
Impl-Runtime: kiro
Impl-Model: default
…#_ensure_images

_ensure_images 内で docker compose config を実行し JSON を解釈して dev
サービス定義を取り出す処理を、同ファイルの _resolve_dev_service() の
呼び出しに置き換える。取得できない (None) ときは従来どおり _run_build()
へフォールバックする。

現状固定テストとして _ensure_images の入口を subprocess.run の応答だけで
固定する 10 件を tests/cli/test_base_image_staleness.py に追加した。

Item-Id: R2-002
Round: 2
Impl-Runtime: claude
Impl-Model: default

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
…images

Extract Compose services reading and dev image specification while preserving image checks and fallback behavior.

Item-Id: R2-003
Round: 2
Impl-Runtime: codex
Impl-Model: default
cmd_scale 内のボリューム・ネットワーク確認、compose 生成、起動、待機処理を
_run_scale_pipeline として抽出し、cmd_scale を引数検証・設定更新・パイプライン呼び出し・後続処理に整理。

Item-Id: R2-004
Round: 2
Impl-Runtime: agy
Impl-Model: default
…#_build_resolved

_build_resolved 内で 5 回並んでいた `return 0 if <call> else 1` の bool→終了コード
変換を、module ヘルパ `_exit_code(ok: bool) -> int` に集約。委譲行 (_build_with_expires)
も同型のため同じヘルパへ統一した。振る舞いは不変。

Item-Id: R2-005
Round: 2
Impl-Runtime: kiro
Impl-Model: default
…#_read_compose_services

_resolve_dev_service が独自に `docker compose config --format json` を実行して
JSON を読んでいたのを、_read_compose_services の呼び出しへ寄せる。compose config
の呼び方は 1 箇所になり、_resolve_dev_service は returncode!=0 / JSONDecodeError で
None、成功時に services.get(dev_service_name, {}) を返す薄い包みになる。

JSONDecodeError の握りは _resolve_dev_service 側に残す。共通関数側で握って
(rc, {}) を返すと _ensure_images の不正 JSON 経路 (except → _run_build) が
「イメージ未指定 → True」へ変わるため。

両関数の本体はテストで通っていなかったので、書き換え前に現状固定テストを
tests/cli/test_rebuild.py へ追加した (失敗時 None / (rc,{}) / 不正 JSON の伝播)。

Item-Id: R3-001
Round: 3
Impl-Runtime: claude
Impl-Model: default

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
…ainer.py#_read_compose_services"

This reverts commit 3ad3fb9.
…#cmd_login

Share Compose context and secret preparation and override file argument construction. Preserve login command variants and execution order with CLI regression tests.

Item-Id: R3-002
Round: 3
Impl-Runtime: codex
Impl-Model: default
…#_image_max_age_days

Consolidate duplicate non-negative integer environment variable parsing
in _image_max_age_days and _snapshot_min_interval_minutes into a shared
helper _env_non_negative_int.

Item-Id: R3-003
Round: 3
Impl-Runtime: agy
Impl-Model: default

@takemi-ohama takemi-ohama left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

🤖 cross-review | round 1 | kiro | APPROVE

SecretStore を操作 1 回持ち回る設計 (store_for/release_store) は、注入の 3 経路と _ensure_env_files を同一インスタンスへ寄せ、往復削減の意図と一致している。env init 後の release_store()(決定 5)、_dispatch_lifecycle finally / TUI 入口での解放、conftest の autouse fixture によるテスト間漏洩対策まで揃っており、モジュールグローバル状態のリスクは制御されている。抽出系リファクタ(_env_non_negative_int / _compose_base_args / _read_compose_services / _dev_image_spec / _unset_caller_only_env_keys / _exit_code)はいずれも既存挙動を保った忠実な抽出で、現状固定テストが伴っている。対象テスト 149 件を実行し全て pass。修正を要する指摘は無し。

@takemi-ohama takemi-ohama left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

🤖 cross-review | round 1 | agy | APPROVE

PLAN55(SecretStore のライフサイクル管理による往復削減)および各ラウンドの採用リファクタリング(R2-001, R2-003, R2-005, R3-002, R3-003)と現状固定テストが要件通り実装され、全テストの通過を確認しました。修正を要する問題はありません。

@takemi-ohama takemi-ohama left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

🤖 cross-review | round 2 | codex | APPROVE

新規の修正指摘はありません。関連テスト 189 件が成功しました。

@takemi-ohama takemi-ohama left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

🤖 cross-review | round 2 | kiro | APPROVE

PLAN55(SecretStore を lifecycle 1 回だけ持ち回り、サーバ backend の往復を認証 1 回+参照ごと 1 回へ収める)の実装として一貫している。store_for/release_store の寿命管理(_dispatch_lifecycle の finally / TUI 入口 / env init 後の release / conftest autouse)が 3 経路 + env init 後読み直しの受け入れ条件と偽サーバ実測で固定されており、_exit_code / _env_non_negative_int / _read_compose_services / _dev_image_spec / _compose_base_args の抽出はいずれも挙動保存で対応テストが付いている。修正を要する設計・正確性・セキュリティ上の指摘は無い。

@takemi-ohama
takemi-ohama marked this pull request as ready for review September 14, 2026 11:29
@takemi-ohama
takemi-ohama merged commit 9a1e504 into main Sep 14, 2026
5 checks passed
@takemi-ohama
takemi-ohama deleted the feat/plan55-up-single-injection branch September 14, 2026 11:47
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.

devbase up が機密を 2 度注入し、サーバ backend では HTTP 往復が設計の想定の 2 倍になる

1 participant