Guidant AI · FR-057 需求討論稿

FR-057 · Detection Tool Integration — OpenSCAP

OpenSCAP 掃描工具接入:SSH 連線型態

在 FR-056 檢測工具整合平台上新增第二個工具 OpenSCAP(CIS / STIG 組態合規稽核),並藉此開出 connector 架構的第三種連線型態 SSH。Agent 維持 Docker 形態不變,作為掃描發起端遠端掃描站內目標主機。

FR-056 續作 3 子需求 × 8 子任務 跨 BE / FE / evidence-agent D1–D7 已拍板
§1

設計前提:為什麼是 SSH 遠端掃描

這一節回答討論過程中的兩個核心疑問:「OpenSCAP 有沒有 API?」「目標主機要裝東西是正常的嗎?」——兩者都已查證定案。

OpenSCAP 沒有 API,是物理限制不是設計選擇

oscap 是純 CLI——無 server、無 daemon。組態稽核要讀目標主機系統內部(設定檔 / 套件庫 / sysctl / 稽核規則),必須以登入身分在目標 OS 上原生執行。「遠端讀主機內部=需要登入身分」全業界一致:連 OpenVAS 做授權掃描(authenticated scan)一樣要存目標 SSH 憑證。

oscap-ssh 是官方遠端模式

發起端 SSH 登入目標 → 推送 content → 在目標上執行目標自己的 oscap → 把報告拉回。Red Hat Satellite / Foreman 大規模採用同一模式。目標主機需一次性安裝 openscap-scanner(幾 MB CLI、非常駐、不開 port、不吃資源)——這是選用 OpenSCAP 的隨附條件。

Nessus / Qualys 為何能零安裝

它們自造檢查引擎(商業核心資產):SSH 登入後只跑通用指令,把原始輸出拉回 scanner 端自行判定。OpenSCAP 開源專案沒有這一層。真正零安裝的組態稽核是商用掃描器的能力,未來接 Nessus 時自然取得。

Agent 維持 Docker,角色是站點調度器

Agent container 只需 openssh-client + oscap-ssh 腳本(Dockerfile 加一行 apt);掃描引擎在各目標主機上。一站一個 Agent、掃站內 N 台目標——與 Rapid7 / Qualys 官方 Containerized Scan Engine 同一模型,部署形態零改動。

