OpenWrap - InApp Developer Guide: iOS InApp Header Bidding for MoPub (1.2.2)

Document created by catherine.racette on Aug 8, 2017Last modified by catherine.racette on Oct 26, 2017
Version 22Show Document
  • View in full screen mode

(Version 1.2.2)

Introduction

In-App Header Bidding allows publishers to allocate ad inventory using a technology and methodology that bypasses inefficiencies that have kept apps from finding the best prices.


Header bidding is the process of sending out an initial ad call to one or more buyers to solicit an exact price for inclusion in the ad server’s inventory allocation process.

 

High-Level Process Overview

  1. The prefetch/header bidding ad call needs to be initiated before requesting ad from Primary SDK.
  2. Buyers get first look at the inventory and submit a pre-bid price.
  3. This pre-bid price then becomes the bid floor for the ad server call, which checks if any other buyers in the same priority tier can beat it. As a result, inventory gets allocated to the highest yielding buyer while respecting other publisher controls that may have been set up in the ad server.

 

Header bidding primarily benefits publishers who use third party SDKs (e.g., MoPub) to manage their ads. However, MoPub doesn’t allow publishers to effectively pull in programmatic buyers that compete against Marketplace and direct deals, so publishers are limited as to which buyers they can utilize.

 

When a page in the publisher's app is loaded, the code reaches out to PubMatic for bids before the ad server’s direct sales are called.

 

The diagram below shows how PubMatic OpenWrap - InApp header bidder integrates with publisher’s app.

The header bidding arrangement accomplishes several objectives:

  • All the demand sources are bidding at the same time, which replaces waterfall’s preferential ordering of buyers.
  • Advertisers have a chance at obtaining the best ad inventory.
  • Stats have shown publisher gains as high as 50 percent in CPMs when moved to header bidding setup.

Supported Ad Formats 

  • Simple Banner

Prerequisites

Before continuing with the in-app code integration, use the guidelines in the MoPub SDK documentation to get started with MoPub integration for iOS.

 

In-App Code Integration

Use the instructions below to complete the in-app code integration.

  1. Integrating the PubMatic Sample Code in the Publisher’s Application
  2. Creating a Header Bidding Request
  3. Prefetching Bids Using PMPrefetchManager
  4. Handling Prefetched Bids from PMPrefetchManager
  5. Receiving Winning Bids using MoPub’s Custom Event Handler
  6. Getting Rendered Ad from Prefetched Creative
  7. Using HeaderBiddingBannerHelper (Optional)
  8. Setting Refresh Interval (Optional)
  9. App debugging

Integrating the PubMatic Sample Code in the Publisher’s Application

Copy the contents of the Headerbidding folder to the Publisher’s iOS application. Refer to PubMatic's Sample application for faster and easier integration.

 

Creating a Header Bidding Request

  1. Import PMPrefetchManager file as shown below.
#import "PMPrefetchManager.h" 
  1. Create Impression objects that contain information about specific ad slots like impressionId (Unique identifier), slot name, sizes and slot index. 
    PMBannerImpression *impression = [[PMBannerImpression alloc] initWithImpressionId:<ImpressionId>
    slotName:<slotName> slotIndex:<SlotIndex> sizes:<AdSizes>];

    ImpressionId :
    Used to identify unique ad slot/banner of MoPub screen.This should match with imp_id configured in step 2 in Ad Server Setup section below.

    SlotName: A string identifier. It should be the same slot name mapped to PubMatic ad tag. Please refer to mapping in an Excel sheet in the PubMatic Setup section below (Internal only).

    SlotIndex:
    Required when the same adunit is used multiple times on the screen. If there are two adunits on the screen, testAdunit (Above the fold) and testAdunit (Below the fold), then slotindex can be used to differentiate between slots with same name.

    AdSizes :
    Array of PMSize objects that lets you request an ad with different sizes.

  2. Create a prefetch request object by specifying the publisher id and impressions, from step 1, to request prefetched bids. It is required to make an ad request to PubMatic against impression objects.
    Sample code for creating ad request & setting some basic parameters:
    PMBannerPrefetchRequest * prefetchAdRequest = [[PMBannerPrefetchRequest alloc] initForPrefetchWithPublisherId:<PublisherId> impressionArray:<impressions>]; 
        [prefetchAdRequest setAwt:PMAWTSeparateTracker];
        [prefetchAdRequest setKeywords:@"entertainment,sports"];
        [prefetchAdRequest setEthnicity:PMEthnicityAsianAmerican];
        [prefetchAdRequest setDnt:NO];
        [prefetchAdRequest setPaid:NO];
        [prefetchAdRequest setDma:@"734"];
        [prefetchAdRequest setCoppa:YES];
        [prefetchAdRequest setIABCategory:@"IAB1-1,IAB1-7"];

    For additional parameter details, please refer to Table 3 in the PubMatic Prefetch API Parameter Details section below.

                    
  3. You can also specify additional targeting information on PMBannerPrefetchRequest object such as store URL, app domain, gender, ethnicity and much more.

 

