Industrial device control plane

The control plane your industrial fleet actually deserves.

Connect OPC-UA, Sparkplug B, Modbus and MQTT to one lean platform where every device is its own identity — and every tenant its own sealed world. Run it at the edge or in your data center.

10k
concurrent devices
49.7ms
p99 ingest latency
601µs
device revocation
tenant · demo-plant-01 / live LIVE
turbine.rpm
bus.voltage
coolant.degC
t/demo-plant-01/d/turbine-A7 10,000 devices connected
Speaks your plant's protocols on day one — as confined, single-device connectors
Modbus/TCP OPC-UA Sparkplug B MQTT Unified Namespace gateway
Industrial connectivity, natively

Speak your plant's protocols on day one.

Modbus/TCP, OPC-UA and Sparkplug B ship as confined connectors — each carrying the authority of exactly one device. A Unified Namespace gateway turns one Sparkplug edge into many isolated identities, with no shared gateway credential to compromise.

  • Modbus/TCP, OPC-UA and Sparkplug B ship on a frozen connector SDK — a new protocol adds zero new core attack surface.
  • Southbound writes verified against 15+ hostile vectors — injection, null-byte, oversized names, type confusion — all blocked at the wire.
1 connector modbus_tcp
2   scope: one_device
3   sdk: frozen
4   // +opcua +sparkplug — zero new core surface
15+ hostile vectors blocked Modbus · OPC-UA · Sparkplug B
Isolation you can prove

Separation your auditor can see, not just trust.

Tenant isolation is enforced in the database with Row-Level Security and in the type system, where a missing tenant filter simply fails to compile. It held through an RLS-drop, through Timescale compression, and through nine evasion attempts.

  • PostgreSQL RLS ENABLE + FORCE from the first migration, proven on a real non-superuser, NOBYPASSRLS role — zero rows leak across tenants.
  • Per-tenant Grafana isolation withstood 9 evasion vectors on a real read-only login.
1 async fn telemetry(ctx: &TenantCtx)
2   // tenant is mandatory, by type
3   let rows = repo. query(ctx).await?;
4  
5 error[E0061]: missing `ctx: &TenantCtx`
6   a query without a tenant does not compile
0 rows cross-tenant RLS FORCE non-superuser proven
A control plane that stays up

Devices keep connecting — even when the control plane blinks.

Authentication happens inside the broker at CONNECT, with a last-known-good key set and zero control-plane round-trip on the hot path. At ten thousand concurrent devices we measured a 49.7 ms p99, and a full reconnect storm recovered every single client.

  • 10,000 concurrent devices at ~5,400 msg/s QoS1 → p99 49.7 ms, 20x under the sub-second target.
  • A 10,000-client reconnect storm recovered 10,000 / 10,000; live key rotation drops zero established sessions.
p99 latency 49.7ms
reconnect 100%
key rotation 0 drops
CP-call / CONNECT 0
broker-local JWKS last-known-good STRICT
Trustworthy device identity

Every device is a short-lived, revocable identity.

Per-device JWTs — and internal-CA mTLS where you need it — bind each device to its tenant by construction, never from a request body. Revoke a compromised device in well under a millisecond, with no residual-access window and no OpenSSL in the transport path.

  • Bounded-latency revocation — device kick measured at 601 µs, far under the 30 s target.
  • Memory-safe TLS via rustls + aws-lc-rs — zero OpenSSL, an entire class of transport CVEs designed out of the device path.
601µs
measured kick-on-revoke · target < 30s
RS256
per-device JWT
mTLS
internal CA
0
residual window
Lean by design

A platform, not a data-center project.

Single Rust binaries, an embedded broker, an in-process rule engine — no external stream processor, no extra message bus. Author a new device type from documentation alone in under a day, and run the whole thing on modest hardware.

  • Device types are declarative YAML — a new type + connector authored from docs in under a day, no compile, no per-type table, no plugin deploy.
  • Distroless, non-root runtime image ~20 MB (uid 65532, no shell); a full database restore drill completed in ~391 ms.
1 device_type: turbine.v2
2   metrics: [rpm, voltage, coolant]
3   connector: modbus_tcp
4   // declarative — no compile, no plugin deploy
distroless ~20 MB uid 65532 · no shell restore drill 391 ms
The platform

Everything an industrial fleet needs — in one lean binary.

No external stream processor, no extra message bus, no data-center project. A control plane you can actually run.

Native industrial protocols

Modbus/TCP, OPC-UA and Sparkplug B as confined, single-device connectors on a frozen SDK.

Unified Namespace gateway

One Sparkplug edge, many cryptographically isolated identities — no shared gateway principal.

Database-enforced isolation

RLS FORCE on a non-superuser role; cross-tenant access is a compile error, not a runtime check.

Broker-local device auth

JWT + internal-CA mTLS validated in-process — zero control-plane call per CONNECT.

In-process rule engine

Threshold, window, absence and geofence over lossless persisted data — no external CEP.

Telemetry + dashboards built in

TimescaleDB hypertables with per-tenant Grafana provisioned automatically.

Pricing → conversation

Bring your fleet into one control plane.

Tell us your protocols, your sites and your scale — we'll show you Spectors on your terms.

Talk to us →