%%{init: {'theme':'base','themeVariables':{'primaryColor':'#E2F0F1','primaryTextColor':'#14201F','primaryBorderColor':'#0E7C86','secondaryColor':'#EEF2F3','secondaryTextColor':'#14201F','tertiaryColor':'#FBFCFC','tertiaryTextColor':'#14201F','lineColor':'#4A5A5C','textColor':'#14201F','mainBkg':'#E2F0F1','nodeBorder':'#0E7C86','nodeTextColor':'#14201F','edgeLabelBackground':'#FBFCFC','titleColor':'#14201F','clusterBkg':'#FBFCFC','clusterBorder':'#E4EAEB','actorBkg':'#E2F0F1','actorTextColor':'#14201F','actorBorder':'#0E7C86','actorLineColor':'#C7D1D2','signalColor':'#4A5A5C','signalTextColor':'#14201F','labelBoxBkgColor':'#EEF2F3','labelBoxBorderColor':'#C7D1D2','labelTextColor':'#14201F','loopTextColor':'#14201F','noteBkgColor':'#F6EBD5','noteTextColor':'#14201F','noteBorderColor':'#9C6B12','activationBkgColor':'#EEF2F3','activationBorderColor':'#C7D1D2','sequenceNumberColor':'#FFFFFF'}}}%%
graph LR
  subgraph cloud["雲端 Guidant AI"]
    CFG["租戶工具設定
(SSH 憑證加密存放)"] TASK["任務: 檢測工具執行
(hosts + profile)"] EV["job_evidences
(source=DETECTION_TOOL)"] end subgraph site["客戶站點"] AGENT["evidence-agent
(Docker, 掃描發起端)"] H1["目標主機 1
openscap-scanner + sshd"] H2["目標主機 2
openscap-scanner + sshd"] H3["目標主機 N ..."] end TASK -->|"心跳派工 (mTLS)
含解密憑證"| AGENT AGENT -->|"oscap-ssh"| H1 AGENT -->|"oscap-ssh"| H2 AGENT -->|"oscap-ssh"| H3 H1 -->|"HTML 報告"| AGENT H2 -->|"HTML 報告"| AGENT AGENT -->|"result (多檔)"| EV CFG -.->|"派工時解密下發"| TASK classDef cloudBox fill:#E2F0F1,stroke:#0E7C86,color:#14201F; classDef siteBox fill:#FFFFFF,stroke:#C7D1D2,color:#14201F; classDef hostBox fill:#E4F1EA,stroke:#2E7D5B,color:#14201F; class CFG,TASK,EV cloudBox; class AGENT siteBox; class H1,H2,H3 hostBox; style cloud fill:#FBFCFC,stroke:#E4EAEB,color:#4A5A5C; style site fill:#FBFCFC,stroke:#E4EAEB,color:#4A5A5C;
架構總覽:Agent(Docker)是發起端,掃描引擎在各目標主機;憑證雲端保管、派工時下發用完即丟
§2

端到端流程

%%{init: {'theme':'base','themeVariables':{'primaryColor':'#E2F0F1','primaryTextColor':'#14201F','primaryBorderColor':'#0E7C86','secondaryColor':'#EEF2F3','secondaryTextColor':'#14201F','tertiaryColor':'#FBFCFC','tertiaryTextColor':'#14201F','lineColor':'#4A5A5C','textColor':'#14201F','mainBkg':'#E2F0F1','nodeBorder':'#0E7C86','nodeTextColor':'#14201F','edgeLabelBackground':'#FBFCFC','titleColor':'#14201F','clusterBkg':'#FBFCFC','clusterBorder':'#E4EAEB','actorBkg':'#E2F0F1','actorTextColor':'#14201F','actorBorder':'#0E7C86','actorLineColor':'#C7D1D2','signalColor':'#4A5A5C','signalTextColor':'#14201F','labelBoxBkgColor':'#EEF2F3','labelBoxBorderColor':'#C7D1D2','labelTextColor':'#14201F','loopTextColor':'#14201F','noteBkgColor':'#F6EBD5','noteTextColor':'#14201F','noteBorderColor':'#9C6B12','activationBkgColor':'#EEF2F3','activationBorderColor':'#C7D1D2','sequenceNumberColor':'#FFFFFF'}}}%%
sequenceDiagram
  participant U as 管理員 / 稽核員
  participant BE as 雲端 BE
  participant AG as Agent (Docker)
  participant T as 目標主機

  U->>BE: 設定 OpenSCAP(帳號 + 金鑰/密碼)
  BE->>BE: 憑證 Fernet 加密存放
  U->>BE: 測試連線
  BE->>AG: probe 派工
  AG->>T: SSH 認證 + 檢查 oscap / SSG content
  AG-->>BE: 四段檢查結果(缺什麼報什麼)
  U->>BE: 任務開始執行(hosts + profile)
  AG->>BE: 心跳
  BE-->>AG: pending_tasks(含解密憑證, mTLS)
  loop 逐台目標
    AG->>T: oscap-ssh xccdf eval --profile ... --report ...
    T->>T: 在目標 OS 上原生執行 oscap
    T-->>AG: HTML 報告 + stdout 統計
  end
  AG->>BE: result(upload_uids 多檔 + summary 加總)
  BE->>AG: 逐檔 mTLS GET /blob/{uid}
  BE->>BE: 逐檔寫 job_evidences + 通知負責人
      
時序:probe 前提檢查 → 心跳領工 → 逐台掃描 → 多檔回收
§3

決策定案 D1–D7

七項決策皆已拍板。設計立場:不自創做法,逐項對齊業界標準(Tenable 官方文件為主要參照)。

D1 · 已拍板 — SSH 憑證放租戶工具設定層(一組共用稽核帳號)

Tenable《Credentialed Checks on Linux》官方建議原文即此模式:每台目標主機建立同名專用掃描帳號。完全沿用 tenant_detection_tool_configs 加密鏈 + FR-056 D9 派工下發,零新表零新機制。任務層帶憑證(明文落 DB)排除;host inventory 表(每台各自憑證)列未來,資料模型可平滑升級。

D2 · 已拍板 — 密碼 / SSH 私鑰二擇一,推薦金鑰 + sudo 提權選項

Tenable 同款建議:金鑰更安全、私鑰只存 scanner 端、可隨時在主機端撤銷公鑰。完整掃描需 root 級讀取而企業普遍禁 root 遠端登入 → use_sudo 布林(oscap-ssh --sudo),「一般帳號 + sudo 提權」是業界標準模式。

D3 · 已拍板 — SCAP content 用目標主機自帶的 SSG

目標裝 scap-security-guide 套件,content 在 /usr/share/xml/scap/ssg/content/,天然匹配該機 OS 版本。任務參數=content 路徑(預設慣例路徑可改)+ profile(常用 CIS/STIG 下拉 + 自由輸入)。平台統一管理 content 列未來(跨發行版版本矩陣維護成本高、錯配掃出整片 notapplicable)。

D4 · 已拍板 — 證據=HTML 原樣上傳,summary 從 stdout 解析

oscap 官方人讀格式就是 HTML(無原生 PDF)。不轉 PDF——LibreOffice 轉複雜 HTML 排版易爛,轉壞的報告比原檔更難看。ARF XML 結構化 findings 留未來 FR(同 FR-056 D4「第一版只存報告」邏輯)。

D5 · 已拍板 — 多目標逐台掃、每台一個證據檔

檔名含主機名、summary 加總,不硬拼單一 HTML。⚠️ 牽動回收鏈:現況 result_ref.upload_uid 是單數,需擴成多檔陣列(獨立子需求 FR-057.3,向下相容 OpenVAS 單檔路徑)。

D6 · 已拍板 — 部署前提:設定頁內建說明 + 準備腳本 + probe 實地檢查

detection_toolssetup_guide 欄位,設定頁渲染前提清單 + 一鍵複製的目標主機準備腳本(裝套件 / 建帳號 / 佈公鑰 / sudoers)。probe 測試連線時 SSH 上去實地驗 oscap 與 SSG content 存在性——錯誤分類四段:連不上 / 認證失敗 / 缺 oscap / 缺 content。

D7 · 已拍板 — 第一版不做

Push 模式(目標自掃回報,Foreman 式——與「按開始→即時派工」任務模型衝突);host inventory 表;ARF findings 解析;content 平台統一管理。

§4

租戶設定與任務參數

4.1 租戶設定欄位(config_field_schema)

keylabeltyperequiredsecret說明
username稽核帳號text必填各目標主機同名帳號(業界慣例)
auth_method認證方式select必填password / private_key,驅動下兩欄條件顯示
passwordSSH 密碼password條件auth_method=password 時必填
private_keySSH 私鑰textarea(新型態)條件auth_method=private_key 時必填(OpenSSH PEM)
ssh_portSSH 連接埠number預設 22
use_sudo使用 sudo 提權boolean預設 true(完整掃描建議)

secret 欄位進 credentials_encrypted 密文;其餘進 field_values。FE 需擴的欄位型態:textarea條件顯示(auth_method 切換)。

4.2 任務參數(param_schema)

keylabeltyperequired說明
hosts掃描目標text必填逗號/空白分隔多台(同 OpenVAS 慣例,connector 邊界正規化)
content_pathSCAP content 路徑text預設 SSG 慣例路徑,可填完整檔案路徑
profile掃描 Profileselect_or_text(新型態)必填下拉常用(CIS L1/L2 Server、STIG)+ 自由輸入 xccdf profile id
timeout_sec逾時秒數number預設 3600,逐台計

4.3 目標主機準備腳本(setup_guide 內容示意)

# 每台目標主機執行一次(Ubuntu/Debian;RHEL 系換 dnf + scap-security-guide)
sudo apt install -y openscap-scanner ssg-base ssg-debderived
sudo useradd -m -s /bin/bash audit-scan
echo '<公鑰>' | sudo tee -a /home/audit-scan/.ssh/authorized_keys
echo 'audit-scan ALL=(root) NOPASSWD: /usr/bin/oscap' | sudo tee /etc/sudoers.d/audit-scan
§5

Agent Connector 設計

新增 core/task_executor_connectors/openscap.py,實作既有 DetectionConnector 介面(run / probe / cancel_event),factory 加 4: "openscap",Dockerfile 加 openssh-client + openscap-utils

run() — 逐台掃描

解析 hosts → 逐台執行 oscap-ssh [--sudo] user@host port xccdf eval --profile … --report … → 收 HTML bytes + stdout 統計 → 回多檔結果。私鑰寫入記憶體型暫存(0600),掃完即刪不落地。

probe() — 四段前提檢查

SSH 連線 → 認證 → command -v oscap → SSG content 存在性。缺什麼在錯誤訊息明確分類,與 run() 共用連線參數解析(單一真相,同 OpenVAS 模式)。

exit code 語意(易踩雷)

0=全 pass;2有 fail 但掃描成功(報告有效,最常見結果);1=執行錯誤。2 絕不可誤判為失敗。

summary(stdout 解析)

{"findings": fail數, "pass": n, "fail": n, "notapplicable": n, "error": n, "hosts_scanned": n}。解析失敗不拖垮派工(證據到手 summary 可缺,同 OpenVAS 原則)。

§6

多檔證據回收鏈擴充

D5 的連鎖工程:一任務掃 N 台=N 份報告,但現況 result 鏈是單檔設計。擴充需跨 agent 與 BE 兩端,且必須向下相容 OpenVAS 單檔路徑。

現況擴充
Agent task_executorresult_ref: {"upload_uid": x} 單數逐檔上傳 blob → {"upload_uids": [{"uid","filename"}, …]};保留單數 key 讀取相容
BE detection_result_handler取單檔 mTLS GET /blob/{uid} 寫一筆證據upload_uids(fallback upload_uid)逐檔取回逐檔寫入;單檔失敗記 warning 續處理其餘(部分成功優於全失敗)

檔名慣例:OpenSCAP掃描報告_<host>_<日期>.html(content_type=text/html)。

§7

拆分:3 子需求 × 8 子任務

依賴鏈:.1 是地基;.2 / .3 可並行(.3 用假多檔即可測,不等 openscap connector)。每子任務=一張 Notion 子卡。

%%{init: {'theme':'base','themeVariables':{'primaryColor':'#E2F0F1','primaryTextColor':'#14201F','primaryBorderColor':'#0E7C86','secondaryColor':'#EEF2F3','secondaryTextColor':'#14201F','tertiaryColor':'#FBFCFC','tertiaryTextColor':'#14201F','lineColor':'#4A5A5C','textColor':'#14201F','mainBkg':'#E2F0F1','nodeBorder':'#0E7C86','nodeTextColor':'#14201F','edgeLabelBackground':'#FBFCFC','titleColor':'#14201F','clusterBkg':'#FBFCFC','clusterBorder':'#E4EAEB','actorBkg':'#E2F0F1','actorTextColor':'#14201F','actorBorder':'#0E7C86','actorLineColor':'#C7D1D2','signalColor':'#4A5A5C','signalTextColor':'#14201F','labelBoxBkgColor':'#EEF2F3','labelBoxBorderColor':'#C7D1D2','labelTextColor':'#14201F','loopTextColor':'#14201F','noteBkgColor':'#F6EBD5','noteTextColor':'#14201F','noteBorderColor':'#9C6B12','activationBkgColor':'#EEF2F3','activationBorderColor':'#C7D1D2','sequenceNumberColor':'#FFFFFF'}}}%%
graph LR
  A["FR-057.1
BE 地基
SSH 型態 + seed + FE 欄位型態"] --> B["FR-057.2
Agent OpenSCAP connector"] A --> C["FR-057.3
多檔證據回收鏈"] B -.->|"端到端驗收匯合"| D["E2E 驗收"] C -.-> D classDef base fill:#E2F0F1,stroke:#0E7C86,color:#14201F; classDef par fill:#E4F1EA,stroke:#2E7D5B,color:#14201F; classDef fin fill:#F6EBD5,stroke:#9C6B12,color:#14201F; class A base; class B,C par; class D fin;
依賴圖:.1 完成後 .2 / .3 並行

FR-057.1 BE:SSH 型態 + OpenSCAP 目錄與設定頁(依賴:無)

#子任務驗收依賴Repo
T-1.1migration:seed openscap(SSH 型態 + config_field_schema)+ param_schema + setup_guide 欄位與內容三環境可套;設定頁清單出現 OpenSCAP(available)BE
T-1.2FE 設定頁欄位型態擴充:textarea / 條件顯示 / setup_guide 渲染 + 腳本複製OpenSCAP 設定頁可完整填寫送出,憑證密文落庫T-1.1FE
T-1.3FE 任務參數型態擴充:select_or_text(profile)任務可選 OpenSCAP 並填參數發佈T-1.1FE

FR-057.2 Agent:OpenSCAP connector(依賴:FR-057.1)

#子任務驗收依賴Repo
T-2.1Dockerfile + factory 註冊 + connector 骨架(SSH 參數解析、私鑰暫存管理)image build 過;unit test 綠T-1.1agent
T-2.2run():逐台 oscap-ssh + HTML 收取 + stdout summary + exit code 2 處理 + 取消/逾時手塞派工 → 掃真實主機 → 報告回收全鏈通T-2.1agent
T-2.3probe():連線/認證/oscap/SSG 四段檢查與錯誤分類四種缺件情境回清楚訊息T-2.1agent

FR-057.3 多檔證據回收鏈(依賴:FR-057.1,可與 .2 並行)

#子任務驗收依賴Repo
T-3.1Agent:task_executor 多檔上傳 + result_ref.upload_uids(向下相容單數)多檔回報結構正確;OpenVAS 單檔迴歸綠agent
T-3.2BE:detection_result_handler 多檔迴圈取回 + 逐檔寫證據 + 部分失敗續處理多檔證據逐檔入池;單檔 fallback 迴歸綠T-3.1BE
§8

端到端驗收

#情境預期
1管理員設定 OpenSCAP(金鑰認證)→ 測試連線probe 通過(含 oscap / SSG 前提檢查)
2任務選 OpenSCAP、2 台 hosts + CIS profile → 開始執行每台各一份 HTML 報告進證據池,summary 加總正確
3任一台缺 openscap-scannerprobe / 掃描回明確分類錯誤(非神祕失敗)
4OpenVAS 既有全鏈迴歸factory / result 單檔路徑 / FE 動態渲染不受影響