Guides
OpenRTB deals and PMP, explained: preferred, private auction, programmatic guaranteed
"PMP," "preferred deal," and "programmatic guaranteed" are commercial terms, not OpenRTB objects. The spec gives you a small set of fields, and the deal types are conventions expressed through them. This guide maps each commercial deal to the exact JSON that carries it, so you can read a pmp block and know what kind of deal you are looking at.
The four deal types, commercially
- Open auction. The public marketplace: any eligible buyer can bid, no prearrangement. No deal at all.
- Private auction (PMP). A closed auction among invited buyers, often at a higher floor, competing on price.
- Preferred deal. A fixed, negotiated price offered to one buyer who gets first look at the inventory but is not obligated to buy.
- Programmatic guaranteed (PG). A committed buy: fixed price, fixed volume, the buyer is obligated to purchase, closest to a traditional direct deal executed programmatically.
The objects that carry them
Deals hang off an impression in the Pmp object (Section 3.2.11), which holds two things:
private_auction:0means open bids are still accepted alongside any deals;1means bidding is restricted to the deals listed and their terms.deals: an array ofDealobjects.
Each Deal (Section 3.2.12) carries the terms:
id(required): the deal ID, the join key both sides agree on in advance.bidfloor/bidfloorcur: the deal price or floor. Note this does not inherit fromimp.bidfloorcur; it defaults to USD on its own.at: an optional per-deal auction type override.1first price,2second price plus, and3means the value inbidflooris the agreed fixed deal price.guar:1marks a guaranteed deal the bidder must bid on;0is the default.wseat/wadomain: restrict which buyer seats or advertiser domains may bid on the deal.
Mapping commercial deals to fields
| Deal type | private_auction | Deal.at | Deal.guar | Price |
|---|---|---|---|---|
| Open auction | 0 (no deal) | request at | n/a | Auction clears |
| Private auction | 1 | 1 or 2 | 0 | Floor, competitive |
| Preferred deal | 1 | 3 (fixed) | 0 | Fixed, first look |
| Programmatic guaranteed | 1 | 3 (fixed) | 1 | Fixed, committed |
The exact combination varies by exchange, since these are conventions rather than spec-mandated encodings, but the axes are always the same: is bidding restricted (private_auction), is the price fixed or auctioned (at), and is the buyer obligated (guar).
The deal ID is the join key
Everything hinges on Deal.id. It is negotiated out of band, then the seller puts it in the bid request and the buyer matches on it to apply the agreed terms. If the IDs do not match on both sides, the deal simply never triggers, and the impression falls through to open-auction pricing with nobody noticing an error. A mismatched or missing deal ID is the most common reason a deal "isn't working."
Common mistakes
- Assuming
Deal.bidfloorcurinherits. It does not. Omitting it means USD, which silently mis-prices a non-USD deal. See bid floors. - Marking a deal
guar: 1without meaning must-bid. A guaranteed deal obligates the bidder; setting it loosely breaks bidder logic. - Setting
private_auction: 1but expecting open bids. That value restricts bidding to the listed deals only.
Validate the pmp block
Deal terms are easy to get subtly wrong and hard to notice, because a broken deal falls through silently. Paste a request with a pmp block into the tester to check the structure, and read the auction-type mechanics in first-price vs second-price.