Share endpoints

Hand a record to another organization, and take delivery of one handed to you.

Authentication, the response envelope, and pagination are on API conventions. All paths are relative to https://api-next.expressconsent.com.

POST /v1/cdrs/:cdrId/shareCreate a share URL for a record you hold
POST /v1/shares/:tokenReceive a record that was shared with you
GET /v1/shares/:tokenRedirect a person to the dashboard to receive it by hand

The direction evidence moves and who pays for it is explained on access and collection. This page is the wire format.

POST /v1/cdrs/:cdrId/share

Creates a share URL for a record your organization holds. The body is optional.

bash
curl -sS -X POST -H "X-API-Key: $EC_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"expiresInMs": 604800000}' \
  "https://api-next.expressconsent.com/v1/cdrs/cdr_abc123/share"
json
{
  "ok": true,
  "data": {
    "token": "xYz7Qw...",
    "shareUrl": "https://api-next.expressconsent.com/v1/shares/xYz7Qw...",
    "expiresAt": 1741839367890
  },
  "requestId": "3f2504e0-4f89-11d3-9a0c-0305e82c3301"
}

You do not need to have collected a record to share it. Sharing a record you have not paid for is normal for a lead generator whose buyers are the payers.

Request

expiresInMsnumberoptionaldefault 2592000000

How long the share URL stays usable, in milliseconds from now. The default is 30 days. Read expiresAt on the response for the expiry you actually got.

Clamped to a maximum of 2 years. A zero, negative, or non-finite value falls back to the default rather than being rejected, as does any non-number.

Response

tokenstringrequired

The share token. This is the credential: anyone holding it and an API key for a different organization can take the record.

shareUrlstringrequired

The absolute URL to hand to the buyer. Identical in form to the shareUrl a capture with autoShare returns, so the two paths are interchangeable.

expiresAtnumberrequired

When the token stops working, as a Unix timestamp in milliseconds.

Generating the share URL during the capture instead avoids the extra call altogether. See autoShare on captureCDR().

POST /v1/shares/:token

Receives a shared record into your organization. The body is optional; sent without one, this saves the record and bills you for it, unless you already have access, or unless the sender had already paid, in which case their access passes to you at no charge.

bash
curl -sS -X POST -H "X-API-Key: $EC_API_KEY" \
  "https://api-next.expressconsent.com/v1/shares/xYz7Qw..."
json
{
  "ok": true,
  "data": {
    "claimed": true,
    "alreadyClaimed": false,
    "cdrId": "cdr_abc123",
    "domainId": "example.com",
    "shareEventId": "se_9f2b..."
  },
  "requestId": "3f2504e0-4f89-11d3-9a0c-0305e82c3301"
}

Request

collect and acceptance are the only fields this body accepts. Anything else is a 400 INVALID_ARGUMENT naming the offending key. A misspelled acceptance must not quietly mean "no requirements".

collectbooleanoptionaldefault true

Whether to become the payer for this record. With false the record still lands in your account with its metadata and consent facts, and you are not billed.

Whether you can download the evidence then depends on the sender. If they had already paid, their access passes to you either way. It is theirs to give, so opting out of payment does not decline it. If they had not, you have no download access until you collect the record later. So collect: false means "do not make me the payer", not "do not give me access".

Any non-boolean value is a 400 INVALID_ARGUMENT rather than being coerced.
acceptanceobjectoptional

Requirements the record must meet before you will take it. A record that fails is refused outright: not saved, not charged, and the token stays usable. Fully documented on acceptance criteria.

Response

claimedbooleanrequired

Always true. The call either succeeds or returns an error.

alreadyClaimedbooleanrequired

true when your organization had already received this record through this token. Repeating the request is safe and never charges twice.

cdrIdstringrequired

The record identifier, now readable through the CDR endpoints.

domainIdstringrequired

The domain the record is filed under, which you need to list it.

shareEventIdstringrequired

Identifies this handoff. An empty string when alreadyClaimed is true: it is not looked up again on a repeat request.

One token, several recipients

A token is not consumed by being used. It is idempotent per organization, so the same token can hand the same record to several different organizations until it expires. Treat a share token as a bearer credential and give it only to the buyer it is meant for.

Expiry is checked before that idempotency check, so repeating a request for a record you already hold returns 410 GONE once the token expires rather than reporting it was already received.

You cannot receive your own share

A token created by your organization is refused for your organization with 400 INVALID_ARGUMENT. To get download access to a record you captured, collect it. See the CDR endpoints. This is the wall an organization that both generates and buys leads hits first; generators and buyers explains why.

GET /v1/shares/:token

Redirects to the dashboard, where a person can sign in and take the record by hand. Responds 302 with a Location of https://app.expressconsent.com/claim/{token}.

This is the only endpoint that needs no API key, because the person following it authenticates in the dashboard instead. It exists so that a share URL pasted into an email is a working link for a human rather than an error.

Nothing is charged by following the redirect. The request that receives the record is the one the dashboard makes afterwards.

Errors

Every code, its HTTP status, and what to do about it is on API errors. The ones specific to these endpoints:

StatusCodeCause
202CDR_PENDINGThe record has not finished rendering. Retry after the Retry-After header says to, which is 2 seconds. Note the 2xx status on a failure.
400INVALID_ARGUMENTYour own organization created the token, the body carried an unrecognized field, collect was not a boolean, acceptance did not validate, or acceptance.leadMatch.phone was not a normalizable North American number
403PASSTHROUGH_ORG_CANNOT_CLAIMYour organization has no billing set up and cannot receive shared records on any surface. Such an organization normally has no API access either, in which case API_ACCESS_DISABLED comes back first.
404NOT_FOUNDNo such token, or no such record on the share path
409CONFLICTOn the share path, more than one record on our side carries that identifier. A data problem, not something you caused.
410GONEThe token has expired
410CDR_INVALIDThe record was flagged invalid and cannot be shared or received
422CDR_ACCEPTANCE_FAILEDThe record did not meet your acceptance requirements

CDR_PENDING is common immediately after a capture that used autoShare: the token is created during the upload, so a buyer acting on it within a second or two arrives before the visual record exists. Retry rather than treating it as a failure.