> ## Documentation Index
> Fetch the complete documentation index at: https://www.composer.id/llms.txt
> Use this file to discover all available pages before exploring further.

# How composerID connects

> The five ways composerID reaches a destination, the minimum destination standard, and when a client incurs cost or configuration change.

This page describes how a published decision gets into a destination system: the five transports, the minimum a destination must offer, and where cost or a configuration change can arise. It is for integration leads and architects planning a deployment.

Every destination is different. Some expose open developer APIs, some licence API access separately, some accept no inbound push at all, and some tenants are configured so strictly that no integration can create a record until the configuration changes.

## Every path carries the Intent ID

Whichever transport a deployment uses, the record that lands in the destination carries the same `intent_id`, and the publish receipt lands on the same audit spine: the append-only [intent timeline](/concepts/events) that every step composerID takes is written to. The transport is an implementation choice, not a different product.

```mermaid theme={"system"}
flowchart LR
  C["composerID"]
  D["Destination system"]
  C -->|"1 Direct API"| D
  C -->|"2 Signed webhooks"| M["Client middleware"]
  M --> D
  C -->|"3 API pull"| Y["Your integration code"]
  Y --> D
  C -->|"4 iPaaS recipe"| I["Client iPaaS connector"]
  I --> D
  C -->|"5 Assisted publish"| H["Requester in the vendor UI"]
  H --> D
  D -.->|"intent_id on the record, receipt on the audit spine"| C
```

<Info>
  The Intent API (`api.composer.id/v1`) is composerID's own REST contract, and it is the name this page and the rest of these docs use for it. Today it is served by the reference sandbox; the production service behind `api.composer.id` is in build. See the [API reference](/api-reference/overview).
</Info>

## The five connection methods

The methods are ordered by how much of the loop composerID runs for you. A deployment can mix methods per destination, and the [Channel Map](/concepts/publishing), the rules that say which kind of work goes to which destination, records which method each destination uses.

<AccordionGroup>
  <Accordion title="1. Direct API (adapter publish)" description="composerID adapter to the destination's own API" icon="plug">
    The default. composerID's adapter authenticates to the destination's own API, maps the canonical intent through the tenant's [MappingProfile](/concepts/schemas), the template that translates canonical fields into one destination's API dialect, and writes the record idempotently. This gives the best fidelity: native objects, native validation, and external IDs returned on the receipt.

    <Warning>
      On some enterprise platforms API access is licensed separately. Confirm what the client's contract includes before planning a machine path: see [when the client incurs cost](#when-the-client-incurs-cost-or-configuration-change).
    </Warning>
  </Accordion>

  <Accordion title="2. Signed webhooks (composerID pushes to you)" description="composerID to endpoints you register" icon="webhook">
    composerID emits HMAC-SHA256-signed events to endpoints you register: middleware, an iPaaS trigger, or a reporting suite. The Intent API declares four outbound events (`vms.requisition.updated`, `vms.assignment.updated`, `vms.timesheet.updated`, `vms.connection.revoked`). Publish receipts, drift reports and enrichment gaps are not among them: you read those from the API and the timeline instead. Your side decides what happens next.

    <Warning>
      Webhooks reach systems you control. Most destination platforms expose no general inbound webhook endpoint for record creation, so the write into the destination still happens through method 1, 3 or 4.
    </Warning>
  </Accordion>

  <Accordion title="3. Intent API (you pull from us)" description="Your code to api.composer.id" icon="code">
    Your integration team calls the Intent API at `api.composer.id/v1` to read intents, receipts and timelines, then handles the last mile in code you own. This is the right shape when an internal platform team already runs destination integrations.

    <Warning>
      Reconciliation becomes your responsibility. Poll the timeline or subscribe to webhooks (method 2) so drift is caught.
    </Warning>
  </Accordion>

  <Accordion title="4. Client iPaaS and third-party connectors" description="composerID to an iPaaS recipe to a certified connector" icon="git-branch">
    composerID triggers a recipe on the integration platform the client already runs (Workato, MuleSoft Anypoint, Boomi, SnapLogic, Celigo, Tray.ai, Microsoft Power Automate / Logic Apps) and the platform's certified connector performs the write. Unified-API layers (Merge, Apideck) and lighter tools (Zapier, Make) fit smaller estates. Procurement orchestration platforms (Zip, ORO Labs) can also carry the publish as part of an orchestrated flow.

    <Warning>
      Recipe volume consumes the client's iPaaS subscription, and connector coverage and field depth vary by platform and tier.
    </Warning>
  </Accordion>

  <Accordion title="5. Assisted publish (deep link and prefill)" description="A deep link into the vendor UI that a human completes" icon="external-link">
    The universal fallback. composerID renders a one-click deep link into the destination with the Intent ID and the decided values, and a human completes the record in the vendor UI. It needs no destination configuration and no vendor licence cost, is available from the start of a deployment, and the record is still anchored to the audit spine.

    <Warning>
      The external ID is captured on confirmation rather than returned on an API receipt, so reconciliation is manual or poll-based.
    </Warning>
  </Accordion>
