fix(iwooos): redact frontend host topology labels

This commit is contained in:
ogt
2026-06-25 11:08:34 +08:00
parent b2a0cf1133
commit 975ed981e2
6 changed files with 325 additions and 256 deletions

View File

@@ -0,0 +1,60 @@
#!/usr/bin/env python3
"""Guard IwoooS public frontend text against host/topology leakage.
This guard is intentionally static and read-only. It does not connect to any
runtime host or API; it only prevents public IwoooS copy from exposing internal
host aliases, LAN endpoints, or working-lane identifiers as product text.
"""
from __future__ import annotations
import argparse
from pathlib import Path
PUBLIC_FILES = [
Path("apps/web/messages/zh-TW.json"),
Path("apps/web/messages/en.json"),
Path("apps/web/src/app/[locale]/iwooos/page.tsx"),
]
FORBIDDEN_FRAGMENTS = [
"host:",
"Kali host",
"Kali 112",
"kali_112",
"internal110",
"security_compliance_s2_110",
"127.0.0.1",
"192.168.",
"P2-110",
"P2-112",
]
def validate(root: Path) -> None:
violations: list[str] = []
for relative_path in PUBLIC_FILES:
path = root / relative_path
text = path.read_text(encoding="utf-8")
for line_number, line in enumerate(text.splitlines(), start=1):
for fragment in FORBIDDEN_FRAGMENTS:
if fragment in line:
violations.append(f"{relative_path}:{line_number}: forbidden {fragment!r}")
if violations:
formatted = "\n".join(violations[:20])
raise SystemExit(f"BLOCKED iwooos_frontend_display_redaction:\n{formatted}")
def main() -> int:
parser = argparse.ArgumentParser(description="Validate IwoooS public frontend display redaction.")
parser.add_argument("--root", default=".")
args = parser.parse_args()
validate(Path(args.root).resolve())
print("IWOOOS_FRONTEND_DISPLAY_REDACTION_GUARD_OK")
return 0
if __name__ == "__main__":
raise SystemExit(main())

View File

@@ -87,6 +87,10 @@ def validate(root: Path) -> None:
str(root / "scripts" / "security" / "public-frontend-env-guard.py")
)
public_frontend_env_guard["validate"](root)
iwooos_frontend_display_redaction_guard = runpy.run_path(
str(root / "scripts" / "security" / "iwooos-frontend-display-redaction-guard.py")
)
iwooos_frontend_display_redaction_guard["validate"](root)
wazuh_readonly_route_boundary_guard = runpy.run_path(
str(root / "scripts" / "security" / "wazuh-readonly-route-boundary-guard.py")
)
@@ -949,21 +953,21 @@ def validate(root: Path) -> None:
'data-testid="iwooos-kali-maintenance-readiness-board"',
"kaliMaintenanceRunwaySteps",
"2026-06-04 08:55",
"kali_112_read_only_observed_at=2026-06-04T08:55:43+08:00",
"kali_112_scanner_health=healthy",
"kali_112_scanner_health_endpoint=127.0.0.1:8080/health",
"kali_112_scanner_service_active=active",
"kali_112_scanner_service_enabled=enabled",
"kali_112_upgradable_package_count=1994",
"kali_112_failed_systemd_unit_count=1",
"kali_112_failed_systemd_unit=networking.service",
"kali_112_systemd_hardening_enabled=0/4",
"kali_112_full_upgrade_authorized=false",
"kali_112_reboot_authorized=false",
"kali_112_package_update_executed=false",
"kali_112_host_reboot_executed=false",
"kali_112_active_scan_executed=false",
"kali_112_runtime_execution_authorized=false",
"security_observer_read_only_observed_at=2026-06-04T08:55:43+08:00",
"security_observer_scanner_health=healthy",
"security_observer_health_endpoint=redacted_internal_health_check",
"security_observer_scanner_service_active=active",
"security_observer_scanner_service_enabled=enabled",
"security_observer_upgradable_package_count=1994",
"security_observer_failed_systemd_unit_count=1",
"security_observer_failed_systemd_unit=networking.service",
"security_observer_systemd_hardening_enabled=0/4",
"security_observer_full_upgrade_authorized=false",
"security_observer_reboot_authorized=false",
"security_observer_package_update_executed=false",
"security_observer_host_reboot_executed=false",
"security_observer_active_scan_executed=false",
"security_observer_runtime_execution_authorized=false",
]:
assert_text_contains("iwooos_projection_page.kali_maintenance_readiness", iwooos_projection_page, text)
@@ -16458,7 +16462,7 @@ def validate(root: Path) -> None:
"headline_percent_after_this_stage=64",
"headline_movement_signal_count=2",
"awooop_read_only_production_landing_evidence_count=1",
"kali_112_read_only_production_evidence_count=1",
"security_observer_read_only_production_evidence_count=1",
"owner_response_received_count=0",
"owner_response_accepted_count=0",
"owner_response_acceptance_gate_open=false",
@@ -17367,7 +17371,7 @@ def validate(root: Path) -> None:
for text in [
"iwooos_rollout_phase_count=5",
"iwooos_rollout_current_phase=observe_first",
"iwooos_rollout_frontstage_source=security_compliance_s2_110",
"iwooos_rollout_frontstage_source=security_compliance_integrated_entry",
"iwooos_rollout_runtime_phase_enabled=false",
"iwooos_rollout_enforcement_enabled=false",
"iwooos_rollout_action_buttons_allowed=false",
@@ -17532,7 +17536,7 @@ def validate(root: Path) -> None:
"iwooos_progress_active_runtime_gate_count=0",
"iwooos_progress_github_primary_ready_count=0",
"iwooos_progress_awooop_landing_evidence_count=1",
"iwooos_progress_kali_112_read_only_evidence_count=1",
"iwooos_progress_security_observer_read_only_evidence_count=1",
"iwooos_progress_review_authorized=true",
"runtime_execution_authorized=false",
"active_runtime_gate_count=0",
@@ -18110,10 +18114,10 @@ def validate(root: Path) -> None:
"iwooos_host_tool_evidence_chain_host_count=3",
"iwooos_host_tool_evidence_chain_tool_lane_count=6",
"iwooos_host_tool_evidence_chain_step_count=5",
"kali_112_integrated_as_read_only=true",
"dev_hosts_111_168_integrated_as_read_only=true",
"security_observer_integrated_as_read_only=true",
"dev_host_group_integrated_as_read_only=true",
"monitoring_tools_evidence_chain_linked=true",
"kali_112_execute_authorized=false",
"security_observer_execute_authorized=false",
"host_update_authorized=false",
"active_scan_authorized=false",
"ssh_mutation_authorized=false",