chore(types): sync approval response types
All checks were successful
Type Sync Check / check-type-sync (push) Successful in 33s
All checks were successful
Type Sync Check / check-type-sync (push) Successful in 33s
This commit is contained in:
@@ -25,6 +25,8 @@ python3 -m py_compile apps/api/src/models/approval.py apps/api/src/services/appr
|
|||||||
-> pass
|
-> pass
|
||||||
/Users/ogt/.pyenv/shims/ruff check apps/api/tests/test_approval_pending_visibility.py
|
/Users/ogt/.pyenv/shims/ruff check apps/api/tests/test_approval_pending_visibility.py
|
||||||
-> pass
|
-> pass
|
||||||
|
pnpm --filter @awoooi/shared-types generate
|
||||||
|
-> pass; packages/shared-types schema / TS types updated for new approval fields
|
||||||
DATABASE_URL='postgresql+asyncpg://test:test@localhost/test' /Users/ogt/.pyenv/shims/pytest apps/api/tests/test_approval_pending_visibility.py -q
|
DATABASE_URL='postgresql+asyncpg://test:test@localhost/test' /Users/ogt/.pyenv/shims/pytest apps/api/tests/test_approval_pending_visibility.py -q
|
||||||
-> 4 passed
|
-> 4 passed
|
||||||
DATABASE_URL='postgresql+asyncpg://test:test@localhost/test' /Users/ogt/.pyenv/shims/pytest apps/api/tests/test_heartbeat_ollama_endpoints.py apps/api/tests/test_heartbeat_pod_state_machine.py -q
|
DATABASE_URL='postgresql+asyncpg://test:test@localhost/test' /Users/ogt/.pyenv/shims/pytest apps/api/tests/test_heartbeat_ollama_endpoints.py apps/api/tests/test_heartbeat_pod_state_machine.py -q
|
||||||
|
|||||||
@@ -2668,7 +2668,7 @@ Phase 6 完成後
|
|||||||
**T153 Legacy HITL pending visibility + warning split(2026-05-31 台北)**:
|
**T153 Legacy HITL pending visibility + warning split(2026-05-31 台北)**:
|
||||||
- 觸發:production `/api/v1/approvals/pending` 有 legacy HITL backlog `count=21`,但 `/api/v1/platform/approvals` 回 `total=0`,operator 會以為前台沒有人工待辦;同時 heartbeat 用 raw PENDING 數量觸發「PENDING 積壓,需人工處理」,把 OBSERVE / NO_ACTION 觀察卡與真正可執行審批混在一起。
|
- 觸發:production `/api/v1/approvals/pending` 有 legacy HITL backlog `count=21`,但 `/api/v1/platform/approvals` 回 `total=0`,operator 會以為前台沒有人工待辦;同時 heartbeat 用 raw PENDING 數量觸發「PENDING 積壓,需人工處理」,把 OBSERVE / NO_ACTION 觀察卡與真正可執行審批混在一起。
|
||||||
- 修正:`ApprovalRequest` / `ApprovalRequestResponse` 外露 `incident_id`、`matched_playbook_id`、`telegram_message_id`、`telegram_chat_id`;DB / repository converter 保留 legacy approval record 的 incident / playbook / Telegram delivery 欄位。`HeartbeatReportService` 將 24h pending 拆成 actionable、observe-only、without-TG;warning 只看 actionable backlog,並在訊息指向 `/awooop/approvals`,Telegram heartbeat 顯示「待審拆分」。
|
- 修正:`ApprovalRequest` / `ApprovalRequestResponse` 外露 `incident_id`、`matched_playbook_id`、`telegram_message_id`、`telegram_chat_id`;DB / repository converter 保留 legacy approval record 的 incident / playbook / Telegram delivery 欄位。`HeartbeatReportService` 將 24h pending 拆成 actionable、observe-only、without-TG;warning 只看 actionable backlog,並在訊息指向 `/awooop/approvals`,Telegram heartbeat 顯示「待審拆分」。
|
||||||
- Verification:API py_compile pass;targeted ruff for new test pass;`test_approval_pending_visibility.py` 4 passed;`test_heartbeat_ollama_endpoints.py` + `test_heartbeat_pod_state_machine.py` 15 passed;`git diff --check` pass。
|
- Verification:API py_compile pass;targeted ruff for new test pass;`pnpm --filter @awoooi/shared-types generate` pass;`test_approval_pending_visibility.py` 4 passed;`test_heartbeat_ollama_endpoints.py` + `test_heartbeat_pod_state_machine.py` 15 passed;`git diff --check` pass。
|
||||||
- 判讀:T153 不批次 approve/reject 生產 PENDING,也不把觀察卡刪掉;它把「前台看得到 legacy HITL 事實」與「告警只針對真正人工 actionable backlog」補齊。舊 fallback kubectl / SSH action 仍需 operator 在 `/awooop/approvals` 逐筆決策;OBSERVE / NO_ACTION 類不再偽裝成 emergency manual backlog。下一段可追 LLM failure fallback 為何大量產生 `OBSERVE / medium` 卡片,但需避免破壞 agent 後續把 PENDING 更新成可執行 action 的路徑。
|
- 判讀:T153 不批次 approve/reject 生產 PENDING,也不把觀察卡刪掉;它把「前台看得到 legacy HITL 事實」與「告警只針對真正人工 actionable backlog」補齊。舊 fallback kubectl / SSH action 仍需 operator 在 `/awooop/approvals` 逐筆決策;OBSERVE / NO_ACTION 類不再偽裝成 emergency manual backlog。下一段可追 LLM failure fallback 為何大量產生 `OBSERVE / medium` 卡片,但需避免破壞 agent 後續把 PENDING 更新成可執行 action 的路徑。
|
||||||
|
|
||||||
**T152 Ansible runtime readiness surfaced(2026-05-24 台北)**:
|
**T152 Ansible runtime readiness surfaced(2026-05-24 台北)**:
|
||||||
|
|||||||
@@ -350,6 +350,32 @@
|
|||||||
"format": "date-time",
|
"format": "date-time",
|
||||||
"title": "Last Seen At",
|
"title": "Last Seen At",
|
||||||
"type": "string"
|
"type": "string"
|
||||||
|
},
|
||||||
|
"telegram_message_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"description": "Telegram approval card message ID",
|
||||||
|
"title": "Telegram Message Id"
|
||||||
|
},
|
||||||
|
"telegram_chat_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"description": "Telegram chat ID for the approval card",
|
||||||
|
"title": "Telegram Chat Id"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"required": [
|
"required": [
|
||||||
@@ -567,6 +593,54 @@
|
|||||||
"default": null,
|
"default": null,
|
||||||
"title": "Last Seen At"
|
"title": "Last Seen At"
|
||||||
},
|
},
|
||||||
|
"incident_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"title": "Incident Id"
|
||||||
|
},
|
||||||
|
"matched_playbook_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"title": "Matched Playbook Id"
|
||||||
|
},
|
||||||
|
"telegram_message_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"title": "Telegram Message Id"
|
||||||
|
},
|
||||||
|
"telegram_chat_id": {
|
||||||
|
"anyOf": [
|
||||||
|
{
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "null"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"default": null,
|
||||||
|
"title": "Telegram Chat Id"
|
||||||
|
},
|
||||||
"metadata": {
|
"metadata": {
|
||||||
"anyOf": [
|
"anyOf": [
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -151,6 +151,14 @@ export type HitCount = number;
|
|||||||
* 最後觸發時間
|
* 最後觸發時間
|
||||||
*/
|
*/
|
||||||
export type LastSeenAt = string;
|
export type LastSeenAt = string;
|
||||||
|
/**
|
||||||
|
* Telegram approval card message ID
|
||||||
|
*/
|
||||||
|
export type TelegramMessageId1 = number | null;
|
||||||
|
/**
|
||||||
|
* Telegram chat ID for the approval card
|
||||||
|
*/
|
||||||
|
export type TelegramChatId = number | null;
|
||||||
/**
|
/**
|
||||||
* 執行動作描述
|
* 執行動作描述
|
||||||
*/
|
*/
|
||||||
@@ -200,6 +208,10 @@ export type ResolvedAt1 = string | null;
|
|||||||
export type Fingerprint1 = string | null;
|
export type Fingerprint1 = string | null;
|
||||||
export type HitCount1 = number;
|
export type HitCount1 = number;
|
||||||
export type LastSeenAt1 = string | null;
|
export type LastSeenAt1 = string | null;
|
||||||
|
export type IncidentId2 = string | null;
|
||||||
|
export type MatchedPlaybookId2 = string | null;
|
||||||
|
export type TelegramMessageId2 = number | null;
|
||||||
|
export type TelegramChatId1 = number | null;
|
||||||
export type Metadata2 = {
|
export type Metadata2 = {
|
||||||
[k: string]: unknown;
|
[k: string]: unknown;
|
||||||
} | null;
|
} | null;
|
||||||
@@ -416,7 +428,7 @@ export type Fingerprint2 = string | null;
|
|||||||
/**
|
/**
|
||||||
* 事件唯一識別碼 (如 INC-20260322-A1B2C3)
|
* 事件唯一識別碼 (如 INC-20260322-A1B2C3)
|
||||||
*/
|
*/
|
||||||
export type IncidentId2 = string;
|
export type IncidentId3 = string;
|
||||||
/**
|
/**
|
||||||
* 事件狀態
|
* 事件狀態
|
||||||
*/
|
*/
|
||||||
@@ -507,7 +519,7 @@ export type ManualFixSteps = string | null;
|
|||||||
export type ManualFixBy = string | null;
|
export type ManualFixBy = string | null;
|
||||||
export type Signals1 = Signal[];
|
export type Signals1 = Signal[];
|
||||||
export type AffectedServices1 = string[];
|
export type AffectedServices1 = string[];
|
||||||
export type IncidentId3 = string;
|
export type IncidentId4 = string;
|
||||||
export type Signals2 = Signal[];
|
export type Signals2 = Signal[];
|
||||||
export type AffectedServices2 = string[];
|
export type AffectedServices2 = string[];
|
||||||
export type ProposalIds1 = string[];
|
export type ProposalIds1 = string[];
|
||||||
@@ -937,6 +949,8 @@ export interface ApprovalRequest {
|
|||||||
fingerprint?: Fingerprint;
|
fingerprint?: Fingerprint;
|
||||||
hit_count?: HitCount;
|
hit_count?: HitCount;
|
||||||
last_seen_at?: LastSeenAt;
|
last_seen_at?: LastSeenAt;
|
||||||
|
telegram_message_id?: TelegramMessageId1;
|
||||||
|
telegram_chat_id?: TelegramChatId;
|
||||||
[k: string]: unknown;
|
[k: string]: unknown;
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
@@ -982,6 +996,10 @@ export interface ApprovalRequestResponse {
|
|||||||
fingerprint?: Fingerprint1;
|
fingerprint?: Fingerprint1;
|
||||||
hit_count?: HitCount1;
|
hit_count?: HitCount1;
|
||||||
last_seen_at?: LastSeenAt1;
|
last_seen_at?: LastSeenAt1;
|
||||||
|
incident_id?: IncidentId2;
|
||||||
|
matched_playbook_id?: MatchedPlaybookId2;
|
||||||
|
telegram_message_id?: TelegramMessageId2;
|
||||||
|
telegram_chat_id?: TelegramChatId1;
|
||||||
metadata?: Metadata2;
|
metadata?: Metadata2;
|
||||||
[k: string]: unknown;
|
[k: string]: unknown;
|
||||||
}
|
}
|
||||||
@@ -1190,7 +1208,7 @@ export interface Annotations {
|
|||||||
* via the `definition` "Incident".
|
* via the `definition` "Incident".
|
||||||
*/
|
*/
|
||||||
export interface Incident {
|
export interface Incident {
|
||||||
incident_id?: IncidentId2;
|
incident_id?: IncidentId3;
|
||||||
status?: IncidentStatus1;
|
status?: IncidentStatus1;
|
||||||
severity: Severity2;
|
severity: Severity2;
|
||||||
signals?: Signals;
|
signals?: Signals;
|
||||||
@@ -1244,7 +1262,7 @@ export interface IncidentCreate {
|
|||||||
* via the `definition` "IncidentResponse".
|
* via the `definition` "IncidentResponse".
|
||||||
*/
|
*/
|
||||||
export interface IncidentResponse {
|
export interface IncidentResponse {
|
||||||
incident_id: IncidentId3;
|
incident_id: IncidentId4;
|
||||||
status: IncidentStatus;
|
status: IncidentStatus;
|
||||||
severity: Severity;
|
severity: Severity;
|
||||||
signals: Signals2;
|
signals: Signals2;
|
||||||
|
|||||||
Reference in New Issue
Block a user