</AccordionGroup>

### Choosing per destination

The choice is made once per destination during connection, recorded in the Channel Map, and revisited only when the destination's posture changes. Use method 1 where the licence allows it, method 4 where an iPaaS already owns that system, and method 5 wherever a machine path is not viable yet. Each destination page states the posture that can be defended from that vendor's documentation.

| Method                | Transport                                         | Destination prerequisites                            | Where cost can arise                                       |
| --------------------- | ------------------------------------------------- | ---------------------------------------------------- | ---------------------------------------------------------- |
| 1. Direct API         | composerID adapter to destination API             | API access enabled; integration user or OAuth client | API access licensed separately on some platforms           |
| 2. Signed webhooks    | composerID to endpoints you register              | None (your endpoint, not the destination's)          | Internal build and hosting of the receiver                 |
| 3. Intent API         | Your code to `api.composer.id`                    | None                                                 | Internal integration engineering                           |
| 4. iPaaS / connectors | composerID to iPaaS recipe to certified connector | Connector configured against the tenant              | iPaaS subscription or task volume; premium connector tiers |
| 5. Assisted publish   | Deep link and prefill into the vendor UI          | None                                                 | None (a human completes the record)                        |

## What composerID asks of a destination

There is a minimum contract for a destination to sit on the automated path, and a defined fallback when it cannot. The target for any destination of record is Tier B or better. Tier C is a fallback, not an end state.

| Tier   | The destination provides                                                                                                                                      | What composerID runs                                                                                     | Reconciliation                                                 |
| ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------- |
| Tier A | An inbound create/update API; an external-reference field that carries a 10 to 64 character ID (the `intent_id`); events or a queryable change feed back out. | The full loop: plan, preflight, publish, back-sync.                                                      | Automatic: events normalised into the `WebhookEvent` envelope. |
| Tier B | An inbound create/update API and an external-reference field, but no usable events out.                                                                       | Publish as Tier A; reconciliation switches to scheduled polling on the destination's change timestamps.  | Poll-based; drift flagged against the canonical intent.        |
| Tier C | No usable inbound path: no API in the licence, an unpurchased API SKU, or tenant configuration that blocks machine creation.                                  | Assisted publish (deep link and prefill), a client iPaaS connector, or the managed-programme (MSP) path. | External ID captured on confirmation; manual or poll-based.    |

<Note>
  The `intent_id` written into the destination's external-reference field is what joins the destination record back to the decision, the [Compliance File](/concepts/compliance-file) and the timeline. A destination without any external-reference field can still be published to, but the join then lives only on composerID's side of the spine.
</Note>

## Two gates: vendor capability and tenant configuration

A destination that passes the tier test can still refuse a record. Tenants are routinely configured with dozens of mandatory fields, approval chains and picklists that any integration must satisfy before a record can exist. That is a configuration gate, not a connectivity gate, and composerID treats it as a first-class step.

<Steps>
  <Step title="Capabilities">
    `GET /v1/destinations/{id}/capabilities` reports what a connected destination supports: objects, auth, events posture and rate limits. This is the vendor gate.
  </Step>

  <Step title="Preflight">
    `POST /v1/preflight` validates a specific intent against the tenant's required fields, custom fields and picklists before anything is written. This is the configuration gate, surfaced before publish rather than discovered as a failed API call.
  </Step>

  <Step title="Enrichment">
    Gaps do not dead-end. A gap returns `422` with an `enrichment_request` body naming the missing canonical fields, the timeline records `enrichment.requested`, and Triage asks the requester the missing questions where they work, so the record arrives complete instead of the tenant being redesigned around the integration.

    When a tenant's mandatory-field load genuinely exceeds what intake should carry, the remaining option is a configuration change in the destination. That is an ownership and lead-time question, covered in the next section.
  </Step>
</Steps>

[Publishing](/concepts/publishing) describes the plan, preflight and publish steps in full.

## When the client incurs cost or configuration change

Most connections need neither budget nor a change request. The exceptions are predictable, and every one of them is visible before go-live: on the destination page, at capabilities, or at preflight.

| Scenario                                           | What changes, and who acts                                                                                                 | Cost signal                                                      | Typical lead time                 |
| -------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------------------- | --------------------------------- |
| Assisted publish only                              | Nothing in the destination; the deep link opens the vendor UI as the requester's own user.                                 | None                                                             | Immediate                         |
| Receive composerID webhooks or pull the Intent API | The client team stands up a receiver or scripts against `api.composer.id`; the destination is untouched.                   | Internal engineering time only                                   | Days                              |
| Standard API connection                            | The destination admin creates an integration user or OAuth client, allow-lists composerID and enables event subscriptions. | Usually included in the existing licence                         | Days                              |
| API access is a separate SKU                       | The vendor enables an API or integration module on the client's contract before any adapter can connect.                   | Vendor licence cost: confirm with the account team               | Weeks (commercial, not technical) |
| Publishing via the client's iPaaS                  | A recipe is built on the client's existing integration platform; the connector writes to the destination.                  | Consumes the existing iPaaS subscription (task or recipe volume) | Days to weeks                     |
| Tenant configuration change                        | Mandatory fields, approval chains or picklists are changed by the internal admin, the MSP or a vendor change request.      | Change-request cost varies: often MSP-managed                    | Weeks (governed change control)   |

<Tip>
  Add two questions to your integration discovery checklist:

  1. Does your destination licence include API access, or is it a separate SKU?
  2. Who owns configuration change requests to the destination (internal admin, MSP, vendor), and what is the typical lead time?
</Tip>

Machine paths are upgrades applied per destination when the licence and the tenant allow, not prerequisites for going live: assisted publish reaches every destination with no vendor cost and no destination configuration.

## Reconciliation follows the destination's posture

Humans keep working inside the destination after publish. How composerID notices depends on what the platform offers. All four postures normalise into the same `WebhookEvent` envelope and the same drift flags.

| Posture          | Meaning                                                                 | Reconciliation                                        |
| ---------------- | ----------------------------------------------------------------------- | ----------------------------------------------------- |
| Push events      | The platform delivers native webhooks or events on record change.       | Event-driven back-sync.                               |
| Push + poll      | Events exist but are partial or per-tenant; polling fills the gaps.     | Events where enabled; scheduled poll fallback.        |
| Poll-first       | No general event bus; records are re-read on change timestamps.         | Scheduled polling against the canonical intent.       |
| No native events | Neither events nor a change feed; relaying requires platform scripting. | Poll, or a relay built in the platform's own tooling. |

[Events](/concepts/events) covers the envelope, the timeline and drift detection.

## Reading a destination page

Every destination page opens the same way, and both opening blocks are derived from the registry that also drives the coverage tables and from the one carrier table the adapter reads, so the picture cannot drift from the code and stays defensible against the vendor's own documentation.

First a status line: the platform's category, its coverage status (Specification mapped, Documented or Roadmap) and whether the vendor's documentation is a public developer portal or gated behind a customer login.

Then an Integration path table, whose four rows are:

| Row                  | What it tells you                                                                                                                          |
| -------------------- | ------------------------------------------------------------------------------------------------------------------------------------------ |
| Authentication       | What the platform's API expects, in its own terms.                                                                                         |
| composerID publishes | The object composerID creates or updates, and the operation it calls.                                                                      |
| Intent ID lands on   | The one field that carries the Intent ID, and whether it is written into the destination record or held as a linkage on composerID's side. |
| Back-sync            | Webhooks where the platform pushes events, polling where it does not, or reads arranged at onboarding where it documents neither.          |

Read each row as one of two signals. Either it works from the vendor's documented posture with no special arrangement, or you plan for it: confirm a licence, schedule polling, or budget lead time. The second is a planning signal, not a blocker. The full API posture, the field mapping and the tenant caveats follow further down each page, under API posture and Publish target and field mapping.

## Next steps

<Columns cols={3}>
  <Card title="Publishing" icon="send" href="/concepts/publishing">
    Plan, preflight, publish, and the idempotency rules behind every write.
  </Card>

  <Card title="Destinations" icon="plug" href="/destinations">
    Every destination system, its posture and its coverage status.
  </Card>

  <Card title="Events" icon="webhook" href="/concepts/events">
    The `WebhookEvent` envelope, the timeline and reconciliation.
  </Card>
</Columns>
