Connectors

The Connector Catalog

The generated provider inventory, parity matrix, categories and release stages, colocated provider layout, and code generators.

The catalog is Ductor's action inventory — the governed set of typed actions the executed stage draws on. Ductor combines imported catalog metadata with hand-authored Go implementations. Rather than list every provider here — the set grows continuously — this page explains how the catalog is organized, how to discover providers programmatically, and how the inventory and provider sources are laid out on disk.

The public directory's generated offline seed currently contains 871 providers and exposes 11,726 action contracts: 11,499 executable actions and 227 catalog-only actions whose runtime implementation is still pending. These values are calculated from the same committed snapshot used to seed the web catalog, so refreshing that snapshot also updates this page at build time. Live deployment counts can differ because the API always reflects the exact binary you built.

Browse the live catalog

The authoritative, always-current directory is at ductor.io/connectors, backed by the JSON API at ductor.io/api/connectors. Provider icons are served at https://cdn.ductor.io/providers/<key>.svg. The API endpoints below return the catalog from your deployment, reflecting exactly the providers your binary was built with.

The provider inventory and parity matrix

Two documents describe the shipped catalog, and both are generated — never hand-edit them:

  • docs/connector-system/provider-inventory.md — one row per provider, with its source, parity tier, and capability flags (OAuth, refresh, shared webhook, dynamic props, poll triggers, delivery triggers). Generated by connectorbootstrapgen.
  • docs/connector-system/15-parity-matrix.md — cross-references Ductor's providers against the donor catalogs. Generated by go run ./internal/cmd/connectorparitymatrix.

Generated files are regenerated, not hand-edited

provider-inventory.md, the parity matrix, and the cmd/ductor/fx_connector_generated_*.go wiring files are deterministic outputs. Editing them by hand is always wrong — regenerate instead (see The generators below). Parallel branches that each add a provider will conflict in these files textually; resolve by re-running the generators after merge, never by hand-merging.

Parity tiers

Each inventory row carries a parity tier recording how completely the provider is implemented. Imported providers land at:

TierMeaning
importedMetadata imported from a donor catalog (auth, base URL, scopes) with no curated actions yet.
partialSome curated actions/triggers on top of imported metadata.
object_tierImplements the normalized object API (get/list/search/create/update records).

Hand-authored Go providers additionally carry richer tiers such as full and native. The bulk of the catalog is imported today, with partial and object_tier providers growing as authors curate them.

Parity tier vs. parity-matrix status

Don't confuse the inventory's parity tier with the parity matrix's status column. The matrix compares Ductor against donors and labels each row covered, gap, or ductor-only (Ductor ships it but the compared donor catalogs don't). ductor-only is a comparison status, not an implementation tier — an imported provider can still be ductor-only.

Parity tier is not a pricing tier

A parity tier is an implementation completeness signal, and it ships today. It is not a price. A separate pricing tier (free, included, standard, premium, metered) exists in the pricing engine, and a certified/community assurance tier is a third axis that is not built at all — three independent signals that should never be read as one. Today the catalog surfaces none of them but parity: it carries no prices, and nothing here bills per action.

Categories

Every provider declares one or more Category values (domain/connector/provider.go). The taxonomy has 39 categories:

crmmarketingnotificationai
telephonyenrichmentpaymentdata_warehouse
file_storagedev_toolsinternaldatabase
analyticsproductivityhraccounting
atssocialdesignerp
iammcplegalknowledge_base
storagevideoinvoicingsurveys
cmsbankingticketingsupport
communicatione_commercegamingsearch
sportsother

Release stages

A provider's maturity is a ReleaseStage: alpha, beta, generally_available, or deprecated. A provider may also set the boolean Deprecated flag with a DeprecationMessage. Tenant provider policy can require a minimum release stage before a connection may be created — see Policies, Quotas & Audit.

Discovering providers, actions, and triggers

The management API exposes read-only catalog endpoints under /api/v2/connector/ (service ConnectorService):

# List providers (paginated; page_size 0-100), optionally filtered.
curl 'https://your-host/api/v2/connector/providers?categories=crm&page_size=50' \
  -H 'Authorization: Bearer <token>'
# → { "providers": [ { "key": "hubspot", "display_name": "HubSpot", ... } ], "next_page_token": "..." }

# Get one provider by key.
curl https://your-host/api/v2/connector/providers/hubspot -H 'Authorization: Bearer <token>'

