Feed value submission
Submit a signed value to an issuer-signed price feed through DALP. Read the issuer nonce, post a new value, and track the on-chain update.
An issuer-signed feed only changes when a trusted issuer submits a new value. A bank pricing a digital asset, an oracle operator refreshing a market rate, or a fund publishing its net asset value all go through the same two endpoints: read the issuer's current nonce, then submit the signed value. The platform holds the issuer's signing key, builds the signature for each update, and tracks the on-chain write to completion, so an integrator never handles a private key directly.
For the read side, use the price feeds API: list feeds, read one feed, and inspect the latest value and staleness. The two endpoints below handle the write side for issuer-signed feeds.
Endpoints
| Job | Method and path | Use it for | Response shape |
|---|---|---|---|
| Read the nonce | GET /api/v2/system/feed/{feedAddress}/nonces/{issuerIdentity} | Read the issuer's current and next nonce for a feed before you submit. | Single-resource envelope with data and links.self. |
| Submit a value | POST /api/v2/system/feed/{feedAddress}/submissions | Sign and submit a new value to the feed as a trusted issuer. | 202 async-accepted body by default, or a synchronous mutation envelope when you send Prefer: wait=N. |
Both endpoints address one feed by its contract address. The submit endpoint returns the on-chain transaction so you can confirm the value landed before you treat it as live.
Who can submit a value
Authorization is topic-driven. A feed prices a subject for a topic, and the right to write a value comes from being a trusted issuer for that feed's topic.
- For the system price topic, the organization identity is the trusted issuer. A caller acting on the organization's behalf needs the
feedsManagerrole, and the platform signs with the organization's signer. - For any other topic, the caller's own identity must be registered as a trusted issuer for the feed's topic in the feed's
trustedIssuersRegistry. Read that registry address from the feed configuration endpoint for the feed you are updating. That registration is the authorization, with no extra role required. The platform signs with the caller's identity.
If the caller's identity is not registered for the feed's topic, the submit endpoint returns a typed permission error before any on-chain attempt, instead of letting the update revert on chain. A caller acting for an organization without the feedsManager role gets the same early rejection.
To authorize an issuer for a topic, see Configure trusted issuers.
Read the issuer nonce
Each issuer-signed feed tracks a nonce per issuer identity, which orders that issuer's updates and prevents replay. Read the current nonce before you submit so you know which value the next update will carry.
The issuerIdentity path value is the issuer's on-chain identity contract address, not the wallet address that signs the transaction.
curl "https://your-platform.example.com/api/v2/system/feed/0x1111111111111111111111111111111111111111/nonces/0x2222222222222222222222222222222222222222" \
-H "X-Api-Key: sm_dalp_xxxxxxxxxxxxxxxx"{
"data": {
"feedAddress": "0x1111111111111111111111111111111111111111",
"issuerIdentity": "0x2222222222222222222222222222222222222222",
"currentNonce": "12",
"nextNonce": "13"
},
"links": {
"self": "/v2/system/feeds/0x1111111111111111111111111111111111111111/nonce/0x2222222222222222222222222222222222222222"
}
}A direct on-chain read backs this endpoint, so the response always reflects the feed's live state. currentNonce is the highest nonce the issuer has used; nextNonce is the value the next accepted submission carries.
Submit a signed value
Call the submit endpoint with the value and the time you observed it. The platform resolves the signer, builds the signature for the issuer, and writes the value to the feed.
curl -X POST "https://your-platform.example.com/api/v2/system/feed/0x1111111111111111111111111111111111111111/submissions" \
-H "X-Api-Key: sm_dalp_xxxxxxxxxxxxxxxx" \
-H "Content-Type: application/json" \
-d '{
"value": "100000000",
"observedAt": 1742637000
}'The request body carries the value to publish:
| Field | Type | Required | Notes |
|---|---|---|---|
value | integer string | Yes | The value in feed units. Multiply the human value by 10 to the power of the feed's decimals. 1.00 at 8 decimals is 100000000. |
observedAt | positive integer | Yes | Unix timestamp in seconds for when the value was observed. Must be greater than zero. |
deadline | non-negative integer | No | Unix timestamp in seconds after which the signed update is no longer valid. Defaults to 0, which means no deadline. |
The feed enforces its own immutable rules on every value. Read those rules with the feed configuration endpoint before you submit:
- When
requirePositiveis set, the feed rejects zero and negative values. driftAllowanceis the most seconds anobservedAttimestamp may sit ahead of chain time. The platform rejects a timestamp that exceeds chain time by more than a short tolerance before it reaches the chain, and the feed contract enforces the per-feed allowance as the final check.- The value must match the feed's pinned schema, and the signature must come from an authorized issuer.
A submission that breaks any of these rules is rejected. For a value far ahead of chain time, the platform returns a typed error at the boundary rather than letting it revert on chain.
Synchronous response
When the platform confirms the transaction within the request, the response carries the result and the transaction hashes:
{
"data": {
"transactionHash": "0xabc1230000000000000000000000000000000000000000000000000000000000",
"feedAddress": "0x1111111111111111111111111111111111111111",
"value": "100000000",
"nonce": "13"
},
"meta": {
"txHashes": ["0xabc1230000000000000000000000000000000000000000000000000000000000"]
},
"links": {
"self": "/v2/system/feeds/0x1111111111111111111111111111111111111111/submit"
}
}The nonce in the response is the nonce the accepted update carried, matching the nextNonce you read before submitting. The same hashes appear in X-Transaction-Hash response headers.
Async response
By default, the submit endpoint queues the submission and returns immediately. It returns 202 with a tracking body:
{
"transactionId": "01890c7e-1f8e-7c3a-9b2d-2f6a4c8e1a90",
"status": "QUEUED",
"statusUrl": "/api/v2/transaction-requests/01890c7e-1f8e-7c3a-9b2d-2f6a4c8e1a90"
}Poll statusUrl until the transaction reaches a terminal state before you treat the new value as live. See Transaction queue lifecycle for the status states and the streaming alternative.
Response timing with Prefer
The submit endpoint uses the RFC 7240 Prefer header to control whether it waits for the transaction to finish or returns immediately.
| Header sent | Behavior |
|---|---|
| None (default) | Queued immediately. Returns 202 with a transactionId and statusUrl. |
Prefer: respond-async | Same as the default. Returns 202 with a tracking body. |
Prefer: wait=60 | Synchronous. Waits up to 60 seconds for confirmation, then returns the transaction result. |
To request a synchronous response, add the Prefer header to your call:
curl -X POST "https://your-platform.example.com/api/v2/system/feed/0x1111111111111111111111111111111111111111/submissions" \
-H "X-Api-Key: sm_dalp_xxxxxxxxxxxxxxxx" \
-H "Content-Type: application/json" \
-H "Prefer: wait=60" \
-d '{
"value": "100000000",
"observedAt": 1742637000
}'The wait value is the maximum number of seconds the platform waits before returning the async 202 instead. The platform clamps it to a supported range, so a very high value does not block the call indefinitely.
Authentication and verification
Both endpoints accept an API key through the X-Api-Key header. The submit endpoint is a state-changing mutation, so a session-cookie caller includes a walletVerification object in the request body to confirm the signer, while API-key callers do not.
To make a submission safe to retry, send an Idempotency-Key header. A repeated request with the same key returns the original result instead of writing the value twice. See Operational integration patterns for the retry, idempotency, and readback discipline around mutations.
Error codes
When a submission fails, the API returns a stable DALP-NNNN error code. The platform checks authorization, the caller's identity, and the observed timestamp before it touches the chain, so most rejections arrive as a typed error rather than an on-chain revert. Read the code to decide whether the caller corrects the request and resends, retries the same call once the platform catches up, or escalates to operator follow-up. Each code below maps to a canonical entry in the platform API error reference.
| Code | HTTP | Category | When it happens |
|---|---|---|---|
| DALP-0043 | 403 | permission | The caller is not authorized to submit for the feed's topic. For the system price topic, the caller is missing the feedsManager role. For any other topic, the caller's identity is not a trusted issuer for it. |
| DALP-0123 | 409 | domain | The authenticated participant has no associated on-chain identity contract. Only a participant with a registered identity can submit feed updates. Register the identity, then resend. |
| DALP-0639 | 422 | client | The observedAt timestamp sits further ahead of chain time than the platform's preflight tolerance allows. The platform rejects it before the chain. Clamp observedAt to the latest observed value, or check the producer's clock against a time source, then resend. |
| DALP-0613 | 503 | dependency | The feed is not yet indexed, or the organization's price-feed signer is not available yet. The submission has not been written. Retry with the same Idempotency-Key once the platform catches up. |
| DALP-0133 | 503 | dependency | The submission reached the platform but returned a malformed transaction reference, so the result cannot be confirmed. Resolve the platform issue, then resubmit under a new Idempotency-Key. |
DALP-0043, DALP-0123, and DALP-0639 are correctable from the caller side: fix the role, register the identity, or correct the timestamp, then resend. DALP-0613 rejects before the submission is written, so retry with the same idempotency key once the platform catches up. DALP-0133 means the write already reached the platform but its result could not be confirmed, so resolve the platform issue and resubmit under a new key rather than reusing the failed one. A request that passes every check here can still revert at the feed contract on a rule the platform cannot see ahead of time, such as the per-feed drift allowance or the requirePositive guard. Track the transaction queue to a terminal state before you treat the value as live.
Related pages
- Price feeds reads the feed registry, latest values, and staleness.
- Publish a feed update walks through the same submission from the operations console.
- Transaction queue lifecycle tracks a queued submission to completion.
- Operational integration patterns covers idempotency, retries, and reconciliation.
Price feeds
Read the on-chain price-feed registry through DALP. List registered feeds, read one feed, resolve a feed for a subject and topic, and inspect latest value, historical rounds, and staleness.
Token sale offering API and CLI flow
Create, configure, activate, buy, finalize, and settle a token sale offering through DALP APIs, SDK methods, and CLI commands.