admin / Syanpse-Vanguard
public
Syanpse-Vanguard / synapse-vanguard-v3 / agents / common / config.py
3298 B · main
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 | """Agent configuration + persisted identity state. Config is read from a JSON/TOML file (path via SV_AGENT_CONFIG) with env-var overrides. Identity (agent_id + dev-mode ingest token) is persisted separately so a restart re-uses the existing enrollment.""" from __future__ import annotations import json import os from dataclasses import dataclass, field @dataclass class AgentConfig: ingest_url: str = "https://localhost:9443" enrollment_token: str = "dev-enrollment-token" hostname: str = field(default_factory=lambda: os.uname().nodename if hasattr(os, "uname") else os.environ.get("COMPUTERNAME", "host")) platform: str = "linux" channels: list[str] = field(default_factory=list) agent_version: str = "0.1.0" # mTLS (production) — paths to the agent's signed client cert/key + CA. mtls_enabled: bool = False client_cert: str | None = None client_key: str | None = None ca_cert: str | None = None verify_tls: bool = True # buffering / batching buffer_path: str = "./agent-buffer.sqlite" state_path: str = "./agent-state.json" batch_size: int = 500 flush_interval_s: float = 5.0 # collector-specific knobs syslog_paths: list[str] = field(default_factory=lambda: ["/var/log/syslog"]) auditd_path: str = "/var/log/audit/audit.log" winlog_channels: list[str] = field(default_factory=lambda: [ "Security", "System", "Application", "Microsoft-Windows-Sysmon/Operational", "Microsoft-Windows-PowerShell/Operational", "Windows PowerShell", "Microsoft-Windows-Windows Defender/Operational", "Microsoft-Windows-TaskScheduler/Operational", "Microsoft-Windows-WMI-Activity/Operational", "Microsoft-Windows-TerminalServices-LocalSessionManager/Operational", ]) @classmethod def load(cls, path: str | None = None) -> "AgentConfig": path = path or os.environ.get("SV_AGENT_CONFIG") data: dict = {} if path and os.path.exists(path): with open(path, "r", encoding="utf-8") as fh: if path.endswith(".toml"): # tomllib is stdlib only on Python 3.11+. Fall back to the # `tomli` backport (same API) on 3.10 and earlier. try: import tomllib except ModuleNotFoundError: import tomli as tomllib data = tomllib.loads(fh.read()) else: data = json.load(fh) # env overrides for the common knobs for key in ("ingest_url", "enrollment_token", "hostname", "platform"): env = os.environ.get(f"SV_AGENT_{key.upper()}") if env: data[key] = env known = {f.name for f in cls.__dataclass_fields__.values()} return cls(**{k: v for k, v in data.items() if k in known}) def load_state(path: str) -> dict: if os.path.exists(path): with open(path, "r", encoding="utf-8") as fh: return json.load(fh) return {} def save_state(path: str, state: dict) -> None: tmp = path + ".tmp" with open(tmp, "w", encoding="utf-8") as fh: json.dump(state, fh) os.replace(tmp, path) |