SettleMint
API referenceGuides

Read and submit price feeds

Read the on-chain price-feed directory, latest values, rounds, and staleness windows, and submit a signed observation as a trusted issuer on V1 or V2.

Overview

A feed maps a subject address and a topic to one governed source of observations. The API reads the directory, feed configuration, values, and staleness policy. Authorized issuers can submit observations. Read Market data for the governance model and the V1 or V2 reference for complete schemas.

V1 routes use /api/v1/system/feeds/*; V2 routes use /api/v2/system/feed/*. Both accept a session cookie or X-Api-Key, including on submission routes.

Call GET /api/v2/system/feed/capabilities before using a feed capability. The directory, issuer-signed factory, or adapter factory can be absent from an organization. An unavailable capability returns an error, not an empty feed list.

Two ways a feed gets registered

An issuer-signed feed is created through the platform's factory. The create request sets its decimals, subject, topic, and description. The platform fixes its retention to the latest round on-chain, requires every submitted value to be greater than zero, and allows no future drift from chain time in the feed contract. The create request does not expose those three settings. A rate or exchange-rate movement that can be zero or negative is unsupported by native feed creation. The indexed API can still serve past accepted observations. Read the feed's configuration with GET /api/v2/system/feed/{feedAddress}/configuration before using it for valuation or settlement.

An external feed, such as a Chainlink-compatible aggregator already deployed on chain, is registered rather than created: POST /api/v2/system/feed/external-registrations maps an existing contract into the directory at a subject and topic. Replacing the feed at that key with PUT /api/v2/system/feed/registrations retires the previous address once the queued write settles; removing it with DELETE /api/v2/system/feed/registrations only deletes the directory mapping; the feed contract itself stays deployed and readable at its own address. Neither the old feed's history nor its own contract state changes.

A stable adapter gives consumers one address that survives a feed replacement underneath it. POST /api/v2/system/feed/adapters deploys one for a subject and topic. Hold onto adapterAddress from the response, not the feed address behind it, especially from a smart contract or any long-lived integration.

Decide who may submit a value

Submission authorization branches on the feed's topic, not on a single role check. The system price topic and every other topic go through different authorization paths, and a caller who satisfies one path does not automatically satisfy the other.

System price topicAny other topic
Who is the trusted issuerThe organization itself.The caller's own on-chain identity.
What the caller needsThe feedsManager role.Registration as a trusted issuer for the feed's topic, in that feed's trustedIssuersRegistry.
Who signs the updateThe platform, using the organization's signer.The platform, using the caller's own identity signer.
Rejection if missing403, feedsManager role required.403, not a trusted issuer for this topic. A caller with no on-chain identity at all gets a separate 409 before the trusted-issuer check even runs.

Read a feed's trustedIssuersRegistry address from its configuration response before you plan a non-price-topic submission. That registry, not a platform-wide role, is where the authorization actually lives, and both rejection paths above happen before any on-chain attempt: a caller who fails either check never spends gas finding out.

Read the latest value and staleness

GET /api/v2/system/feed/{feedAddress}/latest reads directly from the feed contract, so it returns exactly what the chain reports at call time, not an indexed copy.

Staleness is a governed policy, and only V2 exposes it. GET /api/v2/system/feed/staleness-windows/effective?subject=...&topicId=... resolves the same window the platform's own price-age checks enforce elsewhere, such as before a mint. Two governed inputs feed that resolution, and exactly one effective value comes out:

How DALP resolves the effective staleness windowThe global default and per-feed override resolve to one effective window. An override can set a seconds value, mark the feed as never expiring, or inherit the global default. The effective source and age limit determine whether a value is stale.STALENESS POLICYGlobal defaultSystem-wide age limitPer-feed overrideSeconds, never expires,or inherit the global defaultEFFECTIVE WINDOWAge limit + sourceStale if age exceeds the limit

Two governed inputs resolve to one effective window, tagged with its source. The platform's own staleness checks, including the one that gates a mint, use that resolved value.

A resolver that has no observed global-window event keeps the on-chain default of one day. The platform initialises a new resolver to never-expires only when the account that creates it holds the Feeds Manager role, and the effective window is never-expires once an event setting it has been observed. The response's source field tells you which input won: "feed-override" or "global-default". A bare maxAgeSeconds: 0 on the setter routes cannot express both "clear this feed's override" and "reject every value as stale." That ambiguity is why the override is a tagged choice rather than a number. PUT /api/v2/system/feed/staleness-windows accepts {"mode": "seconds", "seconds": N}, {"mode": "never"}, or {"mode": "inherit"} for one feed. PUT /api/v2/system/feed/staleness-windows/global sets the system-wide default with {"mode": "seconds", "seconds": N} or {"mode": "never"}, and has no inherit option. GET /api/v2/system/feed/staleness-windows/global reads that default back in the same shape, so a client can read it, change it, and write it back.

V1 has no equivalent to any of the three staleness-window routes above. A V1-only integration can read a feed's raw age against a threshold it supplies on each call, but it has no route to read or set the platform's governed window at all. Plan a V1-based integration around that gap rather than discovering it when a staleness-window call returns a 404 for the route itself.

Submit a signed value

The submission route resolves the issuer's nonce and signs for you, so an integration never reads or tracks nonces itself.

POST /api/v2/system/feed/{feedAddress}/submissions takes the human value as a decimal string, such as "1.08". The platform converts it to on-chain units using that feed's decimals and refuses values that cannot be represented exactly. It also takes observedAt as a Unix-seconds timestamp. The platform rejects an observedAt more than 300 seconds ahead of chain time before it ever reaches the chain; that boundary is fixed, not configurable per feed. The submit route resolves a signer rather than an executing wallet, chosen by which authorization path above the caller satisfies. It returns the same synchronous-or-queued response shape every other DALP mutation does: an X-Transaction-Hash header when the write confirms within the request, or Location and Preference-Applied: respond-async when it does not. See Idempotency and async settlement for the retry and polling discipline; this route follows it exactly, with no feed-specific exception.

Failure modes worth planning around

Most feed errors are ordinary client mistakes: a bad address, a topic name and topic id that disagree, a malformed request body. A smaller set is worth knowing by name. Check the error's retryable flag and the current instruction state before deciding whether another write is needed. The feed routes do not document request-level replay safety; retaining the original key alone does not make an API retry safe:

  • The directory has no mapping yet for a subject and topic you expect to be registered. This happens when a registration transaction has confirmed but Ledger Data has not caught up. Confirm the registration, then retry once the index catches up.
  • The feed provider, or the organization's price-feed signer, does not answer. Once the dependency recovers, inspect the original operation before deciding whether to submit again.
  • A queued write returns a transaction reference the platform cannot confirm. Check the original request status before submitting again; reusing the key alone does not prove the whole feed route is replay-safe.

Two failures are never worth retrying as sent: a topic name and topic id that resolve to different topics, and an observedAt timestamp more than 300 seconds in the future. Both need a corrected request, not a repeated one. See Errors for how to read the retryable flag DALP actually returns, rather than guessing from the failure's shape.

Next steps

On this page