Download the OpenWrap for Android sample app— OpenWrap_Android.zip
OpenWrap In-App lets publishers solicit multiple programmatic bids for their mobile in-app inventory. OpenWrap sends an initial ad call to one or more header bidding partners to solicit bids for inclusion in the ad server’s inventory allocation process.
High-Level Process Overview
- The OpenWrap call happens before requesting an ad from the primary AdServer SDK.
- Programmatic buyers get first look at the inventory and submit a bid price.
- OpenWrap conducts a server-side auction between bids from different header bidding partners configured by the publisher, then selects a winning bid.
- This winning bid data (including bid eCPM and winning partner) accompanies 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 on the ad server.
OpenWrap primarily benefits publishers who use third party SDKs (for example, DFP) to manage their ads. However, DFP doesn’t allow publishers to effectively include programmatic buyers that compete against AdX and direct deals, so publishers are limited in the buyers they can use.
When a view with an ad slot in the publisher's app loads, the OpenWrap code sends a request to the OpenWrap S2S service for bids before calling the ad server. OpenWrap makes the bid requests in parallel instead of using a sequential waterfall and provides publishers with access to many demand sources.
The diagram below shows how PubMatic OpenWrap integrates with a publisher’s app.
If desired, publishers can also let the winning bid compete with prices available from the direct-sold ads.
OpenWrap In-App provides the following benefits:
- All the demand sources are bidding at the same time, replacing the preferential waterfall order of buyers.
- Advertisers have a chance to obtain the best ad inventory.
- Publishers have seen a monetization increase as high as 50%.
Supported Ad Format
This depends on the setSupportedAPIs parameter value you set on a PMBannerImpression object. This solution gives you full rendering control and applications use their own rendering capabilities to support specific API frameworks, such as MRAID1, MRAID2, VPAID, ORMMA, and so on.
In-App Code Integration
Download the OpenWrap for Android sample app for faster, easier integration. Copy the highlighted core package into your Android app project.
Adding Permissions to the Manifest File
Declare the following security permissions in your manifest file (AndroidManifest.xml).
Table 1: Basic Permissions for the Manifest File
|Permission||Description and Manifest file entry|
Access the Internet. Required for ad-content download.
Access the Network state. Required for retrieving network details from ConnectivityManager
This solution provides two integration approaches. Use the approach that satisfies your requirements.
- Approach 1: Prefetch Bids Using PMPPrefetchManager & PMPrefetchRequest
- Approach 2: Using PMWrapperManager
Approach 1: Prefetch Bids Using PMPPrefetchManager & PMPrefetchRequest
Use the APIs to simply prefetch bids using PMPrefetchManager and PMPrefetchRequest. You get full control on making the ad server (DFP) request by passing a prefetched bid and handling ad server mechanism to determine if the bid wins.
- Creating a Prefetch Request
- Prefetching Bids Using PMPrefetchManager
- Handling Prefetched Bids From PMPrefetchManager
- Calling DFP Ad With Pre-Fetched Bid Information
- Receiving a DFP App Event Callback
- Rendering Prefetched Creative
Creating a Prefetch Request
Create Impression objects that contain information about specific ad slots like impressionId (Unique identifier), slot name and sizes. It is required to make an ad request to PubMatic against impression objects. You may optionally set pmZoneId, custom parameters and supported API framework for this impression. For example:
<ImpressionId> = used to identify unique DFP ad slot/banner on screen, which should match with imp_id configured in step 2 of Ad Server Setup (DFP).
<SlotName> = a string identifier that should be the same slot name mapped to PubMatic ad tag. See PubMatic Mapping.
<AdSizes> = list of PMAdSize used to request an ad with different sizes.For additional parameter details, see Table 4 of PubMatic Prefetch API Parameter Details .
PubMatic requires a prefetch request object to make an ad request against impression objects. Create a prefetch request object by specifying the publisher id and impressions from step 1:
<PublisherId > = unique publisher id.
<P rofileId> = wrapper profile Id of the publisher.
<Impressions> = list of PMBannerImpression objects created in step 1.
Contact your Customer Success Manager to get the PublisherId and ProfileId.
Optionally, specify targeting information on the prefetch request object such as store URL, app domain, gender, and much more.
Sample code for setting basic parameters:
For additional parameter details, see Table 3 in PubMatic Prefetch API Parameter Details .
Prefetching Bids Using PMPrefetchManager
Create a Prefetch Manager object.
Create an object of PMPrefetchListener and set it to PMPrefetchManager, created in above step:
Optionally, set a network timeout using setNetworkTimeout(<timeout in seconds>) method on PMPrefetchManager instance. Default network timeout is 3 seconds, defined as NETWORK_TIMEOUT_SECONDS in PubMaticConstants.java. You can customize it as required. It defines the maximum timeout required to get the response from PubMatic ad server. DFP will send the call if PubMatic responds before the timeout, or when the timeout elapses without a response.
Call prefetchCreatives() on instance of PMPrefetchManager created in step 1.
Handling Prefetched Bids From PMPrefetchManager
- Upon Success, the Prefetch Manager responds with a callback onBidsFetched() with a map of PMBid objects. The keys for this map are the impression ids. The PMBid object contains impression ids and bid information. Save these bids and use them to render ads later if the wrapper bid wins.
Create a PublisherAdRequest.Builder object (in DFP SDK), providing it with all the custom targeting information using addCustomTargeting().Targeting map contains deal id (for key pwtdid), which is used for PMP deals and bid status (for key pwtbst), which is used for reporting.
Calling DFP Ad With Pre-Fetched Bid Information
Create a PublisherAdRequest object, providing it with all the targeting information using requestBuilder
PublisherAdViewclass object, then pass the
publisherAdRequestcreated in step 1.
Receiving DFP App Event Callback
For every winning bid, a DFP app event callback is received via AppEventListener (from DFP SDK):
Implement the AppEventListener and override the onAppEvent() callback method:
- key = app event name. It should be the same as mentioned in step 4 of Manual Creation of Ad Server Line Items.
- winningImpressionId = impressionId for which the wrapper bid has won.
For getting the onAppEvent() callback method, make sure you assigned the app event listener to DFP ad view:
Rendering Prefetched Creative
Fetch the PMBid object for the winning impression id, from the bids you saved earlier in the onBidsFetched() callback of PMPrefetch Listener . This object contains the winning creative in the getCreative(). Use this method to render the ad. For example, use a simple WebView for a banner ad, or a custom MRAID or VPAID ad.
Approach 2: Using PMWrapperManager
This solution provides a standard way (implementing
PMWrapper interface) to easily write your wrapper class to handle making calls to the DFP ad server. The PMWrapperManager handles fetching wrapper bids from PubMatic and handing over them to your wrapper object to initiate the ad server call.
Use the PMWrapperManager class as a convenient way to integrate PubMatic's OpenWrap solution with a DFP ad server. PMWrapperManager initiates prefetch requests to PubMatic and also to the DFP ad server requests through wrapper objects that implement the PMWrapper interface.
You can write your own wrapper class implementing the PMWrapper interface and implementing AppEventListener to handle DFP ad events. See PMDFPWrapper in the OpenWrap for Android sample app for an example.
PMDFPWrapperobject for each ad slot by providing slot name , list of ad sizes, and
- Write code that makes the DFP ad server request in requestAndLoadAd(<PMBid>) method. The PMWrapperManager calls this method of your wrapper class by passing the bid from PubMatic to initiate the ad server call. Save this bid to render the ad later.
Implement an impression() method to return the PMBannerImpression object. PMWrapperManager uses this method to get the impression object representing your ad slot. Your code may be similar to the following:
<ImpressionId> = identifies unique ad slot/banner of DFP on screen.
<SlotName> = a string identifier that should be the same slot name mapped to the wrapper ad tag. See PubMatic Mapping.
<AdSizes> = array of PMAdSize objects for requesting an ad with different sizes.
Create a list of
PMDFPWrapperobjects, one wrapper object to represent a single ad slot.
Create an object of
PMWrapperManagerwith the wrapper object's list created in step 1 and a profile id. You can optionally set version id. See PubMatic Prefetch API Parameter Details for more information.if the version id is not set, OpenWrap defaults to using the live version of the profile.
Optionally set the targeting parameters in your request object.
<ProfileId> = wrapper Profile Id of the publisher.
<PublisherId> = unique Publisher Id.
loadAd()on wrapper manager.
- The wrapper manager fetches bids from PubMatic and initiates ad server calls through your wrapper objects by passing these bids.
Rendering the Ad
Once the ad server notifies that the PubMatic bid has won—that is, by sending the PubMatic specific app event in PMDFPWrapper implemented above—use the getCreative() method from the bid stored in step 2 and render the creative with your own implementation. This solution also provides a simple banner rendering. Just call PMWrapperManager.getPubMaticAdView(<Context>, <PMBid>) and pass the bid stored in step 2. This returns an object of customized WebView with a rendered banner ad. Add this into your parent view where you want to show the ad.
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; that is, auto-refresh is disabled by default. You can set an appropriate refresh interval using the setRefreshInterval(<value in sec>) of PMPrefetchManager. The expected value should be in the range of 12 to 120 seconds.
Table 2: Ad refresh behavior on setting refresh interval value
|Value (X) in seconds||Behavior|
|X<=0||Ad will not refresh|
|X > 0 & X <= 12||Ad will get refreshed after every 12 seconds.|
|X > 12 & X <=120||Ad will get refreshed after every X seconds|
|X > 120||Ad will get refreshed after every 120 seconds|
OpenWrap code logs the request and response from the PubMatic server in debug mode. This debug log can help to determine if PubMatic is providing proper bids or not. Below is a sample log from the OpenWrap for Android sample app.
PubMatic Prefetch API Parameter Details
Please refer the following setter functions for sending the targeting parameter values.
Table 3: PMPrefetchRequest APIs/Setters
|1||setStoreURL(String storeUrl)||URL of the app store from where a user can download this application. This URL must match the storeurl that is whitelisted in the UI.|
|2||setAppDomain(String appDomain)||Indicates the domain of the mobile application|
Indicates whether the mobile application is a paid version or not. Possible values are:
False = Free version
|4||setBirthYear(String yearOfBirth)||Visitor's birth year as a four-digit integer. For example, 1975.|
Gender of the visitor. Possible values are:
|6||setCity(String city)||City of the user. For example, city=New York|
|7||setZip(String zip)||Home zip code if the visitor is present in the U.S.; otherwise it indicates the postal code.|
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:
False - Indicates that the visitor is not COPPA-specific and can be served targeted 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.
List of IAB content categories for the overall site/application. See Table 6.1 Content Categories in the Open RTB 2.4 specifications document.
If the site/application falls under multiple IAB categories, you can send comma-delimited categories .
|10||setKeywords(String keyword)||Sets the keywords list as a comma-delimited String. For example, |
|11||setLocation(Location location)||Location object|
If set, it uses advertisement id otherwise it uses android id for targeting.
Based on the given hashing type, UDID value hashed and sent to the ad server.
This is an optional Wrapper version Id of the publisher. If this is not specified, live version of the above profile is considered.
Exchange specific App Id
Sets the region code using ISO-3166-2; 2-letter state code if USA.
|17||setSummaryDisabled(boolean state)||Set to True if summary in response should be disabled. By default it is set to False so summary is fetched in the PMBid|
Table 4: PMBannerImpression APIs/Setters
|1||setAdSizes(List<PMAdSize> adSizes)||Sets the valid ad sizes|
|2||setInterstitial(boolean interstitial)||Set True if requesting for Interstitial ad. By default it is set to false.|
|3||addCustomParam(String key, String value)||Adds custom key-value parameters in Ad request. This method can be called multiple times with|
same key and different values.
It is sent internally as, key1=val11,val12...|key2=val21,val22....
|4||setPMZoneId(String pmZoneId)||Set the zone id. This parameter is used to pass a zone ID for reporting.|
Sets the fold placement of the ad to be served. Possible values are:
|6||setSupportedAPIs(API... apis)||List of supported API frameworks for this impression. If an API is not explicitly listed, it is assumed not to be supported. Possible values are: VPAID1, VPAID2, MRAID1, ORMMA, and MRAID2.|
Table 5: PMBid APIs
|1||getTargetingInfo()||Returns targeting information, that needs to be sent to ad server|
|2||getTargetingInfoWithPricePrecision()||Returns targeting information, that needs to be sent to ad server with specified price precision|
|3||getImpressionId()||Returns Impression Id. Also used as a bid id|
|4||getPrice()||Returns price/bid value|
|5||getCreative()||Returns ad creative|
|6||getDealId()||Returns deal Id. Used for PMP deals|
|7||getSummary()||Returns bid summary for debugging purpose|
|8||getnURL()||Returns win notice URL called by the exchange if the bid wins|
|9||getWidth()||Returns horizontal width of bid creative|
|10||getHeight()||Returns vertical height of bid creative|
Inventory mapping for demand sources/header bidding partners configured in OpenWrap must be completed in PubMatic Wrapper UI. This process creates a wrapper profile where publishers can map Ad Server slots to partner specific ad units; for example, PubMatic ad tag, AppNexus placement ID, and so on.
Ad Server Setup (DFP)
In addition to in-app code integration, OpenWrap also requires a set of DFP ad server line items with small price increments. The PubMatic Operations team creates these line items using an internal tool.
Publishers must provide trafficker level access, to the email id provided by the PubMatic operations team, to create these line items. Publishers decide the price granularity for the line items and informs the PubMatic operations team. The PubMatic Operations team provide an Excel file containing the specification details upon request.
Manual Creation of Ad Server Line Items
For publishers who prefer to create their own ad server line items, this section explains how to set up the line items. OpenWrap passes bids to the ad server using key-value pairs added to the ad server tags dynamically, as explained in the sections above.
Step 1: Create a new order in DFP for a OpenWrap In-App API with PubMatic as the advertiser and add the relevant details.
Step 2: Set the price and priority of the line items.
Step 3: Set targeting on the
pwtbst value as 1. DFP uses this for reporting purposes. Also set targeting on
pwtecp which would be a winning bid from OpenWrap. You can also set targeting on
pwtdid (depending on custom key-value targeting in DFP). For more information, see Best Practices for Creating Line Items in the Ad Server .
Step 4: Add the OpenWrap In-App API creative provided by PubMatic to the line item you created.
Before setting traffic live, PubMatic’s Solutions Engineering team will assist the publisher’s technical and ad operations teams to conduct pre-launch verification. Once verifications are complete the app is ready to go live. 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 OpenWrap In-App at a granular level, you can:
- Create multiple line items in the ad server for each ad unit/ad size/CPM range/geo.
- Use pwtecp as the targeting attribute.
pwtbstas a targeting attribute. The value for this key must be 1 for all OpenWrap line items. This is used for reporting all wrapper line items in DFP and this key value is set in the Ad Server request by default by the SDK.
- Place the line items at different priorities based on their pricing and relevance.
While creating line items at multiple price points, we recommend you create line items with more granular pricing where the bid density is high.
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.
30 line items between $0-$3 with rate increment of $0.1
- LineItem 1 (covers $0-$0.09) Targeting: pwtecp=0.01*,pwtecp=0.02*....,pwtecp=0.09*, rate=$0.05
- LineItem 2 (covers $0.10-$0.19) Targeting: pwtecp=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: pwtecp=3.0*,pwtecp=3.1*,pwtecp=3.2*, rate=$3.15
- LineItem 32 (covers $3.30-$3.59) Targeting: pwtecp=3.3*,pwtecp=3.4*,pwtecp=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: pwtecp=9.*, rate=$9.5
- LineItem 47 (covers $10.0-$10.99) Targeting: pwtecp=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: pwtecp=20*,pwtecp=21*,pwtecp=22*...... pwtecp=50*) rate= $21