# Actions for a provider, and one action's full spec (input properties, output schema, semantics).
curl 'https://your-host/api/v2/connector/actions?provider_key=hubspot' -H 'Authorization: Bearer <token>'
curl https://your-host/api/v2/connector/actions/hubspot.create_contact -H 'Authorization: Bearer <token>'

# Triggers for a provider, and one trigger's spec.
curl 'https://your-host/api/v2/connector/triggers?provider_key=hubspot' -H 'Authorization: Bearer <token>'
curl https://your-host/api/v2/connector/triggers/hubspot.contact_created -H 'Authorization: Bearer <token>'

Fetching a single action returns its input Properties, OutputSchema, Semantics, required OAuth scopes, provider-native permissions, related action keys, and runtime availability — enough to render a form, validate arguments, explain setup requirements, and know whether the action is safe to retry or can run at all. The registry keeps live counts (ProviderCount, ActionCount, TriggerCount, ModelCount, MapperCount) via RegistryStats (application/connector/registrar.go), which is what the catalog surfaces report.

Action contracts and runtime availability

Catalog enrichment is additive. A curated contract always wins; imported metadata fills only missing scopes, input schemas, output schemas, provider permissions, and action relationships. It never replaces a native request handler or rewrites an existing execution contract.

FieldWhat it tells you
propertiesThe action's input fields, including nested object and array fields.
output_schemaJSON Schema for the provider response. Builders use it for downstream output completion and type checks.
required_scopesOAuth scopes the selected connection must grant before execution.
provider_permissionsProvider roles, products, or grants configured outside the OAuth consent screen. These are setup guidance, not OAuth scopes.
relationsUseful follow-up actions and optional start/status/cancel operations for long-running provider work.
runtime_statusexecutable, metadata_only, needs_runtime, or blocked_by_policy.
runtime_reasonA stable explanation for a non-executable status, such as catalog_runtime_translation_required or dynamic_endpoint.

An action count is not an executability count

Catalog-only actions are intentionally visible so builders and agents can discover their schemas and requirements. The action executor still rejects them. Check runtime_status == "executable" before presenting an operation as runnable.

The catalog reflects your build

Providers are Go code compiled into the binary — there is no runtime provider loader — so the providers available in your deployment are exactly the ones bundled at build time. The live directory on ductor.io shows the full upstream catalog; your instance shows what you shipped.

The colocated provider layout

New providers are authored entirely inside their own directory — one directory = one provider = complete truth — so any number of providers can be authored on parallel branches without touching a shared authored file (docs/connector-system/16-provider-authoring.md):

provider.yaml — bootstrap manifest entry (wiring, + optional provider block)
doc.go — package doc
provider.go — dc.Provider definition (auth types, action/trigger keys)
client.go — shared connector HTTP client wiring
auth.go — credential/OAuth resolution + testAuth hook
register.go — wires the provider + actions/triggers into the registries
upstream.yaml — provenance + per-action parity status
corpus.curated.json — optional additive action/schema/permission overlay

One key, one manifest, one corpus

A provider key must appear in exactly one manifest (colocated or central) and exactly one corpus source (colocated corpus.json or gen/connector-actions/<key>.json). Duplicate manifest keys fail connectorbootstrapgen; duplicate corpus keys fail scripts/sync-connector-corpus.sh. This is the most common way to break the generators.

The code generators

Authoring flows through a small set of generators — never edit the wiring or inventory by hand:

  • internal/cmd/connectorscaffoldgen (and tools/connectorgen) — scaffold a new provider package plus its colocated provider.yaml.
  • internal/cmd/connectorbootstrapgen — regenerate the wiring and provider inventory. Run it via go generate ./cmd/ductor/...; colocated manifests are picked up through the infrastructure/connector/providers/*/provider.yaml glob.
  • tools/connector-icons — stage a provider's brand SVG; once uploaded to R2 it serves at https://cdn.ductor.io/providers/<key>.svg, which the manifest's icon_url must use.

The public site keeps a committed offline seed for boot-time ingestion. Refresh it from sibling backend and frontend checkouts after connector corpus changes:

cd ductor-frontend
pnpm --filter @ductor-frontend/db run catalog:sync-connectors:write
pnpm --filter @ductor-frontend/db run catalog:sync-connectors

The sync resolves provider aliases, merges base and curated corpora with the same gap-only rules as the backend, retains native action contracts, updates action counts, and rejects forbidden source branding. Set DUCTOR_REPO when the backend is not checked out at ../ductor.

Validate the result with make connector-manifest-validate and the provider contract tests under infrastructure/connector/providers/.

Where to go next