REST API for the Data Exchange domain — the facade for all interactions between the blueprint and external agencies and data sources (IRS, SSA, USCIS SAVE, state wage databases, and others).
Calling domains initiate service calls by POSTing to /service-calls. The request carries no PII — adapters retrieve sensitive fields from the source domain using requestingResourceId and the resource type declared in the ExternalService catalog. Results are delivered via the data_exchange.call.completed event and queryable via the event log.
Context passthrough: calling domains attach namespace-keyed metadata to a service call (e.g., PUT /service-calls/{id}/metadata/intake) before or at submission. That metadata is echoed back in the result event so the calling domain's rules can route the result to the right record.
Status: Alpha — Breaking changes expected.
Base URL: https://api.example.com/data-exchange
Services
ExternalService catalog — the configured external data sources available in this deployment.
▶
GET
/services
List external services
#
Retrieve the catalog of external services available in this deployment. All entries are config-managed — defined in data-exchange-config.yaml and seeded at startup. States add entries via overlay; no write endpoints are provided.
Parameters
| Name |
Type |
In |
Req |
Description |
| ▶q |
string |
query |
|
Search query using field:value syntax. Multiple conditions separated by |
Search query using field:value syntax. Multiple conditions separated by spaces are ANDed together. URL Encoding: This parameter must be URL-encoded when sent over HTTP. Most HTTP clients handle this automatically. Examples in this documentation show human-readable syntax for clarity. Syntax| Pattern | Description | Example |
|---|
term | Full-text exact match | john | term | Full-text contains | john | term* | Full-text starts with | john* | *term | Full-text ends with | *smith | field:value | Exact match on field | status:approved | field:value | Contains (case-insensitive) | name:john | field:value* | Starts with | name:john* | field:*value | Ends with | email:*@example.com | field:"value" | Quoted value (for spaces) | name:"john doe" | field.nested:value | Nested field (dot notation) | address.state:CA | field:>value | Greater than | income:>1000 | field:>=value | Greater than or equal | income:>=1000 | field:<value | Less than | income:<5000 | field:<=value | Less than or equal | income:<=5000 | field:val1,val2 | Match any value (OR) | status:approved,pending | -field:value | Exclude / negate | -status:denied | field:* | Field exists (not null) | email:* | -field:* | Field does not exist | -deletedAt:* |
Examplesjohn — exact match for "john" in searchable fieldsjohn — contains "john" in searchable fieldsname:smith — name contains "smith" (case-insensitive)email:*@example.com — email ends with "@example.com"status:approved — exact match on status fieldstatus:approved,pending — status is "approved" OR "pending"income:>=1000 — income greater than or equal to 1000created:>2024-01-01 — created after January 1, 2024status:approved income:>=1000 — approved AND income >= 1000 (multiple conditions)-status:denied — exclude records with status "denied"-deletedAt:* — only records where deletedAt does not existapplicant.state:CA — nested field filter
URL Encoding ReferenceWhen manually constructing URLs, encode these characters: | Character | Encoded |
|---|
| (space) | %20 or + | " | %22 | : | %3A | > | %3E | < | %3C | , | %2C |
Example: `` Human-readable: q=status:approved income:>=1000 URL-encoded: q=status%3Aapproved%20income%3A%3E%3D1000 `` |
| limit |
integer |
query |
|
Maximum number of items to return (1-100). |
| offset |
integer |
query |
|
Number of items to skip before collecting results. |
| ▶sort |
string |
query |
|
Comma-separated list of fields to sort the response by. Prefix a field |
Comma-separated list of fields to sort the response by. Prefix a field with - for descending order. The first field is the primary sort; subsequent fields are tie-breakers in declaration order. URL Encoding: This parameter must be URL-encoded when sent over HTTP. Most HTTP clients handle this automatically. Examples below show human-readable syntax for clarity. Which fields a given list endpoint allows is declared in the operation's x-sortable.fields extension. Sending a field name not present in that list returns 400 FIELD_NOT_SORTABLE. Sending a field name that doesn't exist on the resource schema returns 400 INVALID_SORT_FIELD. When this parameter is omitted, the operation's x-sortable.default (if declared) is applied; otherwise no client-driven sort is applied. A configured tie-breaker (default id) is always appended for stable pagination. See api-patterns.yaml#sorting for the full convention and docs/architecture/x-extensions.md for the extension shape. Syntax| Pattern | Description | Example |
|---|
fieldName | Ascending | sort=createdAt | -fieldName | Descending | sort=-createdAt | field1,field2 | Multi-field | sort=status,-priority | nested.field | Nested field via dot notation | sort=name.lastName |
Examplessort=createdAt — oldest firstsort=-createdAt — newest firstsort=-priority,dueDate — highest priority first, then oldest due datesort=name.lastName,name.firstName — alphabetical by surname, then given name
|
| serviceType |
▶ ServiceType |
query |
|
|
Responses
200
A paginated list of external services.
▶
ExternalServiceList
▶
items
array[ExternalService]
required
id
string (uuid)
required
Stable identifier. Referenced by ExternalServiceCall submissions.
name
string
required
Human-readable name (e.g., "SSA Composite via FDSH").
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
▶
defaultCallMode
CallMode
required
Default call mode for submissions against this service. Can be overridden per call.
No additional fields
programs
array[string]
required
Programs that use this service.
source
string
required
read-only
"system" entries are defined in data-exchange-config.yaml and cannot be deleted via the API. "user" entries are added by states at runtime.
enumsystem user
createdAt
string (date-time)
required
updatedAt
string (date-time)
required
400
The request is malformed or contains invalid parameters.
▶
BadRequest
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
▶
GET
/services/{serviceId}
Get an external service
#
Retrieve a single external service catalog entry by identifier.
Parameters
| Name |
Type |
In |
Req |
Description |
| serviceId |
string |
path |
✓ |
Unique identifier of the external service catalog entry. |
Responses
200
External service retrieved successfully.
▶
ExternalService
id
string (uuid)
required
Stable identifier. Referenced by ExternalServiceCall submissions.
name
string
required
Human-readable name (e.g., "SSA Composite via FDSH").
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
▶
defaultCallMode
CallMode
required
Default call mode for submissions against this service. Can be overridden per call.
No additional fields
programs
array[string]
required
Programs that use this service.
source
string
required
read-only
"system" entries are defined in data-exchange-config.yaml and cannot be deleted via the API. "user" entries are added by states at runtime.
enumsystem user
createdAt
string (date-time)
required
updatedAt
string (date-time)
required
404
The requested resource was not found.
▶
NotFound
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
ServiceCalls
External service call lifecycle — submission through resolution.
▶
GET
/service-calls
List service calls
#
Retrieve a paginated list of external service calls.
Parameters
| Name |
Type |
In |
Req |
Description |
| ▶q |
string |
query |
|
Search query using field:value syntax. Multiple conditions separated by |
Search query using field:value syntax. Multiple conditions separated by spaces are ANDed together. URL Encoding: This parameter must be URL-encoded when sent over HTTP. Most HTTP clients handle this automatically. Examples in this documentation show human-readable syntax for clarity. Syntax| Pattern | Description | Example |
|---|
term | Full-text exact match | john | term | Full-text contains | john | term* | Full-text starts with | john* | *term | Full-text ends with | *smith | field:value | Exact match on field | status:approved | field:value | Contains (case-insensitive) | name:john | field:value* | Starts with | name:john* | field:*value | Ends with | email:*@example.com | field:"value" | Quoted value (for spaces) | name:"john doe" | field.nested:value | Nested field (dot notation) | address.state:CA | field:>value | Greater than | income:>1000 | field:>=value | Greater than or equal | income:>=1000 | field:<value | Less than | income:<5000 | field:<=value | Less than or equal | income:<=5000 | field:val1,val2 | Match any value (OR) | status:approved,pending | -field:value | Exclude / negate | -status:denied | field:* | Field exists (not null) | email:* | -field:* | Field does not exist | -deletedAt:* |
Examplesjohn — exact match for "john" in searchable fieldsjohn — contains "john" in searchable fieldsname:smith — name contains "smith" (case-insensitive)email:*@example.com — email ends with "@example.com"status:approved — exact match on status fieldstatus:approved,pending — status is "approved" OR "pending"income:>=1000 — income greater than or equal to 1000created:>2024-01-01 — created after January 1, 2024status:approved income:>=1000 — approved AND income >= 1000 (multiple conditions)-status:denied — exclude records with status "denied"-deletedAt:* — only records where deletedAt does not existapplicant.state:CA — nested field filter
URL Encoding ReferenceWhen manually constructing URLs, encode these characters: | Character | Encoded |
|---|
| (space) | %20 or + | " | %22 | : | %3A | > | %3E | < | %3C | , | %2C |
Example: `` Human-readable: q=status:approved income:>=1000 URL-encoded: q=status%3Aapproved%20income%3A%3E%3D1000 `` |
| limit |
integer |
query |
|
Maximum number of items to return (1-100). |
| offset |
integer |
query |
|
Number of items to skip before collecting results. |
| ▶sort |
string |
query |
|
Comma-separated list of fields to sort the response by. Prefix a field |
Comma-separated list of fields to sort the response by. Prefix a field with - for descending order. The first field is the primary sort; subsequent fields are tie-breakers in declaration order. URL Encoding: This parameter must be URL-encoded when sent over HTTP. Most HTTP clients handle this automatically. Examples below show human-readable syntax for clarity. Which fields a given list endpoint allows is declared in the operation's x-sortable.fields extension. Sending a field name not present in that list returns 400 FIELD_NOT_SORTABLE. Sending a field name that doesn't exist on the resource schema returns 400 INVALID_SORT_FIELD. When this parameter is omitted, the operation's x-sortable.default (if declared) is applied; otherwise no client-driven sort is applied. A configured tie-breaker (default id) is always appended for stable pagination. See api-patterns.yaml#sorting for the full convention and docs/architecture/x-extensions.md for the extension shape. Syntax| Pattern | Description | Example |
|---|
fieldName | Ascending | sort=createdAt | -fieldName | Descending | sort=-createdAt | field1,field2 | Multi-field | sort=status,-priority | nested.field | Nested field via dot notation | sort=name.lastName |
Examplessort=createdAt — oldest firstsort=-createdAt — newest firstsort=-priority,dueDate — highest priority first, then oldest due datesort=name.lastName,name.firstName — alphabetical by surname, then given name
|
| requestingResourceId |
string |
query |
|
Filter by the requesting resource ID. |
| serviceType |
▶ ServiceType |
query |
|
Filter by service type (e.g., fdsh_ssa, ssa_ievs). |
| status |
▶ ExternalServiceCallStatus |
query |
|
|
Responses
200
A paginated list of service calls.
▶
ExternalServiceCallList
▶
items
array[ExternalServiceCall]
required
id
string (uuid)
required
Unique identifier.
serviceId
string (uuid)
required
ID of the ExternalService catalog entry being called.
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
requestingResourceId
string (uuid)
required
ID of the resource that triggered the call (e.g., an ApplicationMember ID). Combined with `serviceId`, forms the idempotency key.
requestingResourceType
string
Resource type of the requesting resource, copied from the ExternalService catalog entry at submission time. Together with `requestingResourceId`, tells adapters where to fetch sensitive input fields.
▶
callMode
CallMode
required
Whether this call is synchronous or asynchronous.
No additional fields
▶
status
ExternalServiceCallStatus
required
Lifecycle state of an external service call.
No additional fields
data
object
Optional per-call non-PII context (e.g., which FDSH sub-components to request). Polymorphic on `serviceType`.
metadata
object
Namespace-keyed metadata attached by calling domains for context passthrough. Keys are domain names; values are arbitrary objects.
createdAt
string (date-time)
required
When the call was submitted.
updatedAt
string (date-time)
required
When the call status last changed.
total
integer
required
Total number of matching records.
limit
integer
required
Maximum number of records per page.
offset
integer
required
Zero-based offset of the first returned record.
hasNext
boolean
required
Whether additional records exist beyond this page.
400
The request is malformed or contains invalid parameters.
▶
BadRequest
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
▶
POST
/service-calls
Submit a service call
#
Submit a request to call an external service. The request body carries no PII — adapters retrieve sensitive fields from the source domain using requestingResourceId and the resource type declared in the ExternalService catalog entry.
Submissions are deduplicated by requestingResourceId + serviceId. If a pending call already exists for the same pair, the server returns the existing call record rather than submitting a duplicate.
Request body required
▶
ExternalServiceCallCreate
Variant 1
No additional fields
Variant 2
No additional fields
Responses
200
Duplicate submission — an equivalent pending call already exists. Returns the existing call record.
▶
ExternalServiceCall
id
string (uuid)
required
Unique identifier.
serviceId
string (uuid)
required
ID of the ExternalService catalog entry being called.
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
requestingResourceId
string (uuid)
required
ID of the resource that triggered the call (e.g., an ApplicationMember ID). Combined with `serviceId`, forms the idempotency key.
requestingResourceType
string
Resource type of the requesting resource, copied from the ExternalService catalog entry at submission time. Together with `requestingResourceId`, tells adapters where to fetch sensitive input fields.
▶
callMode
CallMode
required
Whether this call is synchronous or asynchronous.
No additional fields
▶
status
ExternalServiceCallStatus
required
Lifecycle state of an external service call.
No additional fields
data
object
Optional per-call non-PII context (e.g., which FDSH sub-components to request). Polymorphic on `serviceType`.
metadata
object
Namespace-keyed metadata attached by calling domains for context passthrough. Keys are domain names; values are arbitrary objects.
createdAt
string (date-time)
required
When the call was submitted.
updatedAt
string (date-time)
required
When the call status last changed.
201
Service call submitted successfully.
▶
ExternalServiceCall
id
string (uuid)
required
Unique identifier.
serviceId
string (uuid)
required
ID of the ExternalService catalog entry being called.
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
requestingResourceId
string (uuid)
required
ID of the resource that triggered the call (e.g., an ApplicationMember ID). Combined with `serviceId`, forms the idempotency key.
requestingResourceType
string
Resource type of the requesting resource, copied from the ExternalService catalog entry at submission time. Together with `requestingResourceId`, tells adapters where to fetch sensitive input fields.
▶
callMode
CallMode
required
Whether this call is synchronous or asynchronous.
No additional fields
▶
status
ExternalServiceCallStatus
required
Lifecycle state of an external service call.
No additional fields
data
object
Optional per-call non-PII context (e.g., which FDSH sub-components to request). Polymorphic on `serviceType`.
metadata
object
Namespace-keyed metadata attached by calling domains for context passthrough. Keys are domain names; values are arbitrary objects.
createdAt
string (date-time)
required
When the call was submitted.
updatedAt
string (date-time)
required
When the call status last changed.
400
The request is malformed or contains invalid parameters.
▶
BadRequest
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
422
The request was well-formed but contained semantic errors.
▶
UnprocessableEntity
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
▶
GET
/service-calls/{serviceCallId}
Get a service call
#
Retrieve a single service call by identifier.
Parameters
| Name |
Type |
In |
Req |
Description |
| serviceCallId |
string |
path |
✓ |
Unique identifier of the service call. |
Responses
200
Service call retrieved successfully.
▶
ExternalServiceCall
id
string (uuid)
required
Unique identifier.
serviceId
string (uuid)
required
ID of the ExternalService catalog entry being called.
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
requestingResourceId
string (uuid)
required
ID of the resource that triggered the call (e.g., an ApplicationMember ID). Combined with `serviceId`, forms the idempotency key.
requestingResourceType
string
Resource type of the requesting resource, copied from the ExternalService catalog entry at submission time. Together with `requestingResourceId`, tells adapters where to fetch sensitive input fields.
▶
callMode
CallMode
required
Whether this call is synchronous or asynchronous.
No additional fields
▶
status
ExternalServiceCallStatus
required
Lifecycle state of an external service call.
No additional fields
data
object
Optional per-call non-PII context (e.g., which FDSH sub-components to request). Polymorphic on `serviceType`.
metadata
object
Namespace-keyed metadata attached by calling domains for context passthrough. Keys are domain names; values are arbitrary objects.
createdAt
string (date-time)
required
When the call was submitted.
updatedAt
string (date-time)
required
When the call status last changed.
404
The requested resource was not found.
▶
NotFound
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
▶
PUT
/service-calls/{serviceCallId}/metadata/{domain}
Set domain metadata on a service call
#
Attach namespace-keyed metadata from the calling domain to a service call. Used for context passthrough — the calling domain stores identifiers it needs to resume when a result arrives (e.g., the verification ID to update). The metadata object is echoed back verbatim in the result event under event.data.metadata.{domain}.
Replaces any existing metadata for the given domain namespace. Other domains' namespaces are unaffected.
Parameters
| Name |
Type |
In |
Req |
Description |
| serviceCallId |
string |
path |
✓ |
Unique identifier of the service call. |
| domain |
string |
path |
✓ |
The calling domain attaching its metadata namespace. enumclient-management data-exchange document-management eligibility intake workflow |
Responses
200
Metadata set successfully. Returns the updated service call.
▶
ExternalServiceCall
id
string (uuid)
required
Unique identifier.
serviceId
string (uuid)
required
ID of the ExternalService catalog entry being called.
▶
serviceType
ServiceType
required
The specific federal service interface being called. Each type has a distinct adapter interface, input schema, and result schema.
FDSH services are prefixed fdsh_ — they route through the CMS Federal Data Services Hub. IEVS sources are separate systems with distinct interfaces. See the Data Exchange architecture doc for the full reference.
No additional fields
requestingResourceId
string (uuid)
required
ID of the resource that triggered the call (e.g., an ApplicationMember ID). Combined with `serviceId`, forms the idempotency key.
requestingResourceType
string
Resource type of the requesting resource, copied from the ExternalService catalog entry at submission time. Together with `requestingResourceId`, tells adapters where to fetch sensitive input fields.
▶
callMode
CallMode
required
Whether this call is synchronous or asynchronous.
No additional fields
▶
status
ExternalServiceCallStatus
required
Lifecycle state of an external service call.
No additional fields
data
object
Optional per-call non-PII context (e.g., which FDSH sub-components to request). Polymorphic on `serviceType`.
metadata
object
Namespace-keyed metadata attached by calling domains for context passthrough. Keys are domain names; values are arbitrary objects.
createdAt
string (date-time)
required
When the call was submitted.
updatedAt
string (date-time)
required
When the call status last changed.
404
The requested resource was not found.
▶
NotFound
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
422
The request was well-formed but contained semantic errors.
▶
UnprocessableEntity
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
▶
DELETE
/service-calls/{serviceCallId}/metadata/{domain}
Remove domain metadata from a service call
#
Remove the calling domain's entire metadata namespace from a service call.
Parameters
| Name |
Type |
In |
Req |
Description |
| serviceCallId |
string |
path |
✓ |
Unique identifier of the service call. |
| domain |
string |
path |
✓ |
The calling domain attaching its metadata namespace. enumclient-management data-exchange document-management eligibility intake workflow |
Responses
204
Metadata removed successfully.
404
The requested resource was not found.
▶
NotFound
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.
500
An unexpected error occurred on the server.
▶
InternalError
code
string
required
Machine-readable error code.
message
string
required
Human-readable error description.
details
array[object]
Additional error details.