# 变更审计记录：DWS_TASK_ENGINE ETL 编排替代 fire_event 事件链

| 字段 | 值 |
|------|-----|
| 日期 | 2026-03-29 05:47:50 |
| Prompt-ID | P20260329-054439 |
| Session-ID | be7f7482 |
| Session 路径 | docs/audit/session_logs/2026-03/29/10_4d217477_050959 |

## 操作摘要

将任务引擎的触发方式从"DWD 加载后 fire_event 事件通知"改为"ETL 显式编排任务"。新增 DWS_TASK_ENGINE ETL 任务，在 DWS 指数计算完成后按顺序 HTTP 调用后端执行 recall_completion_check → task_expiry_check → task_generator。同时回滚了之前的 fire_event("etl_data_updated") 方案，删除了 biz_trigger.py 工具和旧版 fire-event 端点，将 internal_events.py 替换为 run-job 端点。

## 风险评估

- ETL 新增编排任务：**低**（每步失败仅记录日志，不中断后续步骤，不影响 DWS 数据计算）
- 后端 run-job 端点：**低**（Internal-Token 认证，独立路由，复用现有 trigger_scheduler.run_job_by_id）
- fire_event 回滚：**低**（task_expiry_check 的 interval 触发器保留，DWS_TASK_ENGINE 是补充而非替代）

## 数据库变更

无。

## 本次对话文件变更

### 新增文件
- `apps/etl/connectors/feiqiu/tasks/dws/task_engine.py` — DWS_TASK_ENGINE ETL 任务实现
- `apps/backend/app/routers/internal_events.py` — POST /api/internal/run-job 端点（替换旧版 fire-event 端点）
- `apps/backend/app/auth/internal_token.py` — 通用 Internal-Token 认证依赖（上一轮已创建，本轮保留）

### 删除文件
- `apps/etl/connectors/feiqiu/utils/biz_trigger.py` — 不再需要的事件触发工具（fire_event 方案产物）

### 修改文件
- `apps/backend/app/main.py` — 注册 internal_events 路由
- `apps/etl/connectors/feiqiu/orchestration/task_registry.py` — 注册 DWS_TASK_ENGINE 任务
- `apps/etl/connectors/feiqiu/tasks/dwd/dwd_load_task.py` — 回滚 fire_event 触发代码
- `.kiro/steering/frontend-backend-integration.md` — 更新事件驱动触发器规则

## 改动注解

### `apps/etl/connectors/feiqiu/tasks/dws/task_engine.py`
- 变更类型：新增
- 原始原因：之前的 fire_event 方案在 DWD 加载后触发事件，但事件链依赖 trigger_scheduler 的 event 匹配机制，耦合度高且调试困难。改为 ETL 显式编排，在 DWS 指数计算完成后按确定顺序执行后端任务
- 思路分析：继承 BaseTask（非 BaseDwsTask，因为不操作 DWS 表），extract() 返回空，load() 按 `_JOB_SEQUENCE` 顺序调用后端 `POST /api/internal/run-job`。每步独立执行，失败仅 warning 不中断后续步骤。环境变量 `BACKEND_API_URL` + `INTERNAL_API_TOKEN` 缺失时跳过整个任务。超时设置 (5s, 30s) 兼顾连接速度和任务执行时间
- 修改结果：DWS 指数计算完成后自动执行完成检查→过期检查→任务生成全流程，替代之前分散的事件触发机制

### `apps/backend/app/routers/internal_events.py`
- 变更类型：新增（替换旧版）
- 原始原因：旧版 fire-event 端点按 event_name 触发，新版改为按 job_name 直接执行指定任务，语义更明确
- 思路分析：`POST /api/internal/run-job` 接收 `job_name`，查询 `biz.trigger_jobs` 表获取 job_id，调用 `run_job_by_id()` 执行。Internal-Token 认证。job_name 不存在时返回 404
- 修改结果：ETL 可按名称精确执行后端任务，不再依赖事件匹配机制

### `apps/backend/app/auth/internal_token.py`
- 变更类型：保留（上一轮创建）
- 原始原因：将 Internal-Token 认证从 AIConfig 解耦，使 /api/internal/* 端点可独立使用
- 思路分析：从 Authorization header 解析 `Internal-Token {token}` 格式，与 `INTERNAL_API_TOKEN` 环境变量比对。三层防御：格式→空值→匹配
- 修改结果：`verify_internal_token` 依赖函数供 internal_events 路由使用

### `apps/etl/connectors/feiqiu/utils/biz_trigger.py`
- 变更类型：删除
- 原始原因：fire_event 方案被 DWS_TASK_ENGINE 替代，biz_trigger.py 中的 `trigger_biz_event()` 函数不再需要
- 修改结果：ETL 侧不再有独立的事件触发工具，任务引擎调用统一由 DWS_TASK_ENGINE 负责

### `apps/backend/app/main.py`
- 变更类型：修改
- 原始原因：注册新版 internal_events 路由
- 思路分析：在 import 列表添加 `internal_events`，在 `include_router` 调用中注册。CHANGE 注释记录变更历史
- 修改结果：`/api/internal/run-job` 端点可用

### `apps/etl/connectors/feiqiu/orchestration/task_registry.py`
- 变更类型：修改
- 原始原因：注册 DWS_TASK_ENGINE 任务到 ETL 任务注册表
- 思路分析：`layer="INDEX"`，`requires_db_config=False`（不操作数据库），`depends_on=["DWS_WINBACK_INDEX", "DWS_NEWCONV_INDEX", "DWS_RELATION_INDEX"]`（所有指数任务完成后执行）
- 修改结果：DWS_TASK_ENGINE 在 ETL 编排中自动排在指数计算之后

### `apps/etl/connectors/feiqiu/tasks/dwd/dwd_load_task.py`
- 变更类型：修改
- 原始原因：回滚 fire_event 触发代码，DWD 加载后不再需要事件通知
- 思路分析：移除 load() 末尾的 `trigger_biz_event("etl_data_updated")` 调用和相关 import
- 修改结果：DWD 加载任务恢复为纯数据加载，不再有副作用

### `.kiro/steering/frontend-backend-integration.md`
- 变更类型：修改
- 原始原因：更新事件驱动触发器规则，反映新的编排方式
- 思路分析：新增 DWS_TASK_ENGINE 编排说明，明确 task_expiry_check interval 触发器保留
- 修改结果：steering 规则与实际实现一致

## 回滚策略

1. 删除 `apps/etl/connectors/feiqiu/tasks/dws/task_engine.py`
2. 删除新版 `apps/backend/app/routers/internal_events.py`
3. 从 `apps/etl/connectors/feiqiu/orchestration/task_registry.py` 移除 DWS_TASK_ENGINE 注册
4. 从 `apps/backend/app/main.py` 移除 internal_events 路由注册
5. 如需恢复 fire_event 方案：恢复 biz_trigger.py + 旧版 internal_events.py + dwd_load_task.py 事件触发代码

## 合规检查

- ✅ 无新增迁移 SQL
- ✅ 无数据库变更
- ⚠️ 接口代码已变更（新增 /api/internal/run-job），OpenAPI spec 待同步
- ⚠️ DDL 基线状态待确认（本次无 DDL 变更）