Prefetching Bids Using PMPrefetchManager

  1. Create PMPrefetchManager object. Please note that PMPrefetchManager instance must be created using sharedInstance method to share prefetched creative in adapter.
PMPrefetchManager *prefetchManager = [PMPrefetchManager sharedInstance]; 
    prefetchManager.delegate = self;

Set a network timeout (In seconds) using maxNetworkTimeout property of PMPrefetchManager. Default, network timeout is 3 seconds.

 

  1. Adopt the PMPrefetchDelegate and implement the delegate methods.
    - (void)prefetchManager:didReceiveBids: 
    - (void)prefetchManager:didFailWithError:

     

  2. Call prefetchCreativesForRequest: on PMPrefetchManager object created in step 1.

Handling Prefetched Bids from PMPrefetchManager

  1. Upon success, the PMPrefetchManager will respond with delegate callback - (void)prefetchManager:didReceiveBids: with a map of PMBid objects.

    The keys for this map will be the impression ids. The PMBid object contains impression id, status and price information. 
    Example:
    - (void)prefetchManager:(PMPrefetchManager *)prefetchManager didReceiveBids:(NSDictionary *)bids 
    {
    //get bid for impressionId.
                PMBid *bid = bids[impressionId];
    }

    Call MoPub ad with pre fetched bid information. Please note prefetchManager: didReceiveBids: & prefetchManager:didFailWithError are called on a secondary thread to do UI work from these callbacks dispatch it on main queue.

  2. Set bid details from PMBid object as keywords for MoPub ad.

     NSMutableString * keywords = [NSMutableString new]; 
    [keywords appendFormat:@"%@:%d,",@"bidstatus",bid.status.intValue];
           [keywords appendFormat:@"%@:%0.1f,",@"m_bid",bid.price];
           [keywords appendFormat:@"%@:%@,",@"bidid",bid.impId];

         if (bid.dealId) {
                    [keywords appendFormat:@ "%@:%@",@"wdeal",bid.dealId];
                }
    banner.keywords = [NSString stringWithString:keywords];
    (banner is an MPAdView object)

    Note: dealId is used for PMP deals. and bid price is rounded till single decimal digit

                    
  3. Call loadAd: on MPAdView

    dispatch_async(dispatch_get_main_queue(), ^{ 

    [banner loadAd];
    });

    banner: Instance of MPAdView

     

Receiving Winning Bids using MoPub's Custom Event Handler

The publisher must implement a custom event handler subclassing MoPub’s MPBannerCustomEvent.

 

For every winning bid, this event handler will receive event

- (void)requestAdWithSize:(CGSize)size customEventInfo:(NSDictionary *)info 

 

...where, info dictionary contains the impressionId for which the header bid has won.

 

 

Getting Rendered Ad from Prefetched Creative

Call renderedViewForImpressionId:adSize: method on PMPrefetchManager passing the impressionId and size received in the previous step. In case of success, this method will return a rendered creative in a webView & fire impression trackers.

 

NSString *key = [info objectForKey:@”imp_id”]; 
UIWebView *webview = [self.prefetchManager renderedViewForImpressionId:key adSize:size];


Call bannerCustomEvent:didLoadAd: on the custom event class delegate if a valid ad is returned (i.e. webview is not nil)

 

if (webview) { 
        [self.delegate bannerCustomEvent:self didLoadAd:webview];
    }else{
        
        MPLogInfo(@"Failed to render prefetched Ad creative");
        [self.delegate bannerCustomEvent:self didFailToLoadAdWithError:nil];
    }


Using HeaderBiddingBannerHelper (Optional)

The HeaderBiddingBannerHelper is a template that manages the PubMatic pre-fetch calls and makes ad server requests by providing PubMatic bids. This step is optional and can be skipped, particularly if a publisher would like more control over the Ad server calls (MoPub ad request). Alternatively, a publisher may choose to complete this step, as HeaderBiddingBannerHelper class can make the integration easier. 

 

Customize this class to integrate any other header bidding partner in addition to PubMatic.

  1. Create a AdSlotInfo object for each ad slot by providing slot name , list of ad sizes(PMSize) and MPAdView.
    AdSlotInfo * adSlot = [[AdSlotInfo alloc] initWithBannerView:self.mopubAdView slotName:<SlotName> sizes:<AdSizes>]; 

 

  1. Create a list of AdSlotInfo objects
  2. Create an object of MoPubHeaderBiddingBannerHelper with the ad slot list created in step 2 and call execute.
    MoPubHeaderBiddingBannerHelper *helper = [[MoPubHeaderBiddingBannerHelper alloc] initWithAdSlotInfo:<adSlotInfoArray> publisherId:<pubId> controller:<conroller>]; 
    [self.helper execute];

 

