FR-175 機制問答首腦:交接現況(STATE)

這份是 living 檔:每棒就地改,只描述「此刻」。每一棒做了什麼看同資料夾的 fr175-LOG.md。

項目 值
最後更新 2026-11-03(FR-172 結案時改寫「執行流程」頁為主系統與 Agent 三張循序圖;下一棒從「密碼」討論開始)
問答頁 qa/mechanism-qa.html;線上 https://claude.ai/artifact/AmUhtjZVptzoqExGEUhjhx (第 29 版:執行流程改寫,2026-11-03)
branch BE feature/FR-172(session 中途工作樹被別的 session 切過來,本區 commit 都在這);全部未 push
Notion 無卡。本區是問答與整理,不是實作案
§1

🧭 這個角色是什麼

決策者與 PM 會連續問「某件事是怎麼運作的」。這個 session 負責回答並整理成問答頁,每個說法要對回程式碼那一行或三台主機的實查結果。範圍不限線上更新:安裝、發版、主機與容器、密碼、設定檔都問過,之後問到別的機制也放這裡。

修程式、出包、發布、改各案 STATE/LOG 都不是這裡的事。 發現的問題寫進問答頁「發現的問題」並告訴決策者,由各案首腦開卡。

§2

權限與界線

  • 可以做:讀任何 repo、grep、讀本機 DB(SELECT);ssh 唯讀查 188/189/190 與 Agent(docker ps/inspect/logs/exec … cat、ss、systemctl status、journalctl);查更新站 D1(wrangler d1 execute --remote 只下 SELECT);改並 commit 本資料夾的檔與問答頁;發布問答頁到線上網址。
  • 不要做:改程式、出包、發布更新站、改其他案的 STATE/LOG 或 README/FINAL-SPEC、寫入任何主機或資料庫、碰 188 STG/189 POC 的狀態、push。
  • 讀設定檔:主機上的 .env、guidant.env 只准列鍵名(sed -n 's/^\([A-Z_][A-Z0-9_]*\)=.*/\1/p'),不讀值;比對兩台密碼是否相同只比雜湊前幾碼。
  • 回答紀律:一題一答,先結論再事實;查不到就說查不到;有問題用「問題、建議、理由」三段;白話、繁體中文。決策者會邊問邊插話:說「先別寫」就只回答不改文件,問完一輪說「更新文件」才一次寫。
  • 不要先動手:交接讀完回報「已讀完,可以開始問」就停,不先去查別的。
§3

問答頁現況

維護做法(新增一題、畫圖、發布、權限、驗證)全在 維護手冊,這裡只列現況。

題 內容
Q6 +2 補問 安裝八步與 root;公鑰為何在 /etc/guidant/;安裝目錄樹狀圖與 189、190 對照
Q7 +3 補問 密碼與金鑰;.env 密碼全表、業務帳號=cm_app;加密 .env 擋不住什麼與三層建議;docker 身分、rootless 與容器內非 root、入侵處置
Q21 docker compose 十個服務、.env 27 鍵、guidant.env 39 鍵、掛載、優先序與陷阱
Q8 發版流程:現行三階段、CI 五 stage、實況(1.27.x 是 188 手跑出包);改版後 FR-172 Agent 分開出版、FR-173 三條 CI 與 Vault 簽章;四張圖
Q9、Q11 +2、Q12 +1 打一次密碼;預簽網址與長相;主版號兩道門與 2.0 授權模式
執行流程 +1 補問 升級循序圖、時間軸、逐步說明;升級觸發機制(更新單、systemd 監看、升級腳本組成、為何不用升級容器)
Q13~Q19 複製資料庫、快照、停什麼(Q15 +1 補問:資料庫停兩次)、清理、log、進度檔、健康檢查(Q19 已更正:不登入、驗 401)
Q5·Q20 備份現況
待討論 9 條
發現的問題 13 條;最優先:升級失敗時錯誤原文進不了系統(另開卡,出貨前修)

決策者對問答頁的要求(不要改回去):頁面固定亮色;時序圖用 sequenceDiagram+autonumber+階段橫條;目錄結構用樹狀文字圖;主欄 1180px;標題要專業不要口語;補問不分頁;Q8「現況打折」段不放;Q18 維持原文;本機要能直接開、圖可點擊放大。

§4

