Background
The Google RTB protocol is deprecated, and will sunset on February 15th, 2025. If you have not already done so, we recommend that you migrate to the OpenRTB protocol to avoid an interruption to your Real-time Bidding integration on the sunset date.
This guide is intended to aid you in your migration. It describes every field and concept in the Google RTB protocol and identifies the equivalent field or concept in OpenRTB.
How to use this guide
The BidRequest and BidResponse references included in this guide map individual fields of Google RTB protocol messages to their OpenRTB equivalents if they exist, and provide any additional migration instructions in the Notes column.
The majority of Google RTB protocol fields have a simple mapping to OpenRTB–meaning that you can read the corresponding OpenRTB field equivalently, or with a minor adjustment such as modifying the data type. For more complex mappings, the notes will include a link that you can follow to learn more.
There are some Google RTB protocol fields that have no equivalent in OpenRTB. Google is investigating these gaps and will adjust this guide to reflect their status in a future update. We encourage you to contact our support team and provide feedback if the lack of a mapping for an affected field would hinder your migration.
Migration support
You can reach out to the following support channels if you have questions or need help with your migration:
- Authorized Buyers support forum
- Get answers to public technical questions about the RTB protocols or APIs. This is a public forum. You can search for related questions submitted to this forum to find answers. Don't include any private information in your posts to this forum.
- Technical API support alias:
adxbuyerapi-support@google.com
- Get answers to private questions about the RTB protocols or APIs. Unlike the support forum, questions here are private and can include details about your account that may be needed to investigate your question or issue.
- Your Technical Account Manager (TAM)
- If you have an assigned TAM, they can help with account configuration, product and UI questions, and some technical support.
- Help Center Contact Us form
- If you don't have an assigned TAM, you can use this form to get help with account configuration, product and UI questions, and some technical support.
Protocol representation
OpenRTB Protobuf versus JSON Serialization
Google's OpenRTB implementation supports both JSON and Protobuf formats, which have similar representations with minor differences to accommodate the format. The bid request and response references in this guide refer to the Protobuf format unless stated otherwise, but you can refer to the OpenRTB spec for JSON-specific information. We recommend using the Protobuf format because it has reduced CPU costs for serialization and deserialization, and reduced network costs due to smaller wire size.
Differences between these formats include:
- Boolean (Protobuf) versus integer (JSON) data types: Boolean types defined
in the Protobuf implementation are integers in the JSON format, where
0
isFalse
, and1
isTrue
. - Enumeration (Protobuf) versus integer (JSON) data types: Enumeration fields in the Protobuf format are represented as integers in the JSON format, where the JSON value directly corresponds to Protobuf's enum integer value. These are also equivalent to the set of integer values defined for these fields if they exist in the OpenRTB spec.
- Representation of int64 and fixed64 in JSON: The
int64
andfixed64
types defined in the Protobuf implementation are represented as strings in JSON. - Native request and response message (Protobuf) versus JSON string: The JSON format uses a serialized JSON string defined in the OpenRTB spec to represent native request and response information, whereas the Protobuf format defines equivalent fields and messages that must be used instead. See native ads migration notes for more information.
- Accessing extension fields: For brevity, extension fields described in
the bid request and response references use the JSON field path, where
ext
denotes a Google-specific extension to the parent message. See Extensions for additional information about accessing extension fields with the Protobuf format.
Extensions
Extensions define Google-specific components of the protocol. In the bid request and
response references, ext
included in a field path indicates that the child
field is an extension to the parent field's message. These field paths are representative of
how the extensions are accessed in the JSON format, but the Protobuf format uses extensions
as described in the
Protobuf documentation, where accessing extension fields differs depending on the
language of the generated proto libraries. We recommend reading through the Protobuf
documentation's tutorial for your preferred
language, along with its generated code guide (see:
C++,
Java).
As an example, printing the first element of BidRequest.imp.ext.billing_id
could look like the following:
C++
Java
Eligible Buyers and Deals
In Google RTB, BidRequest.adslot.matching_ad_data
indicates the bidder's
matched pretargeting configs and eligible child seats (see the billing_id
field), eligible deals, and bid floors. In Google RTB, billing IDs are grouped by floor and
deals, but no such grouping exists in OpenRTB.
Here is an example to illustrate how this works. See inline comments for more details.
// Google RTB bid request adslot { matching_ad_data { // Suppose that a bidder has two pretargeting configs with billing IDs 123 and 234 // and suppose that they both match. Also suppose this bidder uses GBP as its // currency. billing_id: 123 billing_id: 456 // The bid floor, as indicated by this field, is in micro units of the currency used // by the buyer indicated by the billing IDs. In this case, suppose the buyer uses // GBP. Then this field represents an £8 CPM floor. minimum_cpm_micros: 8000000 direct_deal { direct_deal_id: 2000 // In Google RTB, the deal price is indicated in CPM micros of the buyer's // currency. fixed_cpm_micros: 20000000 ... } } matching_ad_data { // Suppose that the bidder has a child seat with billing ID 789. Also suppose the // child seat has billing ID 789 and uses USD as its currency. billing_id: 789 // All MatchingAdData.minimum_cpm_micros in a given bid request represent the same // monetary value. In this case, suppose that the buyer uses USD and that the // conversion rate from GBP to USD is 1.25. Then this field represents a $10 CPM // floor, which is the same monetary value as the above £8 CPM floor. minimum_cpm_micros: 10000000 direct_deal { direct_deal_id: 1000 ... } } }
While the OpenRTB bid request contains similar information, it stores billing IDs and deals in separate flat lists, so it is no longer possible to determine which billing IDs are associated with a given deal ID based solely on the bid request. We recommend storing the billing IDs associated with deals in order to determine which are applicable for a given deal at bidding time.
// OpenRTB bid request imp { // In OpenRTB, the bid floor is in CPM, rather than CPM micros. It is in units of the // currency indicated by `bidfloorcur`. bidfloor: 10 bidfloorcur: "USD" ext { // The billing IDs of all of the bidder's matching pretargeting configs and all of // its eligible child seats are stored in a flat list here. billing_id: 123 billing_id: 456 billing_id: 789 } pmp { // All eligible deals are stored in a single flat list. deal { id: 1000 // In OpenRTB, the deal floor is in CPM, not CPM micros. bidfloor: 20 // In OpenRTB, all deals use the same currency. This currency is indicated by // the `Deal.bidfloorcur` field. bidfloorcur: "USD" ... } deal { id: 2000 ... } } }
Ad Categories
Ad categories describe the content of an ad, and are used by publishers to describe types of ads that are blocked when bidding on their inventory. Both Google RTB and OpenRTB support communicating blocked categories in the bid request, and declaring categories for ads returned in the bid response. However, they use different fields and taxonomies to define those categories.
Blocked Categories
When you place a bid, the included creative must not have detected categories that were blocked by the publisher, otherwise the bid will be filtered from the auction.
OpenRTB doesn't distinguish between "product" and "sensitive" categories, so it doesn't use
distinct fields like Google RTB's BidRequest.adslot.excluded_product_category
and BidRequest.adslot.excluded_sensitive_categories
to describe blocked
categories. Instead, it uses the BidRequest.bcat
to identify all blocked
categories, using
IAB Content 1.0 taxonomy
rather than Google's taxonomy defined in the
ad-product-categories.txt
and ad-sensitive-categories.txt
reference files.
// Bid request { // Indicates the blocked categories using IAB Content 1.0 Taxonomy. "bcat": [ "IAB8-18", // Wine "IAB9-9" // Cigars ] "imp": { ... } }
Detected Categories
Google detects categories for ads when they are submitted for review. In order to submit
your ads and identify the categories associated with them, Google recommends that you use
the creatives resource from
the Real-time Bidding API. You can use the
detectedCategories
field to find the detected categories for a creative in IAB Content 1.0 taxonomy. You can
reduce bid filtering by not bidding with creatives with detected categories that appear in
BidRequest.bcat
.
Declare Categories
When submitting a creative for review with a bid, you can declare its categories with
OpenRTB in IAB Content 1.0 taxonomy using the BidResponse.seatbid.bid.cat
field.
This lets you declare any category, whereas Google RTB only supports the declaration of
sensitive categories with the BidResponse.ad.category
field.
Macros
Google continues to support existing macros on the creative and in impression tracking URLs. These macros will be expanded within creatives and impression tracking URLs submitted on the OpenRTB protocol.
In addition, Google will also support the following macros from the OpenRTB standard:
OpenRTB macro | Description |
---|---|
${AUCTION_ID} |
ID of the bid request; from OpenRTB's BidRequest.id field. |
${AUCTION_BID_ID} |
ID of the bid; from OpenRTB's BidResponse.bid.id field. |
${AUCTION_IMP_ID} |
ID of the impression just won; from OpenRTB's BidRequest.imp.id
attribute. |
${AUCTION_SEAT_ID} |
ID of the bidder seat for whom the bid was made. |
${AUCTION_AD_ID} |
ID of the ad markup the bidder wishes to serve; from OpenRTB's
BidResponse.seatbid.bid.adid attribute. |
${AUCTION_PRICE} |
Encoded impression cost in CPI micros of the buyer account currency. This is different
from what is specified in the OpenRTB Standard. The macro will have the exact same
behavior as Google's %%WINNING_PRICE%% macro. |
Native Ads
Access NativeRequest and NativeResponse based on OpenRTB format
If you have configured a bidding endpoint to use OpenRTB in the JSON format, incoming bid
requests can include a serialized JSON native markup request object passed in the
BidRequest.imp.native.request
field to represent native ad inventory, which is
comparable to Google RTB protocol's NativeAdTemplate
. In order for your bidding
endpoint to respond with a bid containing a native ad, it must populate
BidResponse.seatbid.bid.adm
with a serialized JSON native markup response
object, which is comparable to Google RTB protocol's NativeAd
message. These
native markup objects can be found in the
OpenRTB Native Ads Specification, and will be referred to as NativeRequest
and NativeResponse
throughout the documentation.
Google's OpenRTB protobuf format uses
NativeRequest
and
NativeResponse
protocol buffer messages that correspond to OpenRTB's native markup
objects, and can appear directly as fields in bid requests and bid responses, respectively.
If your bidding endpoint is configured to use OpenRTB in the Protobuf format, incoming bid
requests can include the BidRequest.imp.native.request_native
field to represent
native ad inventory, which is the NativeRequest
message defined in the proto
rather than a serialized JSON object. Similarly, your bidding endpoint must populate
BidResponse.seatbid.bid.adm_native
to respond with a bid containing a native ad,
which also uses the NativeResponse
defined in the proto rather than a serialized
JSON object.
The NativeRequest
and NativeResponse
objects or messages contain
identical fields in both formats, so to simplify mapped field paths seen in the migration
content for
NativeAdTemplate
and
NativeAd
, we will use {request/request_native}
and
{adm/adm_native}
to indicate portions of the field path that are dependent on
the format. For example, the full field path for NativeRequest.assets
would be
represented as BidRequest.imp.native.{request/request_native}.assets
.
Representation of native ad templates in OpenRTB
In a bid request including native inventory, the Google RTB Protocol describes the native ad
template with a static set of attributes, whereas OpenRTB represents most of these in
BidRequest.imp.native.{request/request_native}.assets
, which is a list of
Asset
that describes
components of the native ad–such as the headline, body, or logo. Each asset included in the
request has a unique id
value.
When placing a bid including a native ad, your bidding endpoint must specify the required
assets and any optional assets you choose to include in the
BidResponse.seatbid.bid.{adm/adm_native}.assets
field. Assets sent in the
response must include the corresponding id
value specified in the bid
request—this is used to structure the template and distinguish similar kinds of assets
such as logos and icons. Here's an example demonstrating how NativeRequest
is
populated and its corresponding NativeResponse
: