Skip to main content

Built-in UI

Starting with v0.18, Conduit ships with a built-in web UI. It's a single-page React application (ConduitIO/conduit-ui) embedded directly into the conduit binary and served by conduit run at /. The UI's TypeScript client is generated from Conduit's served OpenAPI schema, so everything it does is a call to a documented HTTP API — there's no private back-channel between the UI and the engine.

What the UI is for

The UI's scope is deliberately narrow: observe and operate. It is not an authoring surface.

Observe

  • Live record flow. Watch records move through a running pipeline over the existing stream inspector RPCs, with a freeze toggle so you can stop the view on a busy pipeline and inspect a single record without dropping the stream.
  • Per-stage before/after diffs. For a record's position, see it at each stage (source → each processor's input/output → destination) as a field-level diff — exactly which fields a processor added, changed, or removed.
  • Pipeline graph. A topology view of one pipeline's source → processors → destination, with per-node status and live throughput.
  • Throughput, latency, and health, surfaced at the node so a genuinely idle pipeline reads differently from a stalled one.

Operate

  • Start and stop an existing pipeline. These map directly to the StartPipeline and StopPipeline RPCs (the same verbs behind conduit pipelines start / stop). Stopping asks for a confirming second action; starting does not.

That's the whole operate surface for v0.18. Start/stop is all the UI mutates.

Config-as-code stays the single source of truth

The UI does not create, edit, or delete pipelines, connectors, or processors. There is no drag-and-drop DAG editor and no config form. Pipelines are authored as configuration — YAML applied with conduit pipelines deploy / apply, the MCP server, or the library — and that configuration remains the single source of truth. Keeping authoring out of the UI is what keeps Conduit config-as-code and agent-native, rather than introducing a second, drifting source of truth.

Not in v0.18

The following are not UI features yet. Each depends on server-side work that has not shipped, so the UI deliberately does not expose them:

  • Pause — pause is a data-path decision (it must quiesce and checkpoint without losing in-flight records) and needs its own design before there's a verb to call.
  • Pipeline-scoped repair — today repair operates on YAML config text, not on a running pipeline, so there's no running-pipeline repair action to surface.
  • Dead-letter-queue record inspection — DLQ connectors aren't listable, so there's no record set for the UI to read.

If and when the server prerequisites land, the matching UI slices follow. Until then, they're out of scope, not hidden.

Accessing the UI

The UI is served on the same address as the HTTP API (:8080 by default). Start Conduit:

conduit run

Then open http://localhost:8080/ in a browser.

The UI is embedded in the binary and enabled by default. You can turn the route off with api.http.ui.enabled — the assets stay compiled into the binary, so disabling removes the surface, not the binary size:

conduit run --api.http.ui.enabled=false
No authentication

Conduit's HTTP API has no built-in authentication — the recommended posture is to bind to localhost or front the port with an authenticating proxy. Because the UI can start and stop pipelines, anyone who can reach the port can operate them. Don't expose the port on an untrusted network without a proxy in front of it.

Running against a separate UI dev server (CORS)

Conduit denies cross-origin browser requests by default. If you're developing against the UI from a separate dev server (for example a Vite server on http://localhost:5173), allow that origin explicitly with api.http.cors.allowed-origins:

conduit run --api.http.cors.allowed-origins=http://localhost:5173

The flag is repeatable and each value must be an exact scheme://host[:port] with no trailing slash and no path. * allows any origin but is refused on a non-loopback bind — for network deployments, list exact origins instead.

Pipeline status in the UI

Over the wire, a pipeline reports one of four statuses (the engine's internal states collapse to these on the API):

StatusMeaning
runningThe pipeline is processing records.
stoppedThe pipeline is not running — either an operator stopped it or the engine stopped it pending resume.
degradedThe pipeline hit an unrecoverable error; its latest error is shown inline.
recoveringThe engine is automatically attempting to recover the pipeline.

A stopped pipeline additionally carries a stopped-reason that distinguishes an operator stop from an engine stop, so the fleet view can tell "someone stopped this on purpose" from "this is waiting to be resumed."

How it fits together

The UI consumes only Conduit's documented HTTP surface — the same HTTP API you can call directly, the stream inspector websocket streams, and the metrics and health/readiness endpoints. Its route is registered so that /v1/*, /openapi/*, /healthz, /readyz, and the metrics endpoint continue to match first; the SPA only handles paths none of those claim.

scarf pixel conduit-site-docs-using