跳轉到主要內容
文件運行人工審批

人工審批

在任意步驟加 manual_approval 門控:App 內、郵件、API 三條通道批覆,數值可編輯,逾時自動拒絕。

manual_approval 把「等某個人確認再繼續」編碼成步驟修飾符:執行到達設定了它的步驟時暫停,批准後才執行步驟本體。批准之前,系統不會執行該步驟及其下游的任何動作。

配置

yaml
  - step: apply_changes
    agent: executor
    input: "把已审核的变更应用到线上"
    manual_approval:
      enabled: true
      approvers:            # 平台用户 ID;留空 = 发起人 / 有执行权限者可批
        - "usr_team_lead"
      timeout: 86400        # 秒;24 小时无人批复自动拒绝
      approval_message: |
        请确认是否应用本轮变更。
        拒绝或超时不会做任何线上修改。

它可以掛在任意步驟上(agent、code、sub_workflow 等),也常用於一個只列印狀態的輕量 code 步驟,作為純粹的「人工閘門」。

參數

字段類型默認說明
enabledboolean是否啟用審批門控(必填)
approversstring[][]指定審批人(平台使用者 ID)。非空時只有名單內的使用者與管理員能批復——執行發起人也不行,天然滿足職責分離;留空時執行發起人或對該工作流有執行權限的協作者都可批復
timeoutlong3600逾時秒數。到點無人批復則自動拒絕,狀態標 TIMED_OUT
approval_messagestringnull展示給審批人的說明,出現在審批卡片與通知郵件裡
reviewable_actionsarray[]可編輯審批表分組,審批人可勾選子集、編輯數值後再批准(見下文)

審批流程

  1. 執行到達設定了 manual_approval 的步驟時暫停,執行狀態變為 AWAITING_APPROVAL
  2. 建立審批記錄並開始逾時計時;控制台透過 WebSocket 收到 approval_request 即時提醒,審批人可同時收到通知郵件
  3. 審批人從三條通道之一批復:App 內審批列表、訊息裡的一鍵連結、API
  4. 批准 → 步驟繼續;拒絕 → 步驟按失敗處理(可用 on_failure 接通知分支);逾時 → 自動拒絕

通道一:App 內審批列表

控制台的審批管理頁面列出你可見的全部審批,支援卡片/表格兩種檢視與狀態篩選。批准或拒絕時可附備註,備註會儲存在審批記錄裡。設定了 reviewable_actions 的審批會展開為可勾選、可編輯的表格。

通道二:郵件通知與一鍵連結

開啟郵件通知後,審批人(未指定 approvers 時為執行發起人)帳號電子郵件會收到郵件,內容包括:工作流與步驟名、執行 ID、可審核動作數量、逾時提示(「約 N 小時後自動拒絕」)、approval_message 的說明文字,以及進入審批列表的連結。

郵件、Slack、Telegram 這類無法自訂請求標頭的訊息裡,還可以嵌入一鍵批復連結:

text
GET https://braidrun.com/api/webhook-trigger/approval/{approvalId}/approve?api_key=dyk_...
GET https://braidrun.com/api/webhook-trigger/approval/{approvalId}/reject?api_key=dyk_...

連結用 API Key 鑑權(APPROVAL_RESPOND 範圍),Key 放在 api_key 查詢參數裡。為防止連結預覽機器人(Slack 展開、郵件用戶端預抓取)誤觸,第一次開啟只渲染確認頁、不執行任何動作;點擊確認按鈕後帶 confirm=1 再次請求才真正批復。頁面帶 no-store 與 noindex 標頭,避免快取或搜尋引擎重放。

通道三:API

v1 開放 API 提供 5 個審批端點,全部要求 APPROVAL_RESPOND 權限範圍:

端點作用
GET /api/v1/approvals審批列表,可按 status 篩選
GET /api/v1/approvals/{id}審批詳情
GET /api/v1/approvals/execution/{executionId}查某次執行關聯的審批
POST /api/v1/approvals/{id}/approve批准;body 可帶 comment 與 editedItems
POST /api/v1/approvals/{id}/reject拒絕;body 可帶 comment
bash
# 批准(可附备注)
curl -X POST https://braidrun.com/api/v1/approvals/<approval-id>/approve \
  -H "Authorization: Bearer dyk_..." \
  -H "Content-Type: application/json" \
  -d '{"comment": "确认执行"}'

# 拒绝
curl -X POST https://braidrun.com/api/v1/approvals/<approval-id>/reject \
  -H "Authorization: Bearer dyk_..." \
  -H "Content-Type: application/json" \
  -d '{"comment": "本轮预算已用完"}'

editedItems 按分組名提交勾選/編輯後的子集,結構與下節的可編輯審批表對應;不傳則視為原樣全部批准。

可編輯審批表(reviewable_actions)

有些審批的粒度落在單條建議上:一批建議裡只執行其中一部分,個別列還要改數值。reviewable_actions 把這類審批做成表格——審批人勾選要執行的列,直接編輯標了 editable: true 的欄位(例如改出價),然後再點批准。

yaml
    manual_approval:
      enabled: true
      timeout: 86400
      approval_message: |
        请审核本轮调价建议:可勾选要执行的行,并直接修改建议出价。
      reviewable_actions:
        - name: raise_bid
          title: 加价建议
          source_var: raise_bid_file           # 变量值 = 建议清单 JSON 数组文件路径
          output_var: raise_bid_approved_file  # 批准后 = 勾选/编辑后的子集文件路径
          key_field: item_id
          columns:
            - { key: item_name, label: 名称, editable: false }
            - { key: current_bid, label: 当前出价, type: number, editable: false }
            - { key: proposed_bid, label: 建议出价, type: number, editable: true }
            - { key: reason, label: 理由, editable: false }
  • name — 分組內部名,同時用作輸出檔案前綴(批准後引擎寫出 reviewed_<name>.json)
  • source_var — 指向一個變數,變數值是上游步驟產生的建議清單(JSON 陣列檔案路徑)
  • output_var — 批准後設定的變數,值為勾選/編輯後的子集檔案路徑;下游執行步驟改讀它,就只會處理被批准的列
  • key_field — 列身分欄位,編輯後按它對齊;預設按陣列索引對齊
  • columns — 表格欄位定義;editable: true 的欄位審批人可改,type: number 渲染為數字輸入
伺服器端校驗

提交的子集會在伺服器端校驗:不屬於任何分組的資料被過濾;定義了 key_field 時,每列必須能在原清單裡找到對應項,拼一列不存在的資料無法繞過;editable: false 的欄位以原值為準,改了也無效。某個分組一列都沒勾選時會寫出空陣列,下游步驟按「全空跳過」處理。

拒絕與逾時:零改動

審批門控的核心承諾是:批准之前系統不執行任何動作。拒絕或逾時時——

  • 步驟本體不執行,相依它的下游步驟也不會觸發
  • 可用 on_failure 分支接一個「審批被拒」的通知或封存步驟
  • 逾時由系統自動拒絕,決策人記為 system;每次審批決定(含決策人、時間、備註)都會寫入稽核日誌
服務重啟時

審批記錄持久化儲存。服務重啟後,待處理的審批原樣恢復,逾時計時按原始截止時間繼續,審批人照常批復即可。

相關頁面