名探偵Bicep:消えたmoduleの謎(完全版)
- 山崎行政書士事務所
- 9月19日
- 読了時間: 6分

Legend(右下)shall=守る線:what-if+人間承認/audience固定/骨・細部・影/Exit on Page 1will=協力の線:監査協力/説明資料/改善提案Contact(最初の行):infra@hoshiori.co.jp / #infra-opsRunbook一行目:誰/いつ/どこで/何を/なぜ
0|プロローグ:真夜中の“成人式”ふたたび
午前01:58。GitHub Actions のログが白の上に黒で均等に並び、what-if の行だけが淡い青の帯で強調されていた。律斗はヘッドホンを耳に掛けず首に置き、椅子の前脚だけでバランスを取る癖で画面に寄る。
ERROR: The specified module could not be restored:
br:corp/network:v2.3.1
Reason: 404 (Not Found)
main.bicep の中で、module の行だけが、昨夜までの落ち着きを失っていた。module vnet 'br:corp/network:v2.3.1' = { … }。消えたのはコードではない。参照先だ。
Runbook-INV-01(調査開始)誰:Infra(律斗)/いつ:01:58/どこで:GitHub Actions(prd)/何を:module restore 失敗/なぜ:br:corp/network:v2.3.1 が 404
「名探偵Bicepの出番だな」
やまにゃんが背もたれの上で丸くなり、尻尾(USB-C)が光を受けて短くとんと揺れた。合図はいつも短い。
1|現場検証:白い廊下と落ちたパンくず
1-1 Actions の足跡
checkout(深さ fetch-depth: 1)
bicep restore → 失敗
bicep build(--no-restore なし)
what-if スキップ(差分なし判定)
deploy は 止まった(承認ゲート手前)
「テンポは守られた。承認の拍がゲートの前に置いてある」——律斗はそう言って、テンポを BPM 80 に落とした。夜は拍を詰めない。
1-2 物証A:bicepconfig.json
{
"moduleAliases": {
"br": {
"corp": {
"registry": "acrhoshiori.azurecr.io",
"modulePath": "bicep"
}
}
},
"experimentalFeaturesEnabled": {
"symbolicNameCodegen": true,
"moduleAliases": true
}
}
「別名は corp。昨夜と同じ」りなが右下の Legend に薄紫で “Alias” を書き足す。
1-3 物証B:レジストリ(ACR)
az acr repository show-tags \
--name acrhoshiori \
--repository bicep/network \
--output table
返ってきたタグの一覧に、v2.3.1 がない。v2.3.0 と v2.4.0-rc1 はある。「間が抜けてる」と蓮斗。「味見で言えば、塩の瓶と砂糖の瓶のあいだに何もない棚」
1-4 物証C:ACR の保持ポリシー
未参照アーティファクトの自動削除:30日
例外設定:latest のみ
悠真が眉を寄せる。「latest 以外は落ちる。v2.3.1 は未参照と判定された可能性」
「latest は人を惑わせる」と律斗。「消えた module の第一容疑者は保持ポリシー」
2|容疑者の列:誰が module を消したのか
容疑者A:ACR の保持ポリシー(未参照タグの削除)
容疑者B:bicepconfig.json の alias 改変(corp→corpA)
容疑者C:Template Spec へ移行途中の削除(ts: リソースの廃止)
容疑者D:CI の shallow checkout(fetch-depth: 1 によりサブモジュール消失)
容疑者E:大文字小文字(Windowsで通り Linux で落ちる)
容疑者F:人(意図なき bicep publish ミス)
あやのが薄紫で脚注を書く。shall=守る線(保持設定・RBAC・記録)/will=協力の線(監査・説明)。
3|取り調べ:alias と registry の隙間
3-1 エイリアスのずれ
Pull Request の履歴に、目立たない一行。
- "registry": "acrhoshiori.azurecr.io",
+ "registry": "acrhoshiori.azurecr.io/",
末尾スラッシュ。「URL 正規化で問題は出にくいが、別のところに影響が出ることがある」叶多が欄干の図に小さな欠けを描き入れる。「手すりの段差。人は越えられるが、ツールは落ちることがある」
3-2 Template Spec の影
別ブランチに、ts: 参照に置き換える検証コード。
module vnet 'ts:/subscriptions/xxxx/resourceGroups/rg-ts/providers/Microsoft.Resources/templateSpecs/network/versions/2.3.1' = {
name: 'net'
params: { ... }
}
Template Spec リソースはReader がついていない。RBAC 不足。「鍵は置かないが、扉は開けないと渡れない」と律斗。RBACはshall。
4|現場検証Ⅱ:bicep restore の裏で起きていること
bicep restore は .bicep/registry のローカルキャッシュに落とす。CI のステップに
- name: Restore modules
run: bicep restore main.bicep
があるが、キャッシュは actions/cache@v3 で key を hashFiles('**/bicepconfig.json') にしていた。module 参照の hash は鍵に入っていない。奏多が指でBPMを60に落とす。「テンポは先に決めた。次は鍵(cache key)を正しく」
- name: Cache bicep module restore
uses: actions/cache@v3
with:
path: ~/.bicep/registry
key: bicep-registry-${{ hashFiles('**/*.bicep', '**/bicepconfig.json') }}
5|推理の収束:消失の三段重ね
保持ポリシーが v2.3.1 を削除(未参照扱い)
CI の shallow/cache key 不備でローカルキャッシュも空
alias の末尾スラッシュで復元 URLが微妙に不一致 → 404
「三段です」とりな。「一段なら偶然、三段なら設計」
ふみかは黒板に短く書く。
広報(連絡先:press@…)。module 参照 v2.3.1 は復元。保持と alias を是正。Runbookは朝に。
夜は比喩に過酷。事実だけ置いて、朝に続きを。
6|復元計画:墓場からの publish
6-1 旧ビルドアーティファクトの発掘(影)
悠真が影の棚から先月の build artifacts を取り出す。network-2.3.1.json が ZIP に入っている。「骨が残っている。砂から水を戻すのに近いけれど、料理はできる」
6-2 bicep publish の儀式
律斗が命名規約に従って復刻を publish。
bicep publish ./modules/network/2.3.1/main.bicep \
--target br:acrhoshiori.azurecr.io/bicep/network:v2.3.1
署名は人の指、印影は差分ID に紐づけ。shall。
6-3 alias の是正・テスト
bicepconfig.json の 末尾スラッシュを削除、bicep restore を流す。200。Template Spec 側は RBAC をReader 付与、ts: 参照の統一計画は別紙(will)。
7|再発防止 Runbook(Exit on Page 1)
Runbook-MOD-02 再発防止(Exit on Page 1)誰:Infra(律斗)/いつ:2025-09-20/どこで:ACR+CI/何を:module 供給線の保全/なぜ:再発防止手順: Publish パイプラインを分離(bicep publish は手動承認) タグ固定は vX.Y.Z+digest(可能なら) 保持ポリシー:最近 N 版+参照中は除外 Cache key に **/*.bicep+bicepconfig.json alias 検出の lint ルール(末尾スラッシュ禁止) what-if+人間承認を必須ゲート Template Spec へ統一する場合はRBAC(Reader)の付与計画を脚注Exit:復刻不可なら版上げ(v2.3.2)+互換モジュールを24hで publish
あやのが脚注にArtifactory/ACR Governanceのshallを薄紫で追記。willの欄に「監査協力」を置く。
8|副読本:二つの参照方式を持つ理由(br と ts)
りながホワイトボードに二本の線を引く。
br:(Bicep Registry)——軽く、速い。タグ/ダイジェストで pin。ACR の保持が要。
ts:(Template Spec)——RBAC/バージョン履歴がAzure Resourceとして残り、審査に強い。
「shall はどちらにも置ける。鍵(Key EU)、報告72h。will の監査協力は ts が得意」ふみかが補足する。「広報の十秒に出すのはbr の話じゃなく場所。最初の行に連絡先。右下にLegend」
9|朝の比喩:谷は潮が引くように
復旧の朝、ふみかは比喩を一行だけ足した。
広報(連絡先:press@…)。昨夜の**「谷」は潮が引くように退きました。現在は凪**。脚注に保持/復刻/承認線。
りなの指がLegendをなぞる。「比喩は礼儀の上に。礼儀なき比喩は人を傷つける。人ではなく現象に当てる」
10|エピローグ:名探偵Bicepの締め
会議室の空気が、緑の丸の一声で一段落ちた。律斗は bicepconfig.json を閉じ、main.bicep の module 行に視線を戻す。br:corp/network:v2.3.1 は、ふたたび落ち着いた字面になっていた。
「差分は人間に見せると丸く収まる。 テンポは先に決めると事故らない。 “破壊的変更”は高座に出すと笑えるが、本番で出すと泣ける」
扇子は持たないが、見得は切った。やまにゃんが背もたれから降り、棚の前で一拍ためて――ちりん。眠れましたのメールが同時に届いていた。
短い文が長い約束になった音だ。Legendは右下に。連絡先は最初の行に。Exitは最初のページに。そして、名探偵Bicepは、また次の夜のためにBPMを60に落として帰る。





コメント