Show OTT Video Ads with Prebid

In this tutorial, we’ll detail how to set up Prebid.js to display a Programmatic OTT with Prebid (POP) video ad (ad pod) from Google Ad Manager (GAM).

Prerequisites

The code example below was built with Prebid.js and the following:

For example, to build with the AppNexus bidder adapter and GAM use the following command:

gulp build --modules=appnexusBidAdapter,dfpAdServerVideo

For more information about how to build with modules, see the Prebid module documentation.

Ad Pod Module

When the dfpAdServerVideo module is included in the Prebid.js build, the Ad Pod module, for working with ad pods, is automatically included. This module enables developers to add support for an adserver, like Google Ad Manager or Freewheel, that handles ad unit types of adpod. Specifically, the module provides functions to validate, cache, and modify long-form video bids.

Implementation

This section provides information on how to implement and configure Prebid.js to display ad unit types of adpod.

1. Create an ad unit

Create an ad unit that contains a video mediaType object and set the mediaTypes.video.context to adpod. Set the other parameters to the specific properties for the publisher’s inventory.

var videoAdUnit = [{
        code: 'sample-code',
        sizes: [640,480],
        mediaTypes: {
            video: {
                context: 'adpod',
                playerSize: [640, 480],
                adPodDurationSec: 300,
                durationRangeSec: [15, 30],
                requireExactDuration: true
            }
        },
        bids: [
            {
                bidder: 'appnexus',
                params: {
                    placementId: 14542875
                }
            }
        ]
    }];
};

2. Get ad pod targeting

If a publisher wants to retrieve ad pod targeting and create the master tag themselves they can use the getAdPodTargeting method of the dfpAdServerVideo module. The method requires an array of ad unit codes and returns targeting key values and the cache id as JSON.

Example:

pbjs.adServers.dfp.getAdpodTargeting({
  codes: ['adUnitcode-1'],
  callback: function(err, targeting) {
    // Pass targeting to publisher api which will construct the master tag
  }
});

Sample return:

{
  'adUnitCode-1': [
    {
      'hb_pb_cat_dur': '10.00_<label>_15s'
    },
    {
      'hb_pb_cat_dur': '15.00_<label>_30s'
    },
    {
      'hb_cache_id': '123'
    }
  ]
}

Parameters

Parameter Scope Type Description
codes Required [string] An array of adunit codes.
callback Required function Call back function to pass targeting key-values to publisher API for construction of the master tag.

3. Configuring for competitve exclusion
Competitive exclusion is the process of preventing ads in the same industry group from appearing either in the same ad pod or adjacent to each other in the same ad pod. To enable competitive exclusion Prebid.js will need to be configured properly.

After you have instantiated a Prebid instance, call the setConfig method and add the following key-values.

pbjs.setConfig({
  'adpod': {
    'brandCategoryExclusion': true
  }
});

When this setting is enabled, it requires the bidder to include a brand category id on the incoming adpod bids (otherwise the bid is rejected). The bid’s brand category will be processed and transformed to the corresponding brand category used by the publisher’s adserver (see the Category Translation module page for more details). The transformed brand category is then used in the bid caching process and targeting keys that get sent to the adserver for the winning bid(s).

Publishers need to provide a mapping file that will convert IAB sub categories to their labels. Publishers can set the mapping file using:

pbjs.setConfig({
    "brandCategoryTranslation": {
        "translationFile": "<url_to_file>"
    }
});

Publishers should ensure that the JSON returned from their custom translation file is valid for Prebid by adhering to the following structure:

{
    "mapping": {
        "<your-iab-sub-category>": {
            "id": "<label id or name>",
            "name": "<label name>"
        },
   ...
   }
}

Your ad ops team will need to add labels to the line item to indicate which industries will be included in your competitive exclusion.

Here is an example of the targeting key’s value with the setting enabled (where 123 is the brand category id):

  hb_pb_cat_dur = '10.00_123_10s'

When the setting is disabled (which is the default state), bidder’s don’t have to supply a brand category on the adpod bids. The category part of the bid caching is not included and is not within the generated targeting keys.

The following is an example of the targeting keys with the setting not enabled:

hb_pb_cat_dur = '10.00_10s'

4. Implement Custom Price Buckets

By default, Prebid.js caps all CPMs at $20. With sell side video there may be an expecation to see CPMs over $20. In order to receive those bids, custom price buckets need to be implemented by setting the priceGranularity object of the setConfig method.

For instructions on setting custom price buckets, view the Custom Price Granularity Buckets documentation on prebid.org.

5. Send request for bids and build video URL

The dfpAdServerVideo module provides a method, buildAdpodVideoUrl, that combines publisher-provided parameters with Prebid.js targeting key values to build a GAM video ad tag URL that can be used by a video player.

In the example below the callback in the bidsBackHandler returns the video ad tag needed by the video player.

pbjs.que.push(function(){
    pbjs.addAdUnits(videoAdUnit);
    pbjs.setConfig({
        cache: {
            url: 'https://prebid.adnxs.com/pbc/v1/cache'
        },
        adpod: {
            brandCategoryExclusion: true
        },
        brandCategoryTranslation: {
            translationFile: "https://mymappingfile.com/mapping.json"
        }
    });

    pbjs.requestBids({
        bidsBackHandler: function(bids) {
            pbjs.adServers.dfp. buildAdpodVideoUrl({
                codes: ['sample-code'],
                params: {
                    iu: '/123456/testing/prebid.org/adunit1',
                    description_url: 'https://mycontent.com/episode-1'
                },
                callback: function(err, masterTag) {
                    // Invoke video player and pass the master tag
                }
            });
        }
    });
});

Parameters

Parameter Scope Type Description
iu Required string adunit
description_url Required string The value should describe the video playing on the page.

Understanding the arguments to this method is especially important if you plan to pass any custom parameters to GAM. The params key in the argument to buildAdpodVideoUrl supports all parameters from the GAM API.

Further Reading

Prebid API Reference
Prebid.js Video Overview
Prebid.js Long Form (Ad Pod) Video