This is an automated email from the ASF dual-hosted git repository. obermeier pushed a commit to branch pr-4547 in repository https://gitbox.apache.org/repos/asf/streampipes.git
commit 0bbaade79eeb2dcb597036afaaf9899b6807757c Author: obermeier <[email protected]> AuthorDate: Fri Jun 12 14:58:47 2026 +0200 Update section numbering --- AGENTS.md | 6 ++--- SECURITY.md | 4 +-- THREAT_MODEL.md | 76 ++++++++++++++++++++++++++++++++++----------------------- 3 files changed, 50 insertions(+), 36 deletions(-) diff --git a/AGENTS.md b/AGENTS.md index 13937d6b7b..1680711dbb 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -52,12 +52,12 @@ Read **[SECURITY.md](SECURITY.md)** for how to report (`[email protected] code-execution by design**, not a sandbox. - An **adapter ingesting data from an external source** is the intended function; source trust and the handling guarantee for hostile ingested data - are spelled out in THREAT_MODEL.md (and are an open §14 question). + are spelled out in THREAT_MODEL.md (and are an open §11 question). - Transport security (TLS), network isolation, and extension vetting are **operator** responsibilities, not engine invariants. ### Step 3 — Route the finding -Route the finding to exactly one disposition in **THREAT_MODEL.md §13** +Route the finding to exactly one disposition in **THREAT_MODEL.md §10** (VALID, or one of the `OUT-OF-MODEL` / `BY-DESIGN` dispositions) and cite the section that justifies the call. This model is **v0** — open questions for the -PMC are in §14. +PMC are in §11. diff --git a/SECURITY.md b/SECURITY.md index 11f77abfea..ab99509c1a 100644 --- a/SECURITY.md +++ b/SECURITY.md @@ -36,7 +36,7 @@ properties StreamPipes upholds given its deployment assumptions versus those left to the operator (transport security, network isolation, extension vetting, source trust), and the recurring non-findings. Triagers of scanner, fuzzer, or AI-generated findings should route each through `THREAT_MODEL.md` -§13. +§10. This file is **v0** and carries open questions for the StreamPipes PMC in -`THREAT_MODEL.md` §14. +`THREAT_MODEL.md` §11. \ No newline at end of file diff --git a/THREAT_MODEL.md b/THREAT_MODEL.md index 810fda38ea..f994dfc8cd 100644 --- a/THREAT_MODEL.md +++ b/THREAT_MODEL.md @@ -21,7 +21,7 @@ > rubric, run with Claude Opus) for the Apache StreamPipes PMC to review, > correct, and own. Every non-trivial claim is provenance-tagged > *(documented)* / *(maintainer)* / *(inferred)*; the *(inferred)* tags are -> hypotheses, each with a matching question in §14. Written against the `dev` +> hypotheses, each with a matching question in §11. Written against the `dev` > branch; revise on a new public-facing surface (a new REST surface, adapter > class, auth mechanism, or broker integration), not on internal refactors. @@ -41,25 +41,25 @@ Apache StreamPipes is an **open-source Industrial IoT data platform** for connecting industrial data sources, building real-time streaming pipelines, and exploring time-series data *(documented: README)*. In-scope component families *(documented: root `AGENTS.md` architecture boundaries; roles -inferred — §14 Q1)*: +inferred — §11 Q1)*: | Component | Role | Primary surface | | --- | --- | --- | -| **`streampipes-rest`** | the HTTP/REST front door — auth, user/resource management, pipeline + adapter control | network (the primary untrusted boundary) *(inferred — §14 Q1)* | +| **`streampipes-rest`** | the HTTP/REST front door — auth, user/resource management, pipeline + adapter control | network (the primary untrusted boundary) *(inferred — §11 Q1)* | | **`streampipes-service-core`** | bootstrapping, **security**, migrations, scheduling *(documented: AGENTS.md)* | in-process | | **`*-management` modules** | business/domain logic (pipelines, adapters, data lake) | in-process | -| **Connect adapters (extensions)** | ingest data from **external** industrial sources (OPC-UA, MQTT, HTTP, files, DB, …) | the external-data ingestion boundary *(inferred — §14 Q2)* | -| **Pipeline elements (processors/sinks)** | run processing logic over the event streams; deployable as extensions | in-process / extension-runtime code *(inferred — §14 Q2)* | -| **Message broker + data lake** | event transport (Kafka/MQTT/NATS-class) and time-series persistence | intra-deployment infra *(inferred — §14 Q3)* | +| **Connect adapters (extensions)** | ingest data from **external** industrial sources (OPC-UA, MQTT, HTTP, files, DB, …) | the external-data ingestion boundary *(inferred — §11 Q2)* | +| **Pipeline elements (processors/sinks)** | run processing logic over the event streams; deployable as extensions | in-process / extension-runtime code *(inferred — §11 Q2)* | +| **Message broker + data lake** | event transport (Kafka/MQTT/NATS-class) and time-series persistence | intra-deployment infra *(inferred — §11 Q3)* | | **UI** (`ui/`) | browser client | client trust domain | StreamPipes is **not** a single hardened process: it is a multi-service deployment that depends on a message broker, a time-series/metadata store, and -the external data sources its adapters connect to *(inferred — §14 Q3)*. +the external data sources its adapters connect to *(inferred — §11 Q3)*. ## §3 — Adversaries in and out of scope -**In scope** *(inferred — §14 Q4)*: +**In scope** *(inferred — §11 Q4)*: 1. An **authenticated-but-limited UI/REST user** trying to act outside their role/permissions (read other users' pipelines, escalate, reach the host). @@ -68,7 +68,7 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. 3. A **malicious external data source** an adapter connects to, feeding hostile payloads into the ingestion path (see §7 for the boundary). -**Out of scope** *(inferred — §14 Q5)*: +**Out of scope** *(inferred — §11 Q5)*: 4. **An operator with host / container / broker / datastore access.** Anyone controlling the deployment infrastructure is not an adversary StreamPipes @@ -84,20 +84,20 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. - **Client (UI/API) → `streampipes-rest`** is the primary boundary: requests are authenticated and authorized against the user/role model before acting - *(inferred — §14 Q6)*. Whether request bodies, pipeline/adapter definitions, + *(inferred — §11 Q6)*. Whether request bodies, pipeline/adapter definitions, and configuration are treated as untrusted here is load-bearing for triage. - **Adapter → external data source** is a distinct boundary: the data an adapter ingests is **attacker-influenceable** in a way the REST surface is not, and the question is what StreamPipes guarantees about parsing/handling hostile ingested data versus what it passes through to downstream pipeline - elements *(inferred — §14 Q2)*. + elements *(inferred — §11 Q2)*. - **Inter-service / broker** boundaries are assumed to run inside an operator-controlled, network-isolated deployment perimeter *(inferred — - §14 Q3)*. + §11 Q3)*. ## §5 — What StreamPipes upholds (given §3/§4 assumptions) -*(all inferred — §14 Q7)* +*(all inferred — §11 Q7)* - **Authentication** of UI/REST sessions via the configured mechanism before privileged actions. @@ -108,7 +108,7 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. ## §6 — What StreamPipes leaves to the operator -*(inferred — §14 Q8)* +*(inferred — §11 Q8)* - **Transport security (TLS)** on the REST endpoint, the broker, and the datastore, and the security of those backing services themselves. @@ -121,7 +121,7 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. ## §7 — Properties StreamPipes does *not* uphold (by design) -*(inferred — §14 Q9)* +*(inferred — §11 Q9)* - **A sandbox around installed extensions** (custom adapters / processors / sinks). Deploying a pipeline element is deploying code that runs with the @@ -133,14 +133,14 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. affect a pipeline's behavior.** Adapters ingest whatever the source sends; whether StreamPipes claims any robustness guarantee on malformed/oversized ingested data, versus treating it as the operator's-source-trust problem, is - the key §14 question (Q2). + the key §11 question (Q2). - **Resource fairness as a hard guarantee** — a high-rate source or expensive pipeline can exhaust runtime resources; bounding it is an operator/config - concern *(inferred — §14 Q10)*. + concern *(inferred — §11 Q10)*. ## §8 — Key configuration levers (load-bearing) -*(all inferred — §14 Q11; confirm names + defaults)* +*(all inferred — §11 Q11; confirm names + defaults)* | Lever | Why it matters | | --- | --- | @@ -149,34 +149,48 @@ the external data sources its adapters connect to *(inferred — §14 Q3)*. | TLS on REST + broker + datastore | decides whether sessions/events are on the wire in clear. | | Extension installation policy | decides who may deploy adapter/processor code into the runtime. | -## §11a — Known non-findings (seed for scanner/AI triage) +## §9 — Known non-findings (seed for scanner/AI triage) -Confirm and extend *(inferred — §14 Q12)*: +Confirm and extend *(inferred — §11 Q12)*: - **"A custom adapter / processor can run arbitrary code."** By design — installing an extension is an authorized code deployment, not a sandbox escape. `BY-DESIGN`. - **"An adapter accepts data from an untrusted external source."** That is the intended function; in-model only if StreamPipes claims a parsing/handling - guarantee the report violates (§14 Q2). Otherwise the source's + guarantee the report violates (§11 Q2). Otherwise the source's trustworthiness is the operator's concern. - **"The default/initial admin or an unauthenticated endpoint is reachable."** In-model only against the shipped default; an operator-loosened auth config - is `OUT-OF-MODEL: non-default-build` (confirm the shipped default in §14). + is `OUT-OF-MODEL: non-default-build` (confirm the shipped default in §11). - **Dependency-tail CVEs** (broker client, OPC-UA/MQTT library, a transitive JAR) from an SCA scanner — triage upstream unless StreamPipes' own code reaches the vulnerable path with untrusted input. -## §13 — Triage dispositions +## §10 — Triage dispositions -A finding is **VALID** only when all hold: the violated property is one -StreamPipes claims (§5), the attacker is in scope (§3), and the affected code -is on an in-model surface (§2/§4) reached by untrusted input. Otherwise route -to one of: `OUT-OF-MODEL: adversary-not-in-scope` · `OUT-OF-MODEL: -equivalent-harm` · `OUT-OF-MODEL: unsupported-component` · `OUT-OF-MODEL: -non-default-build` · `BY-DESIGN: property-disclaimed`. +Route every finding to **exactly one** disposition below and cite the +justifying section named in parentheses. -## §14 — Open questions for the StreamPipes PMC +A finding is **VALID** only when **all** hold: the violated property is one +StreamPipes claims (**§5**), the attacker is in scope (**§3**), and the +affected code is on an in-model surface (**§2/§4**) reached by untrusted input. + +Otherwise route to exactly one of: + +- `OUT-OF-MODEL: adversary-not-in-scope` — the attacker is excluded by **§3**. +- `OUT-OF-MODEL: equivalent-harm` — the attacker already holds equivalent + capability, so the property is not one StreamPipes upholds (**§7**). +- `OUT-OF-MODEL: unsupported-component` — the affected surface is not a + modeled component (**§2**); e.g. broker, data lake, or other + perimeter-internal infrastructure. +- `OUT-OF-MODEL: non-default-build` — the issue depends on a non-default + configuration lever (**§8**); e.g. operator-disabled TLS, loosened auth, or + an unvetted installed extension. +- `BY-DESIGN: property-disclaimed` — the property is one StreamPipes + explicitly does not uphold (**§7**); e.g. installed-extension code execution. + +## §11 — Open questions for the StreamPipes PMC Grouped in waves; answer inline. Each promotes an *(inferred)* tag to *(maintainer)*. @@ -212,7 +226,7 @@ Grouped in waves; answer inline. Each promotes an *(inferred)* tag to initial-admin/auth setup and whether any endpoint is unauthenticated by default. 12. What do scanners/fuzzers/researchers most often report that you consider a - non-finding? (Feeds §11a.) + non-finding? (Feeds §9.) **Wave 4 — meta** 13. StreamPipes has a root `AGENTS.md` but no `SECURITY.md`/`THREAT_MODEL.md`;
