{"_id":"5a571716caec3a00286fcbcf","project":"5429beef1163360800ed31fa","version":{"_id":"5429beef1163360800ed31fd","__v":22,"project":"5429beef1163360800ed31fa","createdAt":"2014-09-29T20:19:59.904Z","releaseDate":"2014-09-29T20:19:59.904Z","categories":["5429beef1163360800ed31fe","55e74e1f5d36b32b002563fa","55e7500a73169617001f2e86","55e76b8196131b2f00bf4b72","55e89569cdbb8a350096df9c","55f8935eb089b71700a8364e","55f8a67d3bb4bb0d0022d093","55f9dbefc7ef770d00d9bf6d","5601c21a22ecf60d002b27b3","5601c21ff12aee0d001bb06e","5601c2256c7b610d00280db5","5601c22c22ecf60d002b27b4","5603738d0c78b00d0039af47","5626f70bfcbbc621004ebf52","566f7a1ae144ab0d00e9732f","566f85ca7820960d00c3b93d","56708ce43a32d20d00c45cbf","56708d436995210d003aad8e","5736471abe10a9200030732c","57a82c7aff9bd30e00a6f1c1","591b8500e3992319007190f4","5a3718305c66a60012d960ba"],"is_deprecated":false,"is_hidden":false,"is_beta":false,"is_stable":true,"codename":"","version_clean":"1.0.0","version":"1.0"},"category":{"_id":"55f9dbefc7ef770d00d9bf6d","version":"5429beef1163360800ed31fd","__v":6,"pages":["55f9eec4c7ef770d00d9bf83","55f9fb8daba81f0d00a11566","5601ca6870694e0d00e3c66f","5601cb9b96e0f70d0044b0fd","56157d7af2d81d0d006c895f","5671d738c17bf90d00b95822"],"project":"5429beef1163360800ed31fa","sync":{"url":"","isSync":false},"reference":true,"createdAt":"2015-09-16T21:15:27.664Z","from_sync":false,"order":4,"slug":"publisher-ui-setup","title":"Trafficking and Inventory"},"user":"569d8ad30306a10d00ce9a1f","__v":0,"parentDoc":null,"updates":[],"next":{"pages":[],"description":""},"createdAt":"2018-01-11T07:49:42.834Z","link_external":false,"link_url":"","githubsync":"","sync_unique":"","hidden":false,"api":{"results":{"codes":[]},"settings":"","auth":"required","params":[],"url":""},"isReference":true,"order":33,"body":"In few occasions advertisers mandate publishers to prevent their campaigns from being served on the same page in a single session along with the campaigns of their competitors. For example, a soft drink brand advertiser might request that you not serve their line items together with other soft drink brand advertiser(s). \n\nYou can prevent the campaigns of competitors from serving together by applying proper **negative key value pair targeting** to the campaigns. Requirement here is that, on the client side the publisher should make sure the placement ad requests are sent serially  (one after the other) so the ad server can filter out competitive campaigns from being returned for the same page.\n\nLets take an example of **Coca Cola** and **Pepsi** as the competing brands and both of them do not want their campaigns to be served on the same page together and both are targeting the same set of placements lets say **Header Placement** and **Right Rail Placement**. Below are the steps to setup this example, \n[block:api-header]\n{\n  \"title\": \"Step 1 : Campaigns setup\"\n}\n[/block]\n  * Create both campaigns and assign the appropriate brand name for each \n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/f53c090-Screen_Shot_2018-01-09_at_12.36.50_PM.png\",\n        \"Screen Shot 2018-01-09 at 12.36.50 PM.png\",\n        824,\n        478,\n        \"#ea0d0e\"\n      ],\n      \"caption\": \"Coca Cola Brand Campaign\"\n    }\n  ]\n}\n[/block]\n\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/11ba1f6-Screen_Shot_2018-01-09_at_12.47.09_PM.png\",\n        \"Screen Shot 2018-01-09 at 12.47.09 PM.png\",\n        797,\n        455,\n        \"#1e73ad\"\n      ],\n      \"caption\": \"Pepsi Brand Campaign\"\n    }\n  ]\n}\n[/block]\n* Target both the campaigns to the same placements for testing purpose, but in reality you need not particularly target to the same exact set of placements. Many times there will be an overlap of a sublet of placements that both the campaigns are targeted to where you would expect the competitive brand exclusion to apply. \n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/fd6beb8-Screen_Shot_2018-01-09_at_12.46.24_PM.png\",\n        \"Screen Shot 2018-01-09 at 12.46.24 PM.png\",\n        798,\n        462,\n        \"#1884c4\"\n      ],\n      \"caption\": \"Placement targeting\"\n    }\n  ]\n}\n[/block]\n* Create a **Dynamic key** under key-value pairs management tab [here](https://console.getpolymorph.com/placements/#/key-values) and give an appropriate key name that holds the brand(s) that your campaign does not want to serve along on the same page/session.\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/afc4be3-Screen_Shot_2018-01-11_at_12.21.32_PM.png\",\n        \"Screen Shot 2018-01-11 at 12.21.32 PM.png\",\n        708,\n        312,\n        \"#e5e6e6\"\n      ]\n    }\n  ]\n}\n[/block]\n* Apply negative targeting to campaigns against the competitive brands to be excluded in the same session / page.\n\nBelow is an example where the **Coca Cola** campaign is setting a negative targeting (is-not) against the brand **Pepsi**, which means when an ad request for a certain placement reaches the Ad server, then \"Coca Cola\" campaign will not be eligible to be served for that request if the web page already has another placement which has received a \"Pepsi\" campaign (Brands already served on the page will be passed in the ad request). So in order to keep the competitive brand exclusion intact, Ad server will skip the \"Coca Cola\" campaign and look for any other campaign which has no conflict with the brand \"Pepsi\".\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/451681f-Screen_Shot_2018-01-11_at_12.26.30_PM.png\",\n        \"Screen Shot 2018-01-11 at 12.26.30 PM.png\",\n        970,\n        437,\n        \"#f7f7f7\"\n      ]\n    }\n  ]\n}\n[/block]\nSimilarly if \"Pepsi\" does not want to share the space with \"Cola Cola\" on the same page, then set the appropriate negative targeting under pepsi campaign as shown below\n[block:image]\n{\n  \"images\": [\n    {\n      \"image\": [\n        \"https://files.readme.io/c3c265b-Screen_Shot_2018-01-11_at_12.39.10_PM.png\",\n        \"Screen Shot 2018-01-11 at 12.39.10 PM.png\",\n        969,\n        423,\n        \"#f7f7f7\"\n      ]\n    }\n  ]\n}\n[/block]\n\n[block:api-header]\n{\n  \"title\": \"Step 2 : Client side Integration using JS SDK\"\n}\n[/block]\n* Render JS V2 documentation can be found [here](https://dev.getpolymorph.com/docs/render-js-v2-integration) \n* Requirement : Ad requests should be made serially (one after the other) for the **Competitive Brand Exclusion** to function as expected.\n\nSample Render JS code snippet that makes Ad calls serially for all the placements on the page\n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"<script> \\n  var adsnativetag = adsnativetag || {};\\n  adsnativetag.cmdQ = adsnativetag.cmdQ || [];\\n</script>\\n<script async='async' type='text/javascript' src='//static.adsnative.com/static/js/render.v2.js'></script>\\n<script type=\\\"text/javascript\\\">\\n  // - Store all the brands related to the campaigns that are served on the page\\n  brandsOnThePage = [];\\n  // - List all the placements that you want to serially create/render on the page\\n  // - Recommended to list based on the position on the page from top to bottom\\n  placementIds = ['PLACEMENT_ID_1', 'PLACEMENT_ID_2', 'PLACEMENT_ID_3'];\\n  // - List of the ad unit instances defined for each of the placement ids\\n  adUnits = [];\\n  curPlacementIndex = -1;\\n\\n  adsnativetag.cmdQ.push(function() {\\n    function defineAndFetchAdUnit() {\\n      curPlacementIndex++;\\n      if(placementIds.length <= curPlacementIndex) return;\\n\\n      adUnit = adsnativetag.defineAdUnit({\\n        apiKey: placementIds[curPlacementIndex],\\n        keyValues: {\\n          // Pass the brands already on the page for competitive exclusion\\n          brands_on_the_page: brandsOnThePage \\n        },\\n        callbackOnAdResponse: adCallback\\n      });\\n      adUnits.push(adUnit);\\n\\n      adUnit.fetchAd(function(status, adObject) {\\n        if(status) {\\n          console.log('AD returned');\\n        }\\n      });\\n    }\\n\\n    function adCallback(status, adObject) {\\n      if(status) {\\n        console.log(adObject.promotedBy + ' campaign returned');\\n        if(adObject.promotedBy) {\\n\\n          // Store the brand of the current campaign returned by Ad server in the list\\n          brandsOnThePage.push(adObject.promotedBy);\\n\\n          // Define and Fetch next Ad Unit for serial flow\\n          defineAndFetchAdUnit();\\n        }\\n      }\\n    }\\n\\n    // Init by Defining and fetching first Ad Unit / Placement instance\\n    defineAndFetchAdUnit();\\n  });\\n</script>\",\n      \"language\": \"html\"\n    }\n  ]\n}\n[/block]\nRendering the Ad units will be unchanged and can be invoked in any order, use the standard displayAdUnit function to render each placement in the appropriate location on the page. \n[block:code]\n{\n  \"codes\": [\n    {\n      \"code\": \"  <body>\\n  \\n    .....\\n      \\n    <div id='div-an-ad-1'>\\n        <script type='text/javascript'>\\n            univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[0], 'div-an-ad-1'); });\\n        </script>\\n    </div>\\n    \\n   ... HTML...\\n   \\n    <div id='div-an-ad-2'>\\n        <script type='text/javascript'>\\n            univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[1], 'div-an-ad-2'); });\\n        </script>\\n    </div>\\n    \\n   ... HTML...\\n   \\n    <div id='div-an-ad-3'>\\n        <script type='text/javascript'>\\n            univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[1], 'div-an-ad-3'); });\\n        </script>\\n    </div>\\n\\n    .....\\n\\n  </body>\",\n      \"language\": \"html\"\n    }\n  ]\n}\n[/block]\n\n[block:api-header]\n{\n  \"title\": \"Step 3 : Result & Testing\"\n}\n[/block]\n* When the page is loaded, **PLACEMENT_ID_1** Adunit will be invoked first and the **brandsOnThePage** list will be empty since there are no ads rendered on the page yet. \n* Lets say Adserver chooses **Pepsi** campaign and returns to the client, now **Pepsi** ad loads in **PLACEMENT_ID_1** Adunit and **brandsOnThePage=[\"Pepsi\"]**\n* Next in the series the  **PLACEMENT_ID_2** Adunit will be invoked and **brandsOnThePage** will carry **Pepsi** brand name, now the ad server will skip **Coca Cola** campaign because of the negative targeting rule against the **Pepsi** brand name. So any other campaign will be returned to the client which has no conflict with **Pepsi**. \n* Same decisioning applies if **Coca Cola** was served for **PLACEMENT_ID_1**, then **Pepsi** will not be served for  **PLACEMENT_ID_2**.","excerpt":"","slug":"how-to-setup-competitive-brand-exclusion-on-polymorph","type":"basic","title":"Competitive Brand Exclusion on Polymorph"}

