In This Article
In the early days of programmatic advertising, a DSP receiving a bid request had almost no visibility into how many intermediaries the request had passed through before reaching them. A single impression could be routed through multiple resellers, each adding margin, before arriving at the buyer. The OpenRTB SupplyChain object (commonly called "schain") was introduced to solve this opacity problem by documenting every entity that handled a bid request from publisher to buyer.
What Is the SupplyChain Object?
The SupplyChain object is a structured data field within OpenRTB bid requests that records the complete path of entities through which a bid request has passed. Each entity in the path is represented as a "node" containing identifying information and its relationship to the publisher.
Formally defined in the OpenRTB specification (initially as an extension in OpenRTB 2.5, later formalized in OpenRTB 2.6 and Community Extensions), the schain object provides buyers with unprecedented transparency into the supply chain before they commit to a bid.
Why It Matters
Before schain, a DSP could only see the final entity that forwarded the bid request. It had no way to determine whether the impression had passed through one intermediary or five. This opacity created several problems:
- Hidden costs: Each intermediary adds margin, inflating the final price without adding value for the advertiser.
- Fraud risk: Additional hops in the supply chain increase the surface area for fraudulent manipulation.
- Unauthorized reselling: Intermediaries without publisher authorization could insert themselves into the supply chain.
- Performance degradation: Each additional hop adds latency, reducing the time available for bid evaluation.
Node Structure
The schain object contains a nodes array, where each node represents one entity in the supply chain. The nodes are ordered from first to last: the first node is the entity with the most direct relationship to the publisher, and the last node is the entity that sent the bid request to the DSP.
{
"source": {
"ext": {
"schain": {
"complete": 1,
"ver": "1.0",
"nodes": [
{
"asi": "publisher.com",
"sid": "pub-direct-12345",
"rid": "req-abc-001",
"hp": 1,
"domain": "publisher.com",
"name": "Publisher Inc."
},
{
"asi": "exchange-a.com",
"sid": "seller-67890",
"rid": "req-xyz-002",
"hp": 1,
"domain": "exchange-a.com"
},
{
"asi": "reseller-network.com",
"sid": "reseller-11111",
"rid": "req-def-003",
"hp": 0
}
]
}
}
}
}
Node Field Definitions
| Field | Type | Required | Description |
|---|---|---|---|
| asi | String | Yes | The canonical domain of the entity (advertising system identifier). Should match the domain in ads.txt. |
| sid | String | Yes | The seller ID as it appears in ads.txt or the entity's internal identifier for the upstream node. |
| rid | String | No | The request ID used by this node to track the request internally. Useful for debugging and tracing. |
| hp | Integer | No | Whether the node is the "head" of the supply chain (1 = yes). Typically only the first node has hp=1. |
| domain | String | No | The domain of the website or app where the inventory originates (if different from asi). |
| name | String | No | Human-readable name of the entity. |
Complete vs. Incomplete Chains
The complete field at the schain level indicates whether all nodes in the supply chain are represented:
- complete: 1 means the chain is complete—every entity that handled the bid request is represented as a node.
- complete: 0 means the chain is incomplete—one or more entities are missing. This may happen when an intermediary does not support the schain specification and fails to append itself.
Buyers should treat incomplete chains with caution, as they may indicate intermediaries that are not transparent about their participation.
Why schain Matters for Supply Path Optimization
Supply Path Optimization (SPO) is the practice of analyzing and selecting the most efficient supply paths to reach desired inventory. schain is the primary data source that enables SPO.
How DSPs Use schain for SPO
- Path discovery: DSPs aggregate schain data across millions of bid requests to map all available paths to a given publisher's inventory.
- Path analysis: They analyze which paths have fewer intermediaries, lower latency, and higher win rates.
- Path selection: DSPs preferentially bid on paths with the fewest hops and the most direct publisher relationships.
- Cost optimization: By buying through direct paths, advertisers reduce the number of intermediaries taking margin, improving effective CPMs.
- Fraud reduction: Shorter, well-known supply paths are inherently less susceptible to fraud.
A practical SPO example: a publisher's inventory may be available through 15 different SSPs and exchanges. schain data reveals that only 3 of those paths are direct (one hop from publisher to exchange), while 12 involve additional resellers. An advertiser can direct their DSP to prefer the 3 direct paths, potentially saving 15-30% on effective media costs.
Implementation Guide
For Publishers (First Node)
As the originator of the supply chain, the publisher (or their direct SSP) must create the initial schain object:
// Publisher creates the initial schain
{
"complete": 1,
"ver": "1.0",
"nodes": [
{
"asi": "publisher.com",
"sid": "direct-pub-id",
"hp": 1
}
]
}
The publisher's SSP or header bidding wrapper should pass this schain object when forwarding the bid request to downstream exchanges.
For Intermediaries (Middle Nodes)
Each intermediary that receives a bid request with an existing schain must append its own node before forwarding:
// Intermediary appends its node
existingChain.nodes.push({
"asi": "my-exchange.com",
"sid": "my-seller-id-for-this-publisher",
"rid": "my-internal-request-id",
"hp": 0
});
// Forward the updated chain to downstream buyers
Critical rules for intermediaries:
- Never remove or modify existing nodes—only append new nodes.
- If you receive a bid request without a schain and you have a direct relationship with the publisher, you may create a new schain with yourself as the first node.
- If you receive a request without a schain and you do NOT have a direct publisher relationship, you should not fabricate a schain.
- Always include your
asivalue as the domain that matches your ads.txt/sellers.json entries.
For DSPs (Consuming schain)
DSPs parse the schain from incoming bid requests and use it for bid decisioning:
// DSP schain validation logic
function validateSchain(bidRequest) {
const schain = bidRequest.source?.ext?.schain;
if (!schain) {
return { valid: false, reason: 'No schain present' };
}
if (schain.complete === 0) {
return { valid: false, reason: 'Incomplete supply chain' };
}
if (!schain.nodes || schain.nodes.length === 0) {
return { valid: false, reason: 'Empty node list' };
}
// Verify first node matches ads.txt
const firstNode = schain.nodes[0];
const publisherDomain = bidRequest.site?.domain;
if (firstNode.hp !== 1) {
return { valid: false, reason: 'First node not marked as head' };
}
// Verify all node ASI domains are in sellers.json
for (const node of schain.nodes) {
if (!isInSellersJson(node.asi)) {
return { valid: false, reason: `Node ${node.asi} not found in sellers.json` };
}
}
return { valid: true, pathLength: schain.nodes.length };
}
Relationship to ads.txt and sellers.json
The schain object complements but does not replace ads.txt and sellers.json. Together, they form a comprehensive verification framework:
| Standard | What It Verifies | Who Publishes It |
|---|---|---|
| ads.txt | Which sellers are authorized to sell a publisher's inventory | Publisher |
| sellers.json | Which publishers a seller represents | Seller (SSP/Exchange) |
| schain | The complete path of entities in a specific bid request | Each entity in the chain |
A buyer performing full verification will cross-reference all three: confirming the schain nodes match ads.txt authorizations, verifying sellers.json identity claims, and checking that the supply chain is complete and untampered.
Validation and Fraud Detection
DSPs implement several schain-based validation checks:
Tampering Detection
- Node order validation: The first node must have
hp: 1. If it doesn't, the chain may have been manipulated. - ASI consistency: Each node's
asishould match the domain of the entity forwarding the request. A mismatch suggests the node was fabricated. - SID consistency: The
sidin each node should be a valid identifier that the corresponding entity actually uses, verifiable against ads.txt and sellers.json.
Anomaly Detection
- Unexpected path length: If a publisher's inventory typically arrives through 1-2 hops, but a bid request shows 5+ nodes, this may indicate unauthorized reselling.
- Unknown ASIs: Nodes with ASI domains not found in any sellers.json should be flagged.
- Duplicate nodes: The same ASI appearing multiple times in a chain suggests circular routing.
Adoption and Industry Status
schain adoption has grown significantly since its introduction, driven by advertiser demand for transparency and DSP requirements. Major programmatic platforms including Google, The Trade Desk, and NexBids require schain in bid requests and use it for bid decisioning. The IAB Tech Lab has continued to refine the specification, addressing edge cases and providing clearer implementation guidance.
Despite progress, challenges remain. Not all SSPs and exchanges fully support schain, particularly in emerging markets and smaller platforms. Some intermediaries have been found to manipulate schain data by omitting nodes or fabricating direct relationships. Continued industry enforcement and buyer-side validation are essential to maximizing the standard's effectiveness.