Setting Refresh Interval (Optional)

This solution provides an optional feature to auto refresh the banner ad after a specified interval.

 

The default value for refresh interval is 0 seconds, i.e., by default auto refresh feature is disabled. The publisher can set an appropriate refresh interval using the refreshInterval property of PMPrefetchManager. Expected value should be in range of 12 to 120.

Table 1. Ad refresh behaviour on setting refresh interval value:

Value (X) in secondsBehaviour
X<=0Ad will not refresh
X > 0 & X <= 12Ad will get refreshed after every 12 seconds.
X > 12 & X <=120Ad will get refreshed after every X seconds
X > 120Ad will get refreshed after every 120 seconds

 

Note: To use this feature, please disable the ad server’s refresh functionality. Please refer to the MoPub portal documentation for additional information.

                

ATS Configuration on iOS 9.0 or later

App Transport Security (ATS) is enabled by default for apps linked against the iOS 9.0 or later. Currently, Pubmatic’s mobile header bidding solution uses HTTP end point. Thus, you need to add exceptions by configuring NSAppTransportSecurity key’s value in your app’s Info.plist file.

 

e.g. Add following to your Info.plist file.

<key>NSAppTransportSecurity</key>
<dict>
     <key>NSAllowsArbitraryLoads</key>
     <true/>
</dict>

For more details see ATS reference in Apple’s documentation.

 

App Debugging

Header bidding code logs the request & response from the PubMatic server in debug mode. This debug log can help to see if PubMatic is providing proper bids or not. Below is sample logs from Header bidding sample application.

 

PubMatic Prefetch API Parameter Details

Please refer the following properties for sending the targeting parameter values.

 

Table 2. PMBannerPrefetchRequest properties

S. noMethodDescription
1storeURLURL of the app store from where a user can download this application. This URL must match the storeurl that is whitelisted in the UI.
2appDomainIndicates the domain of the mobile application.
3paid

Indicates whether the mobile application is a paid version or not. Possible values are:

  • PMBOOLNo - Free version
  • PMBOOLYES - Paid version
4awt

Indicates whether the tracking URL has been wrapped or not in the creative tag.

Possible options are:

  • PMAWTSeparateTracker - Indicates that the tracking URL is sent separately in the response JSON as tracking_url. In this case, the tracking_url field is absent in the JSON response.
  • PMAWTiframeEmbeddedTracker - Indicates that the tracking_url value is wrapped in an Iframe and appended to the creative_tag.
  • PMAWTJSEmbeddedTracker - Indicates that the tracking_url value is wrapped in a JS tag and appended to the creative_tag.
5pmZoneIdThis parameter is used to pass a zone ID for reporting.
6ethnicityNumeric code of ethnicity.
7userIncomeUser's income or income range in dollars (whole numbers). For example, inc=50000 or 50000-75000. 
8birthYearVisitor's birth year as a four-digit integer. For example, 1975.
9genderGender of the visitor. Possible values are:
  • PMGenderMale - Male
  • PMGenderFemale - Female
  • PMGenderOther - Others
  • PMGenderUnknown - Unknown
10cityCity of the user. For example, city=New York
11zipHome zip code if the visitor is present in the U.S.; otherwise it indicates the postal code. 
12coppa