已查實事實(回答時可直接用,不必重查)

  1. 「有沒有新版」只看版號:更新站、主系統、主機預檢都是 semver 逐段比數字;同版號重編不算新版;guidantai upgrade --force 可同版重跑。
  2. 升級中畫面:前門 guidant-fe 全程不停;探不到 /api/1.0/version 就送 maintenance.html;維護頁每 3 秒讀 /upgrade-progress.json,nginx 直接 alias 到主機進度檔。
  3. 單支 API 502 不跳維護頁:只有更新中心在升級中、輪詢拿到閘道錯誤才整頁 reload。
  4. 主機接單:guidant-upgrade-order.path 監看 orders/,觸發 .service 以 root 跑 guidantai upgrade --from-order。
  5. 升級 log:逐行輸出在 journal;migrate 另落 log/upgrade-migrate-<單號>.log。
  6. system_logs:換接後每分鐘排程補寫 6239~6247+6248,只寫一次。
  7. 診斷包:收 24 小時 system_logs、最近三支 upgrade/install log、last-switch.json;只收 guidant.env(遮罩),不收 .env。
  8. Agent 升級結果回報更新站:1.27.9 起代送,真環境未驗。
  9. Agent 檢測 Profile:心跳帶清單,1.27.10 起多帶 tool、name。
  10. draining 是兩件事:worker 不撿新單(app/background_job/worker_loop.py:78)+Agent 不派新任務(core/plugins/_agent_commands.py:34);後端順手查檔不監看;不擋 API。
  11. 更新單:orders/<單號>.json,主機開跑前就刪;單上無路徑無指令,主機只用版號在 incoming/ 拼路徑重驗。
  12. 進度檔重置時機:每次開始升級,以及每次新包下載完或離線上傳完的自動預檢(scripts/installer/lib/upgrade_order.sh:251)。歷史在資料庫 product_update_jobs,更新中心有「更新紀錄」表。
  13. 資料庫停兩次:第 3 步停、cp -a 冷複製;第 4 步 env GUIDANT_PGDATA_DIR=…pgdata-next 臨時覆寫 compose 掛載、反查後跑 migration;第 6 步再停、先改 .env 再改名回 pgdata。
  14. 健康檢查:不登入;/version 版號、隨機帳號登入驗 401 LOGIN_401001、三支 menu/status 不帶 token 驗 401(upgrade_health.sh:33)。不驗業務資料。
  15. 失敗原因去向:system_logs 只有預寫一句+退出碼;受檢容器 docker logs 隨容器刪除消失;upgrade_apply_on_copy.sh:107、upgrade_rollback.sh:75/:84 丟 /dev/null。
  16. 第三方映像:隨包出貨、build 機釘 digest、出包有弱點放行門;已升過兩次(6a25bfe5b、30be617e8);PostgreSQL 16 支援到 2028-11。
  17. 發版實況:1.27.x 是首腦在 188 手跑 /home/jedi/fr167-build-<版>.sh(build_bundle.sh --skip-prod-key-check)+本機 publish-<版>.sh 用測試章簽;CI package 段未跑過正式出版。
  18. FR-172/173 進度(11-02):FR-172 B-0/U-1/U-2/A-0/H-1/H-2 已做,在 ws-CM-3401 未合回;Vault 192.168.50.172 已架未接 GitLab;FR-173 未開卡。
  19. api_logs_old/system_logs_old:188、189 有(189 共 206 MB),190 無;決策者裁刪,建議寫 migration;本區未執行任何寫入。
  20. guidantai 一律要 sudo:讀 600 設定檔+操作 docker;決策者同意維持。
  21. 出貨包內容(現行):install.sh 與輔助腳本、docker-compose.yml、images/(自家 be/fe/init、分類服務、postgres、redis、seaweedfs、bugsink 全部 docker save)、vulndb/、agent/、docs/、sbom/(scripts/build/build_bundle.sh 檔頭)。FR-172 後主系統包拿掉 agent/。
§5

🔴 下一棒:密碼討論的起點

決策者 11-02 說「想來討論一下密碼的問題」,還沒開始問。問到什麼答什麼,不要先寫文件。

客戶主機上的密碼

密碼/金鑰 怎麼產生 放哪 每台不同?
資料庫 cmmgr、cm_app,Redis 四組,物件儲存,分類服務 token,錯誤追蹤站 Django 金鑰與庫密碼 安裝時 gen_pw:openssl rand -base64 24 去掉 /+= 取 24 字(install.sh:204);客戶可用設定檔自帶 .env 明文,600 root 是
JWT、三把資料欄位加密金鑰 gen_key:openssl rand -base64 32(install.sh:210) guidant.env 明文,600 root 是
系統管理員 admin 登入密碼 有填 GUIDANT_ROOT_ADMIN_PASSWORD 就轉 bcrypt;沒填用 scripts/init/06-admin.sql 內建預設雜湊 資料庫使用者表 沒填時每台相同
錯誤追蹤站管理員 出包時烙進包:CI 變數 GUIDANT_BUGSINK_ADMIN_PASSWORD → gen_bugsink_admin_bake.sh → bugsink-admin.secret 主機 /srv/guidant-ai/bugsink-admin.secret,600 同一版包的所有客戶相同

開始前先跟決策者對齊:FR-173 design §1 D8 寫「客戶主機預設密碼(DB、Redis、Bugsink 每台同組)」,與現況不符。實查 DB、Redis 每台隨機;真正每台相同的是預設 admin 雜湊與錯誤追蹤站管理員。

已知結論與缺口

  • 加密 .env 擋不住 root 與磁碟;建議三層:手冊要求全碟加密、密碼改掛檔案、有 TPM2 才用 systemd-creds(問答頁 Q7 補問 2)。
  • sudo guidantai rotate-credentials 換資料庫兩帳號與 Redis;不換 JWT、三把加密金鑰、錯誤追蹤站、物件儲存。
  • 首次登入強制改密碼:jedi-iam 有 need_change_password(jedi_iam/app/service/login_service.py:66),還沒查預設 admin 是否被標成必改。
  • 遮罩:診斷包、進度檔、log 遮 PASSWORD=、SECRET=、TOKEN=;錯誤追蹤 SDK 堆疊區域變數是已知盲區。
  • 不給客戶印明文密碼的 CLI:guidant credentials 已移除。

還沒查、可能會被問到:預設 admin 有沒有強制首次改密碼;rotate-credentials 改兩個檔是否原子;物件儲存 s3.json 與 .env 兩份怎麼保持一致;Agent 本機管理員密碼怎麼產生(189 兩台 Agent 都提示尚未設定);密碼複雜度與過期政策在哪設。

§6

讀序

  1. 本檔,特別是「下一棒:密碼討論的起點」。
  2. README 的結論與需求討論紀錄。
  3. 問答頁 Q7(含三則補問)與 Q21:本機開 qa/mechanism-qa.html#q7,或線上網址加 #q7。
  4. 要改問答頁前讀 維護手冊。
  5. 有需要再讀 docs/features/FR-173-2611-release-pipeline/design.md §1 D8、scripts/installer/install.sh:200~215、scripts/init/06-admin.sql、scripts/build/gen_bugsink_admin_bake.sh。