7 · High‑Level Architecture — Stella Ops


0 Purpose & Scope

Give contributors, DevOps engineers and auditors a complete yet readable map of the Core:

  • Major runtime components and message paths.
  • Where plug‑ins, CLI helpers and runtime agents attach.
  • Technology choices that enable the sub‑5 second SBOM goal.
  • Typical operational scenarios (pipeline scan, mute, nightly re‑scan, etc.).

Anything enterprise‑only (signed PDF, custom/regulated TLS, LDAP, enforcement) must arrive as a plug‑in; the Core never hard‑codes those concerns.

1 Component Overview

#ComponentResponsibility
1API GatewayREST endpoints (/scan, /quota, /token/offline); token auth; quota enforcement
2Scan ServiceSBOM parsing, Delta‑SBOM cache, vulnerability lookup
3Policy EngineYAML / (optional) Rego rule evaluation; verdict assembly
4Quota ServicePer‑token counters; 333 scans/day; waits & HTTP 429
5Client‑JWT IssuerIssues 30‑day offline tokens; bundles them into OUK
5RegistryAnonymous internal Docker registry for agents, SBOM uploads
6Web UIReact/Blazor SPA; dashboards, policy editor, quota banner
7Data StoresRedis (cache, quota) & MongoDB (SBOMs, findings, audit)
8Plugin HostHot‑load .NET DLLs; isolates community plug‑ins
9Agentssbom‑builder, Stella CLI scanner CLI, future StellaOpsAttestor
flowchart TD
    subgraph "External Actors"
        DEV["Developer / DevSecOps / Manager"]
        CI["CI/CD Pipeline (e.g., Stella CLI)"]
        K8S["Kubernetes Cluster (e.g., Zastava Agent)"]
    end

    subgraph "Stella Ops Runtime"
        subgraph "Core Services"
            CORE["Stella Core
(REST + gRPC APIs, Orchestration)"] REDIS[("Redis
(Cache, Queues, Trivy DB Mirror)")] MONGO[("MongoDB
(Optional: Long-term Storage)")] POL["Mute Policies
(OPA & YAML Evaluator)"] REG["StellaOps Registry
(Docker Registry v2)"] ATT["StellaOps Attestor
(SLSA + Rekor)"] end subgraph "Agents & Builders" SB["SBOM Builder
(Go Binary: Extracts Layers, Generates SBOMs)"] SA["Stella CLI
(Pipeline Helper: Invokes Builder, Triggers Scans)"] ZA["Zastava Agent
(K8s Webhook: Enforces Policies, Inventories Containers)"] end subgraph "Scanners & UI" TRIVY["Trivy Scanner
(Plugin Container: Vulnerability Scanning)"] UI["Web UI
(Vue3 + Tailwind: Dashboards, Policy Editor)"] CLI["Stella CLI
(CLI Helper: Triggers Scans, Mutes)"] end end DEV -->|Browses Findings, Mutes CVEs| UI DEV -->|Triggers Scans| CLI CI -->|Generates SBOM, Calls /scan| SA K8S -->|Inventories Containers, Enforces Gates| ZA UI -- "REST" --> CORE CLI -- "REST/gRPC" --> CORE SA -->|Scan Requests| CORE SB -->|Uploads SBOMs| CORE ZA -->|Policy Gates| CORE CORE -- "Queues, Caches" --> REDIS CORE -- "Persists Data" --> MONGO CORE -->|Evaluates Policies| POL CORE -->|Attests Provenance| ATT CORE -->|Scans Vulnerabilities| TRIVY SB -- "Pulls Images" --> REG SA -- "Pulls Images" --> REG ZA -- "Pulls Images" --> REG style DEV fill:#f9f,stroke:#333 style CI fill:#f9f,stroke:#333 style K8S fill:#f9f,stroke:#333 style CORE fill:#ddf,stroke:#333 style REDIS fill:#fdd,stroke:#333 style MONGO fill:#fdd,stroke:#333 style POL fill:#dfd,stroke:#333 style REG fill:#dfd,stroke:#333 style ATT fill:#dfd,stroke:#333 style SB fill:#fdf,stroke:#333 style SA fill:#fdf,stroke:#333 style ZA fill:#fdf,stroke:#333 style TRIVY fill:#ffd,stroke:#333 style UI fill:#ffd,stroke:#333 style CLI fill:#ffd,stroke:#333
  • Developer / DevSecOps / Manager – browses findings, mutes CVEs, triggers scans.
  • Stella CLI – generates SBOMs and calls /scan during CI.
  • Zastava Agent – inventories live containers; Core ships it in passive mode only (no kill).

1.1 Client‑JWT Lifecycle (offline aware)

  1. Online instance – user signs in → /connect/token issues JWT valid 12 h.
  2. Offline instance – JWT with exp ≈ 30 days ships in OUK; backend re‑signs and stores it during import.
  3. Tokens embed a tier claim (“Free”) and maxScansPerDay: 333.
  4. On expiry the UI surfaces a red toast 7 days in advance.

2 · Component Responsibilities (runtime view)

ComponentCore ResponsibilityImplementation Highlights
Stella CoreOrchestrates scans, persists SBOM blobs, serves REST/gRPC APIs, fans out jobs to scanners & policy engine..NET 10 LTS, CQRS, Redis Streams; pluggable runner interfaces.
SBOM BuilderExtracts image layers, queries Core for missing layers, generates SBOMs (multi‑format), uploads blobs.Go binary; wraps Trivy & Syft libs.
Stella CLIPipeline‑side helper; invokes Builder, triggers scan, streams progress back to CI/CD.Static musl build.
Zastava AgentK8s admission webhook enforcing policy verdicts before Pod creation.Rust for sub‑10 ms latencies.
UIAngular 17 SPA for dashboards, settings, policy editor.Tailwind CSS; Webpack module federation (future).
RedisCache, queue, Trivy‑DB mirror, layer diffing.Single instance or Sentinel.
MongoDB (opt.)Long‑term SBOM & policy audit storage (> 180 days).Optional; enabled via flag.
StellaOps.RegistryAnonymous read‑only Docker v2 registry with optional Cosign verification.registry :2 behind nginx reverse proxy.
StellaOps.MutePoliciesYAML/Rego evaluator, policy version store, /policy/* API.Embeds OPA‑WASM; falls back to opa exec.
StellaOpsAttestorGenerate SLSA provenance & Rekor signatures; verify on demand.Side‑car container; DSSE + Rekor CLI.

All cross‑component calls use dependency‑injected interfaces—no intra‑component reach‑ins.


3 · Principal Backend Modules & Plug‑in Hooks

NamespaceResponsibilityBuilt‑in Tech / DefaultPlug‑in Contract
configurationParse env/JSON, health‑check endpoint.NET 10 LTS OptionsIConfigValidator
identityEmbedded OAuth2/OIDC (OpenIddict 6)MIT OpenIddictIIdentityProvider for LDAP/SAML/JWT gateway
pluginloaderDiscover DLLs, SemVer gate, optional Cosign verifyReflection + CosignIPluginLifecycleHook for telemetry
scanningSBOM‑ & image‑flow orchestration; runner poolTrivy CLI (default)IScannerRunner – e.g., Grype, Copacetic, Clair
feedmergeNightly NVD merge & feed enrichmentHangfire jobdrop‑in *.Schedule.dll for OSV, GHSA, NVD 2.0, CNNVD, CNVD, ENISA, JVN and BDU feeds
tlsTLS provider abstractionOpenSSLITlsProvider for custom suites (incl. SM2, where law or security requires it)
reportingRender HTML/PDF reportsRazorLightIReportRenderer
uiAngular SPA & i18nAngular 20new locales via /locales/{lang}.json
schedulingCron + retriesHangfireany recurrent job via *.Schedule.dll
classDiagram
    class configuration
    class identity
    class pluginloader
    class scanning
    class feedmerger
    class tls
    class reporting
    class ui
    class scheduling

    class AllModules

    configuration ..> identity : Uses
    identity ..> pluginloader : Authenticates Plugins
    pluginloader ..> scanning : Loads Scanner Runners
    scanning ..> feedmerger : Triggers Feed Merges
    tls ..> AllModules : Provides TLS Abstraction
    reporting ..> ui : Renders Reports for UI
    scheduling ..> feedmerger : Schedules Nightly Jobs

    note for scanning "Pluggable: ISScannerRunner
e.g., Trivy, Grype" note for feedmerger "Pluggable: *.Schedule.dll
e.g., OSV, GHSA Feeds" note for identity "Pluggable: IIdentityProvider
e.g., LDAP, SAML" note for reporting "Pluggable: IReportRenderer
e.g., Custom PDF"

When remaining = 0:
API returns 429 Too Many Requests, Retry‑After: <UTC‑midnight> (sequence omitted for brevity).


4 · Data Flows

4.1 SBOM‑First (≤ 5 s P95)

Builder produces SBOM locally, so Core never touches the Docker socket. Trivy path hits ≤ 5 s on alpine:3.19 with warmed DB. Image‑unpack fallback stays ≤ 10 s for 200 MB images.

sequenceDiagram
    participant CI as CI/CD Pipeline (Stella CLI)
    participant SB as SBOM Builder
    participant CORE as Stella Core
    participant REDIS as Redis Queue
    participant RUN as Scanner Runner (e.g., Trivy)
    participant POL as Policy Evaluator

    CI->>SB: Invoke SBOM Generation
    SB->>CORE: Check Missing Layers (/layers/missing)
    CORE->>REDIS: Query Layer Diff (SDIFF)
    REDIS-->>CORE: Missing Layers List
    CORE-->>SB: Return Missing Layers
    SB->>SB: Generate Delta SBOM
    SB->>CORE: Upload SBOM Blob (POST /scan(sbom))
    CORE->>REDIS: Enqueue Scan Job
    REDIS->>RUN: Fan Out to Runner
    RUN->>RUN: Perform Vulnerability Scan
    RUN-->>CORE: Return Scan Results
    CORE->>POL: Evaluate Mute Policies
    POL-->>CORE: Policy Verdict
    CORE-->>CI: JSON Verdict & Progress Stream
    Note over CORE,CI: Achieves ≤5s P95 with Warmed DB

4.2 Delta SBOM

Builder collects layer digests. POST /layers/missing → Redis SDIFF → missing layer list (< 20 ms). SBOM generated only for those layers and uploaded.

4.3 Feed Enrichment

sequenceDiagram
    participant CRON as Nightly Cron (Hangfire)
    participant FM as Feed Merger
    participant NVD as NVD Feed
    participant OSV as OSV Plugin (Optional)
    participant GHSA as GHSA Plugin (Optional)
    participant REGC as Regional Catalogue Plugin (Optional)
    participant REDIS as Redis (Merged Feed Storage)
    participant UI as Web UI

    CRON->>FM: Trigger at 00:59
    FM->>NVD: Fetch & Merge NVD Data
    alt Optional Plugins
        FM->>OSV: Merge OSV Feed
        FM->>GHSA: Merge GHSA Feed
        FM->>REGC: Merge Regional Catalogue Feed
    end
    FM->>REDIS: Persist Merged Feed
    REDIS-->>UI: Update Feed Freshness
    UI->>UI: Display Green 'Feed Age' Tile

4.4 Identity & Auth Flow

OpenIddict issues JWTs via client‑credentials or password grant. An IIdentityProvider plug‑in can delegate to LDAP, SAML or external OIDC without Core changes.

5 · Runtime Helpers

HelperFormPurposeExtensible Bits
Stella CLIDistroless CLIGenerates SBOM, calls /scan, honours threshold flag--engine, --pdf-out piped to plug‑ins
ZastavaStatic Go binary / DaemonSetWatches Docker/CRI‑O events; uploads SBOMs; can enforce gatePolicy plug‑in could alter thresholds

6 · Persistence & Cache Strategy

StorePrimary UseWhy chosen
Redis 7Queue, SBOM cache, Trivy DB mirrorSub‑1 ms P99 latency
MongoDBHistory > 180 d, audit logs, policy versionsOptional; document‑oriented
Local tmpfsTrivy layer cache (/var/cache/trivy)Keeps disk I/O off hot path
flowchart LR
    subgraph "Persistence Layers"
        REDIS[(Redis: Fast Cache/Queues
Sub-1ms P99)] MONGO[(MongoDB: Optional Audit/History
>180 Days)] TMPFS[(Local tmpfs: Trivy Layer Cache
Low I/O Overhead)] end CORE["Stella Core"] -- Queues & SBOM Cache --> REDIS CORE -- Long-term Storage --> MONGO TRIVY["Trivy Scanner"] -- Layer Unpack Cache --> TMPFS style REDIS fill:#fdd,stroke:#333 style MONGO fill:#dfd,stroke:#333 style TMPFS fill:#ffd,stroke:#333

7 · Typical Scenarios

#FlowSteps
S‑1Pipeline Scan & AlertStella CLI → SBOM → /scan → policy verdict → CI exit code & link to Scan Detail
S‑2Mute Noisy CVEDev toggles Mute in UI → rule stored in Redis → next build passes
S‑3Nightly Re‑scanSbomNightly.Schedule re‑queues SBOMs (mask‑filter) → dashboard highlights new Criticals
S‑4Feed Update CycleFeedMerge Service merges feeds → UI Feed Age tile turns green
S‑5Custom Report GenerationPlug‑in registers IReportRenderer/report/custom/{digest} → CI downloads artifact
sequenceDiagram
    participant DEV as Developer
    participant UI as Web UI
    participant CORE as Stella Core
    participant REDIS as Redis
    participant RUN as Scanner Runner

    DEV->>UI: Toggle Mute for CVE
    UI->>CORE: Update Mute Rule (POST /policy/mute)
    CORE->>REDIS: Store Mute Policy
    Note over CORE,REDIS: YAML/Rego Evaluator Updates

    alt Next Pipeline Build
        CI->>CORE: Trigger Scan (POST /scan)
        CORE->>RUN: Enqueue & Scan
        RUN-->>CORE: Raw Findings
        CORE->>REDIS: Apply Mute Policies
        REDIS-->>CORE: Filtered Verdict (Passes)
        CORE-->>CI: Success Exit Code
    end
sequenceDiagram
    participant CRON as SbomNightly.Schedule
    participant CORE as Stella Core
    participant REDIS as Redis Queue
    participant RUN as Scanner Runner
    participant UI as Dashboard

    CRON->>CORE: Re-queue SBOMs (Mask-Filter)
    CORE->>REDIS: Enqueue Filtered Jobs
    REDIS->>RUN: Fan Out to Runners
    RUN-->>CORE: New Scan Results
    CORE->>UI: Highlight New Criticals
    Note over CORE,UI: Focus on Changes Since Last Scan

8 · UI Fast Facts

  • Stack – Angular 17 + Vite dev server; Tailwind CSS.
  • State – Signals + RxJS for live scan progress.
  • i18n / l10n – JSON bundles served from /locales/{lang}.json.
  • Module Structure – Lazy‑loaded feature modules (dashboard, scans, settings); runtime route injection by UI plug‑ins (road‑map Q2‑2026).

9 · Cross‑Cutting Concerns

  • Security – containers run non‑root, CAP_DROP:ALL, read‑only FS, hardened seccomp profiles.
  • Observability – Serilog JSON, OpenTelemetry OTLP exporter, Prometheus /metrics.
  • Upgrade Policy/api/v1 endpoints & CLI flags stable across a minor; breaking changes bump major.

10 · Performance & Scalability

ScenarioP95 targetBottleneckMitigation
SBOM‑first≤ 5 sRedis queueMore CPU, increase ScannerPool.Workers
Image‑unpack≤ 10 sLayer unpackPrefer SBOM path, warm Docker cache
High concurrency40 rpsRunner CPUScale Core replicas + side‑car scanner services

11 · Future Architectural Anchors

  • ScanService micro‑split (gRPC) – isolate heavy runners for large clusters.
  • UI route plug‑ins – dynamic Angular module loader (road‑map Q2‑2026).
  • Redis Cluster – transparently sharded cache once sustained > 100 rps.

12 · Assumptions & Trade‑offs

Requires Docker/CRI‑O runtime; .NET 9 available on hosts; Windows containers are out‑of‑scope this cycle.
Embedded auth simplifies deployment but may need plug‑ins for enterprise IdPs.
Speed is prioritised over exhaustive feature parity with heavyweight commercial scanners.


13 · References & Further Reading

(End of High‑Level Architecture v2.2)