# Feeds system

Source: https://docs.settlemint.com/docs/architects/components/infrastructure/feeds-system
The Feeds system maps subjects and topics to active price or foreign exchange
feeds, so DALP workflows, token contracts, APIs, and external consumers can
resolve current market data without hard-coding feed addresses.




Identity, claim topics, and trusted issuers are defined in the [claims and identity model](/docs/architects/concepts/claims-and-identity).

The Feeds system is the on-chain discovery layer for price and foreign exchange data in DALP. It maps each subject and topic pair to the active feed contract. Platform workflows, token contracts, APIs, SDK clients, and external integrations can then resolve current data without storing feed addresses in every consumer.

Related pages:

* [Issuer-Signed Scalar Feed](/docs/architects/components/capabilities/issuer-signed-scalar-feed) for issuer-attested price data
* [Feeds update flow](/docs/architects/flows/feeds-update-flow) for the feed value lifecycle
* [Token price resolution API](/docs/developers/api-integration/token-price-resolution) for application reads of base-price and FX conversion paths
* [SMART Protocol integration (ERC-3643)](/docs/architects/components/asset-contracts/smart-protocol-integration) for token contracts that consume feeds
* [Execution Engine](/docs/architects/components/infrastructure/execution-engine) for workflows that use feed data

## At a glance [#at-a-glance]

* Feeds provide price and FX data through a directory keyed by subject and topic
* The FeedsDirectory separates **discovery** (which feed serves a subject + topic) from **delivery** (the contract that returns the value)
* Current feed surfaces include **issuer-signed scalar feeds**, **external scalar feed registrations**, and **Chainlink aggregator adapters** for integrations that expect `AggregatorV3Interface`
* Feeds can be global, such as economy-wide FX rates, or token-specific, such as asset base prices
* Feed management is privileged because stale, missing, or unauthorised pricing data can affect compliance decisions, API price reads, and valuations

<Mermaid
  chart="`flowchart TD
  A[Asset, currency pair, or other subject] --> B[Topic: base price or FX rate]
  B --> C[FeedsDirectory resolves subject + topic]
  C --> D[Active scalar feed]
  D --> E[PriceResolver normalises values]
  D --> F[Aggregator adapter exposes Chainlink-style reads]
  E --> G[APIs, workflows, token modules, and UI valuations]
  F --> H[External consumers that expect AggregatorV3Interface]
