Files
wehub-resource-sync 4b6817381b
CI (OpenClaw E2E) / openclaw test (push) Has been cancelled
CI / coverage-report (push) Has been cancelled
CI / test-kubernetes (push) Has been cancelled
CI / should-run-thorough (push) Has been cancelled
CI / test-thorough (cloudwatch-demo) (push) Has been cancelled
CI / test-thorough (flink-ecs) (push) Has been cancelled
CI / test-thorough (upstream-lambda) (push) Has been cancelled
CI / test-thorough (prefect-ecs-fargate) (push) Has been cancelled
Release / build-binaries (zip, opensre.exe, onefile, windows-latest, windows-x64) (push) Has been cancelled
Benchmark image — build + push to ECR (any adapter) / build + push (push) Has been cancelled
CI / quality (ubuntu-latest) (push) Has been cancelled
CI / test (tools-runtime) (push) Has been cancelled
CI / test (e2e-general) (push) Has been cancelled
CI / test (cli-runtime) (push) Has been cancelled
CI / test (e2e-provider-and-openclaw) (push) Has been cancelled
CI / test (integrations-and-misc) (push) Has been cancelled
Release / verify (push) Has been cancelled
Release / build-python-dist (push) Has been cancelled
Release / build-binaries (tar.gz, opensre, onedir, macos-15-intel, darwin-x64) (push) Has been cancelled
Release / build-binaries (tar.gz, opensre, onedir, macos-latest, darwin-arm64) (push) Has been cancelled
Release / build-binaries (tar.gz, opensre, onedir, ubuntu-22.04, linux-x64) (push) Has been cancelled
Release / publish-release (push) Has been cancelled
Release / publish-main-release (push) Has been cancelled
Interactive Shell Live (PR + post-merge) / turn-checks (no-LLM) (push) Has been cancelled
CodeQL / Analyze (python) (push) Has been cancelled
Interactive Shell Live (PR + post-merge) / turn-live shard ${{ matrix.shard_index }} (push) Has been cancelled
Release / prepare (push) Has been cancelled
Release / build-binaries (tar.gz, opensre, onedir, ubuntu-22.04-arm, linux-arm64) (push) Has been cancelled
Synthetic Deterministic Tests / Synthetic offline (deterministic) (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 13:10:45 +08:00

129 lines
4.0 KiB
Python

from __future__ import annotations
import re
from rich.text import Text
from platform.terminal.theme import (
BRAND,
DIM,
ERROR,
HIGHLIGHT,
SECONDARY,
TEXT,
)
from surfaces.interactive_shell.ui.components.time_format import _elapsed_hms, _fmt_timing
from tools.registry import resolve_tool_display_name
# (padded_label, text_color) -- all labels are 6 chars wide. Every badge draws
# from the theme's accent tokens (HIGHLIGHT / BRAND) so the whole phase strip
# stays within the active palette (e.g. all blue shades under the blue theme),
# alternating the two accents for light per-phase distinction.
BADGE_STYLES: dict[str, tuple[str, str]] = {
"READ": ("READ ", HIGHLIGHT),
"PLAN": ("PLAN ", BRAND),
"INVEST": ("INVEST", HIGHLIGHT),
"DIAG": ("DIAG ", BRAND),
"MERGE": ("MERGE ", HIGHLIGHT),
}
_NODE_EVENT_TYPE: dict[str, str] = {
"extract_alert": "READ",
"resolve_integrations": "READ",
"plan_actions": "PLAN",
"merge_hypotheses": "MERGE",
"investigation_agent": "INVEST",
"diagnose_root_cause": "DIAG",
"opensre_llm_eval": "DIAG",
"publish_findings": "DIAG",
}
_NODE_PHASE: dict[str, str] = {
"extract_alert": "LOAD",
"resolve_integrations": "LOAD",
"plan_actions": "PLAN",
"merge_hypotheses": "DIAGNOSE",
"investigation_agent": "INVESTIGATE",
"diagnose_root_cause": "DIAGNOSE",
"opensre_llm_eval": "DIAGNOSE",
"publish_findings": "PUBLISH",
}
_NODE_LABELS: dict[str, str] = {
"extract_alert": "Reading alert",
"resolve_integrations": "Loading integrations",
"plan_actions": "Planning",
"investigate": "Gathering evidence",
"investigation_agent": "Investigation",
"diagnose_root_cause": "Diagnosing",
"publish_findings": "Publishing",
}
def _node_event_type(node_name: str) -> str:
if node_name.startswith("investigate"):
return "INVEST"
return _NODE_EVENT_TYPE.get(node_name, "DIAG")
def _node_phase_label(node_name: str) -> str:
if node_name.startswith("investigate"):
return "INVESTIGATE"
return _NODE_PHASE.get(node_name, node_name.upper()[:12])
def _node_label(node_name: str) -> str:
if node_name.startswith("investigate_"):
action = node_name[len("investigate_") :]
return f"Investigate · {action.replace('_', ' ').title()}"
return _NODE_LABELS.get(node_name, node_name.replace("_", " ").title())
def _humanise_message(message: str) -> str:
if not message:
return ""
m = re.match(r"Planned actions:\s*\[(.+)\]", message)
if m:
raw = re.findall(r"'([^']+)'", m.group(1))
return ", ".join(resolve_tool_display_name(action) for action in raw)
if "No new actions" in message:
return ""
if "integrations" in message.lower() or "resolved" in message.lower():
m2 = re.search(r"\[(.+)\]", message)
if m2 and (services := re.findall(r"'([^']+)'", m2.group(1))):
return ", ".join(services)
m3 = re.match(r"validity:(\d+%)", message)
if m3:
return f"confidence {m3.group(1)}"
return re.sub(r"^datadog:", "", message)
def build_progress_step_text(
*,
node_name: str,
elapsed_total: float,
elapsed_step_ms: int | None = None,
status: str = "active",
message: str | None = None,
) -> Text:
ev_type = _node_event_type(node_name)
badge_label, badge_color = BADGE_STYLES.get(ev_type, BADGE_STYLES["DIAG"])
label = _node_label(node_name)
err = status == "error"
timing = _fmt_timing(elapsed_step_ms) if elapsed_step_ms is not None else ""
t = Text()
t.append(f"{_elapsed_hms(elapsed_total)} ", style=SECONDARY)
if status == "active":
t.append("· ", style=SECONDARY)
else:
t.append("✗ " if err else "✓ ", style=f"bold {ERROR if err else HIGHLIGHT}")
t.append(badge_label, style=f"bold {badge_color}")
t.append(" · ", style=DIM)
t.append(label, style=f"bold {TEXT}")
if msg := _humanise_message(message or ""):
t.append(f" {msg}", style=BRAND)
if timing:
t.append(f" {timing}", style=SECONDARY)
return t