Competitive Brand Exclusion on Polymorph


In few occasions advertisers mandate publishers to prevent their campaigns from being served on the same page in a single session along with the campaigns of their competitors. For example, a soft drink brand advertiser might request that you not serve their line items together with other soft drink brand advertiser(s). You can prevent the campaigns of competitors from serving together by applying proper **negative key value pair targeting** to the campaigns. Requirement here is that, on the client side the publisher should make sure the placement ad requests are sent serially (one after the other) so the ad server can filter out competitive campaigns from being returned for the same page. Lets take an example of **Coca Cola** and **Pepsi** as the competing brands and both of them do not want their campaigns to be served on the same page together and both are targeting the same set of placements lets say **Header Placement** and **Right Rail Placement**. Below are the steps to setup this example, [block:api-header] { "title": "Step 1 : Campaigns setup" } [/block] * Create both campaigns and assign the appropriate brand name for each [block:image] { "images": [ { "image": [ "https://files.readme.io/f53c090-Screen_Shot_2018-01-09_at_12.36.50_PM.png", "Screen Shot 2018-01-09 at 12.36.50 PM.png", 824, 478, "#ea0d0e" ], "caption": "Coca Cola Brand Campaign" } ] } [/block] [block:image] { "images": [ { "image": [ "https://files.readme.io/11ba1f6-Screen_Shot_2018-01-09_at_12.47.09_PM.png", "Screen Shot 2018-01-09 at 12.47.09 PM.png", 797, 455, "#1e73ad" ], "caption": "Pepsi Brand Campaign" } ] } [/block] * Target both the campaigns to the same placements for testing purpose, but in reality you need not particularly target to the same exact set of placements. Many times there will be an overlap of a sublet of placements that both the campaigns are targeted to where you would expect the competitive brand exclusion to apply. [block:image] { "images": [ { "image": [ "https://files.readme.io/fd6beb8-Screen_Shot_2018-01-09_at_12.46.24_PM.png", "Screen Shot 2018-01-09 at 12.46.24 PM.png", 798, 462, "#1884c4" ], "caption": "Placement targeting" } ] } [/block] * Create a **Dynamic key** under key-value pairs management tab [here](https://console.getpolymorph.com/placements/#/key-values) and give an appropriate key name that holds the brand(s) that your campaign does not want to serve along on the same page/session. [block:image] { "images": [ { "image": [ "https://files.readme.io/afc4be3-Screen_Shot_2018-01-11_at_12.21.32_PM.png", "Screen Shot 2018-01-11 at 12.21.32 PM.png", 708, 312, "#e5e6e6" ] } ] } [/block] * Apply negative targeting to campaigns against the competitive brands to be excluded in the same session / page. Below is an example where the **Coca Cola** campaign is setting a negative targeting (is-not) against the brand **Pepsi**, which means when an ad request for a certain placement reaches the Ad server, then "Coca Cola" campaign will not be eligible to be served for that request if the web page already has another placement which has received a "Pepsi" campaign (Brands already served on the page will be passed in the ad request). So in order to keep the competitive brand exclusion intact, Ad server will skip the "Coca Cola" campaign and look for any other campaign which has no conflict with the brand "Pepsi". [block:image] { "images": [ { "image": [ "https://files.readme.io/451681f-Screen_Shot_2018-01-11_at_12.26.30_PM.png", "Screen Shot 2018-01-11 at 12.26.30 PM.png", 970, 437, "#f7f7f7" ] } ] } [/block] Similarly if "Pepsi" does not want to share the space with "Cola Cola" on the same page, then set the appropriate negative targeting under pepsi campaign as shown below [block:image] { "images": [ { "image": [ "https://files.readme.io/c3c265b-Screen_Shot_2018-01-11_at_12.39.10_PM.png", "Screen Shot 2018-01-11 at 12.39.10 PM.png", 969, 423, "#f7f7f7" ] } ] } [/block] [block:api-header] { "title": "Step 2 : Client side Integration using JS SDK" } [/block] * Render JS V2 documentation can be found [here](https://dev.getpolymorph.com/docs/render-js-v2-integration) * Requirement : Ad requests should be made serially (one after the other) for the **Competitive Brand Exclusion** to function as expected. Sample Render JS code snippet that makes Ad calls serially for all the placements on the page [block:code] { "codes": [ { "code": "<script> \n var adsnativetag = adsnativetag || {};\n adsnativetag.cmdQ = adsnativetag.cmdQ || [];\n</script>\n<script async='async' type='text/javascript' src='//static.adsnative.com/static/js/render.v2.js'></script>\n<script type=\"text/javascript\">\n // - Store all the brands related to the campaigns that are served on the page\n brandsOnThePage = [];\n // - List all the placements that you want to serially create/render on the page\n // - Recommended to list based on the position on the page from top to bottom\n placementIds = ['PLACEMENT_ID_1', 'PLACEMENT_ID_2', 'PLACEMENT_ID_3'];\n // - List of the ad unit instances defined for each of the placement ids\n adUnits = [];\n curPlacementIndex = -1;\n\n adsnativetag.cmdQ.push(function() {\n function defineAndFetchAdUnit() {\n curPlacementIndex++;\n if(placementIds.length <= curPlacementIndex) return;\n\n adUnit = adsnativetag.defineAdUnit({\n apiKey: placementIds[curPlacementIndex],\n keyValues: {\n // Pass the brands already on the page for competitive exclusion\n brands_on_the_page: brandsOnThePage \n },\n callbackOnAdResponse: adCallback\n });\n adUnits.push(adUnit);\n\n adUnit.fetchAd(function(status, adObject) {\n if(status) {\n console.log('AD returned');\n }\n });\n }\n\n function adCallback(status, adObject) {\n if(status) {\n console.log(adObject.promotedBy + ' campaign returned');\n if(adObject.promotedBy) {\n\n // Store the brand of the current campaign returned by Ad server in the list\n brandsOnThePage.push(adObject.promotedBy);\n\n // Define and Fetch next Ad Unit for serial flow\n defineAndFetchAdUnit();\n }\n }\n }\n\n // Init by Defining and fetching first Ad Unit / Placement instance\n defineAndFetchAdUnit();\n });\n</script>", "language": "html" } ] } [/block] Rendering the Ad units will be unchanged and can be invoked in any order, use the standard displayAdUnit function to render each placement in the appropriate location on the page. [block:code] { "codes": [ { "code": " <body>\n \n .....\n \n <div id='div-an-ad-1'>\n <script type='text/javascript'>\n univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[0], 'div-an-ad-1'); });\n </script>\n </div>\n \n ... HTML...\n \n <div id='div-an-ad-2'>\n <script type='text/javascript'>\n univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[1], 'div-an-ad-2'); });\n </script>\n </div>\n \n ... HTML...\n \n <div id='div-an-ad-3'>\n <script type='text/javascript'>\n univadistag.cmdQ.push(function() { var display_status = univadistag.displayAdUnit(adUnits[1], 'div-an-ad-3'); });\n </script>\n </div>\n\n .....\n\n </body>", "language": "html" } ] } [/block] [block:api-header] { "title": "Step 3 : Result & Testing" } [/block] * When the page is loaded, **PLACEMENT_ID_1** Adunit will be invoked first and the **brandsOnThePage** list will be empty since there are no ads rendered on the page yet. * Lets say Adserver chooses **Pepsi** campaign and returns to the client, now **Pepsi** ad loads in **PLACEMENT_ID_1** Adunit and **brandsOnThePage=["Pepsi"]** * Next in the series the **PLACEMENT_ID_2** Adunit will be invoked and **brandsOnThePage** will carry **Pepsi** brand name, now the ad server will skip **Coca Cola** campaign because of the negative targeting rule against the **Pepsi** brand name. So any other campaign will be returned to the client which has no conflict with **Pepsi**. * Same decisioning applies if **Coca Cola** was served for **PLACEMENT_ID_1**, then **Pepsi** will not be served for **PLACEMENT_ID_2**.