Indicates whether the visitor is COPPA-specific or not. For COPPA (Children's Online Privacy Protection Act) compliance, if the visitor's age is below 13, then such visitors should not be served targeted ads.

 

Possible options are:

  • PMBOOLNo - Indicates that the visitor is not COPPA-specific and can be served targeted ads.
    • PMBOOLYES - Indicates that the visitor is COPPA-specific and should be served only COPPA-compliant ads.

 

The United States Federal Trade Commission has written a comprehensive FAQ on complying with COPPA at http://business.ftc.gov/documents/Complying-with-COPPA-Frequently-Asked-Questions.

13appCategoryApplication primary category as displayed on storeurl page for the respective platform.  
14keywordsList of keywords indicating the consumer's interests or intent. 
15latitudeLatitude of the device location.
16longitudeLongitude of the device location.
17dntIf set, it restricts user and device targeting. 
This can also be set by enabling the “Limit Ad Tracking” option in the iOS device.
18isIDFAEnabled

If set, it uses advertisement id otherwise it uses vendor id for targeting.

 

This has effect only if 'dnt' is set to NO.

19udidHashTypeAllows to apply following hashing on udid param value before sending to server 
  •  PMUdidhashTypeUnknown=0,
  • PMUdidhashTypeRaw=1,
  • PMUdidhashTypeSHA1=2,
  • PMUdidhashTypeMD5=3

Default is PMUdidhashTypeRaw

20IABCategory

List of IAB content categories for the overall site/application. Refer the "Table 6.1 Content Categories" in the Open RTB 2.1 / 2.2 specifications document. If the site/application falls under multiple IAB categories, you can send categories separated by comma.

Note: For more details about these parameters, please refer to HTTP Parameters Details (SSP Ad Server) 

                

PubMatic Mapping 

Inventory mapping for PubMatic slots and ad tags must be completed in the PubMatic Admin console. Please contact your Customer Success Manager to complete this process.

 

Ad Server Setup on MoPub

The following steps are required so impressions can be allocated to PubMatic by the ad server, based on actual bid price and the recommendation from PubMatic. These are passed to the ad server using key-value pairs added to the MoPub ad request using PubMatic OpenWrap - InApp header bidding code.

 

The publisher needs to provide trafficker level access to create these line items to the email id provided by the PubMatic operations team.

 

Step 1: Create a new order in MoPub for In-App Header Bidding API with PubMatic as the advertiser and add the relevant details.

 

Step 2: Set the price and priority of the line items.

  • Select Network for Type and a Priority of 12. (To enable PubMatic’s response to compete with MoPub Marketplace and Ad Networks).
  • Select Custom Native Network for the Network and add Class name and Data. <Class> is an adapter (subclass of CustomEventBanner class) class name. Data should be a map of <imp_id>:<adunit_id>. Add <imp_id> same as impression id passed in PMBannerImpression.   

Step 3: Ad unit targeting. Assign line items to appropriate ad units.

 

 

Step 4: Set targeting on the “bidstatus” value as 1 from the In-App Header Bidding API tag’s response. In addition to “bidstatus”, you can also set targeting on “m_bid”. For more information, please refer to the Best Practices to Create Tags in the Ad Server section. 

 

Pre-Launch Verification

Before setting traffic live, PubMatic’s Solutions Engineering team will assist the publisher’s technical and ad operations teams conduct pre-launch verification. Once verifications are complete the setup is ready to go live on a small number of sites. Post-launch, the PubMatic Operations team will ensure that the publisher is achieving the desired results and will provide consultation to ramp up the implementation.

 

Best Practices for Creating Line Items in the Ad Server

To control monetization through In-App Header Bidding at a granular level, you may:

  • Create multiple In-App Header Bidding line items in the ad server for each ad unit/ad size/CPM range/geo.
  • Use “m_bid” as the targeting attribute.
  • Place the line items at different priorities based on their pricing and relevance.

 

Important Notes:

  • Currently PubMatic supports (one decimal point) 10 cent granularity in key value targeting.
  • The maximum length of the keywords that MoPub supports is 10K characters. As a result, you can approximately add 300+ bid values in each line item, assuming each targeting line has 30 characters.

    Example:
    This line item will match any ad request containing keyword "bidstatus:1,m_bid:0.#" (# between 0 to n) 
    m_bid:0.1 AND bidstatus:1
    m_bid:0.2 AND bidstatus:1
    m_bid:0.3 AND bidstatus:1
    ...
    m_bid:0.n AND bidstatus:1

 

Examples:

If 80% of the bids are between $0 to $3, create line items at a $0.1 granularity. For other ranges you can create line items at a higher granularity.

 

Sample Variations:
30 line items between $0-$3 with rate increment of $0.1

  • LineItem 1 (covers $0-$0.09) Targeting: bid=0.01,bid=0.02....,bid=0.09, rate=$0.05
  • LineItem 2 (covers $0.10-$0.19) Targeting: bid=0.1, rate=$0.15
    and so on for next 28 line items

15 Line items between $3-$8 with rate increment of $0.30

  • LineItem 31 (covers $3.0-$3.29) Targeting: bid=3.01,bid=3.1,bid=3.2, rate=$3.15
  • LineItem 32 (covers $3.30-$3.59) Targeting: bid=3.3,bid=3.4,bid=3.5, rate=$3.45
    and so on for next 13 line items

12 Line items between $9-$20 with rate increment of $1.0

  • LineItem 46 (covers $9.0-$9.99) Targeting: bid=9, rate=$9.5
  • LineItem 47 (covers $10.0-$10.99) Targeting: bid=10, rate=$3.45
    and so on for next 10 line items

 

A final high- priority line item for very high bids

  • Line Item 58 (Covers $20 and above) Targeting : bid=20,bid=21,bid=22...... bid=50) rate= $21

 

Reporting

Reporting is provided through PubMatic’s comprehensive analytics platform. Header Bidder Performance report provides insights into how PubMatic in-app header bidder is performing.

 

  • MoPub reporting functionality should be used if reporting at the line item level is required.
  • Header Bidder Performance Report is available in the PubMatic UI. Select Analytics | Reports | Advanced Reports from the main navigation.

 

Sample Report

Attachments

    Outcomes