`"
/>

***

## What feeds are in DALP [#what-feeds-are-in-dalp]

Feeds are on-chain data sources that supply trusted market information, including prices, exchange rates, and valuations, to platform consumers. Each feed is a contract that returns data in a pinned format. The FeedsDirectory maps a &#x2A;*(subject, topic)** pair to the feed contract address, so consumers never hard-code feed addresses.

When a feed is registered, the directory captures:

| Field             | Description                                                                                    |
| ----------------- | ---------------------------------------------------------------------------------------------- |
| **Subject**       | Token address, entity address, or deterministic currency-code address for economy-wide FX data |
| **Topic**         | Data type the feed provides (base price, FX rate)                                              |
| **Feed contract** | Address applications query for data                                                            |
| **Feed kind**     | Scalar numeric feed. The directory validates the scalar interface before registration.         |
| **Schema hash**   | Pins the expected data format for consistency                                                  |

***

## How API and SDK clients read feed data [#how-api-and-sdk-clients-read-feed-data]

DALP resolves token prices for API and SDK reads from the active FeedsDirectory for the token's system. The API looks for a token-scoped base-price feed, normalises the value to 18 decimals, and checks the PriceResolver staleness policy. Currency conversion uses active global FX feeds in the same directory.

The feed directory is the operating source for price reads. If a token base-price feed is stale, the API rejects the price read under the active PriceResolver policy. If no conversion path exists for the requested currency, publish the missing feed data first or request a currency that already has an active FX path.

The SDK exposes the same feed surfaces as the API. Clients can list feeds, resolve by subject and topic, read configuration, submit issuer-signed updates, inspect staleness, and create adapters when the caller has the required privileges. On-chain consumers that use the PriceResolver addon read from the same FeedsDirectory and receive 18-decimal normalised values. External systems that need a Chainlink-style interface can read through the aggregator adapter instead of calling the API.

## Where feeds are used [#where-feeds-are-used]

| Consumer                  | Purpose                                                   | Failure impact                                     |
| ------------------------- | --------------------------------------------------------- | -------------------------------------------------- |
| **Compliance modules**    | Limit checks and valuation requirements                   | Transfer blocked if feed stale or missing          |
| **Yield / distribution**  | Determine distribution amounts based on current prices    | Distribution delayed or calculated on stale values |
| **Asset Console**         | Display current portfolio value in preferred currency     | UI shows outdated valuations                       |
| **Execution Engine**      | Incorporate feed data into multi-step workflows           | Workflow paused pending fresh data                 |
| **External integrations** | Consume prices via Chainlink-compatible adapter interface | Integration returns stale round data               |

***

## Feed types supported [#feed-types-supported]

### Issuer-signed scalar feed (capability) [#issuer-signed-scalar-feed-capability]

A factory-deployed capability where the asset issuer cryptographically signs and publishes price data. Each feed instance is created through a factory contract, following the same pattern as other DALP capabilities (Airdrop, Vault, XvP Settlement, Token Sale).

* **Deployment model:** factory pattern, one instance per asset or subject
* **Data format:** fixed-point integer with configurable decimals
* **Key properties:** history modes (latest-only, bounded, full), drift allowance, positive-value requirement, signature verification

See [Issuer-Signed Scalar Feed](/docs/architects/components/capabilities/issuer-signed-scalar-feed) for configuration, signing model, and value format details.

### External feed registration [#external-feed-registration]

DALP can register an existing feed contract in the directory when the feed already exists outside the DALP factory flow. The registration still uses the same subject and topic mapping as factory-created feeds, so consumers resolve it through the directory instead of storing the external address directly.

Use this path when an approved external feed should become the active source for a subject and topic. Use the adapter path when an external consumer needs a stable Chainlink-style read interface on top of the directory mapping.

### Chainlink aggregator adapter (infrastructure) [#chainlink-aggregator-adapter-infrastructure]

A wrapper contract that presents a DALP scalar feed through the **AggregatorV3Interface** used by many market-data integrations.

**Why it exists:** External integrations need a stable address. Feed replacement does not change the adapter address. The adapter resolves the current feed from the FeedsDirectory on every call. Consumers do not need to update their pointers.

| Property              | Detail                                                                           |
| --------------------- | -------------------------------------------------------------------------------- |
| **Interface**         | Chainlink `AggregatorV3Interface` (`latestRoundData`, `decimals`, `description`) |
| **Address stability** | Permanent, survives feed replacement in the directory                            |
| **Resolution**        | Dynamic, queries FeedsDirectory per call for current feed address                |
| **Configuration**     | Subject + topic pair (same mapping as the directory)                             |
| **Deployment**        | One adapter per (subject, topic) combination                                     |

**Use cases:** cross-platform data sharing, portfolio valuation by external trackers, oracle aggregation, and audit or compliance feeds for external systems that expect Chainlink-style reads.

***

## Who can manage feeds [#who-can-manage-feeds]

| Action                      | Who can do it                                                       | Scope                               |
| --------------------------- | ------------------------------------------------------------------- | ----------------------------------- |
| **Register a feed**         | Feeds Manager role, or an approved addon factory during creation    | Any subject permitted by that path  |
| **Replace / remove a feed** | Feeds Manager role                                                  | Any subject, including global feeds |
| **Create feed + adapter**   | Feeds Manager role, or a governance role holder on a specific token | Global feeds require Feeds Manager  |
| **Read feed data**          | Any contract or off-chain caller                                    | Unrestricted                        |

* Feed registration is a privileged operation because unauthorised changes to pricing data could affect compliance decisions and valuations
* Schema hash pinning ensures consumers always know the expected data format; format changes require explicit feed replacement
* Global feeds, including address-zero subjects and deterministic currency-code subjects for FX data, can only be managed by the Feeds Manager, not by individual token governance roles

***

## How to choose the right feed path [#how-to-choose-the-right-feed-path]

Use the path that matches the consumer and operational owner:

| Need                                            | Use this path                                     | Why it fits                                                                   |
| ----------------------------------------------- | ------------------------------------------------- | ----------------------------------------------------------------------------- |
| Publish issuer-attested token or market data    | Issuer-signed scalar feed                         | The feed stores signed fixed-point values, history settings, and drift checks |
| Register a feed contract that already exists    | External feed registration                        | Consumers still resolve through the directory by subject and topic            |
| Give an external system a stable oracle address | Chainlink aggregator adapter                      | The adapter address stays stable while the directory can replace the feed     |
| Read prices from an application or script       | API or SDK feed and exchange-rate endpoints       | Reads use the same directory, staleness policy, and pagination envelopes      |
| Keep global FX feeds current                    | Exchange-rate refresh scheduler and batch submits | The scheduler validates provider payloads and submits current rates by base   |

If you are setting up a feed for the first time, start with [Create a feed](/docs/operators/data-feeds/create-feed). If you are integrating through code, use [Create feeds with the API](/docs/developers/feeds/create-feeds). Use this architecture page when you need to understand how those calls resolve data.

## Operational model [#operational-model]

### Signals [#signals]

* **Feed registered / replaced / removed**: directory events indexed by the chain indexer
* **Value updated**: feed-level events (issuer-signed feeds emit on each signed update)
* **Outlier flagged**: drift allowance exceeded on an issuer-signed feed

### Deployment prerequisites [#deployment-prerequisites]

System and organisation deployment workflows prepare feed infrastructure before they create exchange-rate feeds. Each workflow registers the shared `price` topic, deploys the issuer-signed scalar feed factory, resolves the factory address, and waits for the indexer to make prior deployment events visible before continuing.

These steps are safe to repeat. If the topic already exists, the workflow continues. If the feed factory is already registered on-chain, DALP recovers the existing factory from indexed registry events instead of creating a duplicate. Temporary RPC, transport, or indexer visibility failures remain retryable so the workflow can resume once the dependency catches up.

### Exchange rate refresh [#exchange-rate-refresh]

DALP refreshes active FX feeds from the configured exchange rate provider on a recurring schedule. The refresh cycle groups active feeds by base currency, fetches one provider payload for each base, and submits validated rates in batches. Provider response keys are normalised to uppercase ISO currency codes before submission.

Production FX feeds are global platform data even when the feed subject is a deterministic ISO 4217 currency-code address rather than address zero. The indexer and currency-conversion graph use that scope to pick up active FX pairs separately from per-asset price feeds.

The refresh scheduler starts for every enabled network when exchange-rate auto-refresh is enabled. Operators can disable automatic refreshes or set the refresh interval in the `exchangeRates` configuration block. The interval accepts duration values such as `30m`, `6h`, or `1d`, with a minimum of five minutes and a default of six hours.

The provider fetch uses a primary endpoint with a fallback mirror. The scheduler retries transient provider, network, timeout, and payload-shape failures with backoff. A base currency rejected by both endpoints as not found is treated as a permanent provider rejection for that cycle, so the scheduler logs the issue and waits for the next scheduled refresh instead of spending the retry budget on an unsupported base.

The refresh cycle does not submit a new on-chain value when the provider timestamp for that base has not changed. Timestamps are tracked per base currency, so a failed EUR refresh does not block USD, and a successful USD refresh does not suppress a later EUR retry.

Before submission, DALP drops missing quote currencies and rates that are zero, negative, non-finite, or outside the configured sanity bounds. If every feed for a base fails validation, the scheduler keeps that base eligible for the next refresh instead of advancing its stored timestamp.

### Failure modes [#failure-modes]

| Failure                                     | System behavior                                                       |
| ------------------------------------------- | --------------------------------------------------------------------- |
| Feed stale (no updates)                     | Consumers read last-known value; compliance may block                 |
| Feed removed from directory                 | Discovery returns zero address; consumers must handle                 |
| Invalid signature                           | Issuer-signed feed rejects the update on-chain                        |
| Drift exceeded                              | Value flagged as outlier; consumers decide risk tolerance             |
| Adapter target missing                      | Adapter call reverts; external integrations see failure               |
| Exchange rate provider temporarily fails    | Scheduler retries with backoff, then waits for the next refresh cycle |
| Exchange rate base is unsupported           | Scheduler skips that base for the cycle and logs the rejection        |
| Exchange rate quote missing or invalid      | Scheduler skips the affected feed and retries on a later cycle        |
| Organisation signer or CLAIM purpose absent | Scheduler skips submission until the organisation signer is ready     |

See [Feeds update flow](/docs/architects/flows/feeds-update-flow) for the full lifecycle including validation checkpoints and recovery.

***

## Dependencies [#dependencies]

**On-chain:**

* FeedsDirectory contract (central registry)
* Factory contracts (deploy issuer-signed feed and adapter instances)
* Token contracts (subjects for token-specific feeds)

**Off-chain:**

* Chain indexer (indexes directory and feed events for the platform UI and API)
* Exchange-rate refresh scheduler (keeps active global FX feeds current when auto-refresh is enabled)
* Execution Engine (orchestrates workflows that consume feed data)

For a task-oriented setup path, use [Create a feed](/docs/operators/data-feeds/create-feed) or [Create feeds with the API](/docs/developers/feeds/create-feeds). To read the price that application code receives from base-price and FX feeds, use the [token price resolution API](/docs/developers/api-integration/token-price-resolution). To understand update validation and recovery, read the [Feeds update flow](/docs/architects/flows/feeds-update-flow).

***

## See also [#see-also]

* [Issuer-Signed Scalar Feed](/docs/architects/components/capabilities/issuer-signed-scalar-feed) for configuration, signing model, and value format
* [Token price resolution API](/docs/developers/api-integration/token-price-resolution) for resolved application prices and FX conversion paths
* [Feeds update flow](/docs/architects/flows/feeds-update-flow) for the feed value update lifecycle
* [Compliance modules](/docs/compliance-security/security/compliance) for how feeds support compliance checks
