From cb1c1f6f9ea6f3ccb6c1b3ddcae996118b28dbdc Mon Sep 17 00:00:00 2001 From: Demetrio Girardi Date: Fri, 29 Sep 2023 11:13:38 -0700 Subject: [PATCH 01/12] JS: document new `eventHistoryTTL` and `minBidCacheTTL` settings (#4884) --- dev-docs/publisher-api-reference/setConfig.md | 29 +++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/dev-docs/publisher-api-reference/setConfig.md b/dev-docs/publisher-api-reference/setConfig.md index e29a3f50c3..18cd3d5a5b 100644 --- a/dev-docs/publisher-api-reference/setConfig.md +++ b/dev-docs/publisher-api-reference/setConfig.md @@ -24,6 +24,8 @@ Core config: * [Turn on send all bids mode](#setConfig-Send-All-Bids) * [Configure send bids control](#setConfig-Send-Bids-Control) * [Bid cache](#setConfig-Use-Bid-Cache) +* [Minimum bid cache TTL](#setConfig-minBidCacheTTL) +* [Event history TTL](#setConfig-eventHistoryTTL) * [Set the order in which bidders are called](#setConfig-Bidder-Order) * [Set the page URL](#setConfig-Page-URL) * [Set price granularity](#setConfig-Price-Granularity) @@ -279,6 +281,33 @@ pbjs.setConfig({ }); ``` +#### Minimum bid cache TTL + + + +By default, Prebid keeps every bid it receives stored in memory until the user leaves the page. This can cause high memory usage on long-running single-page apps; you can configure Prebid to drop stale bids from memory with `minBidCacheTTL`: + +```javascript +pbjs.setConfig({ + minBidCacheTTL: 60 // minimum time (in seconds) that bids should be kept in cache +}) +``` + +When set, bids are only kept in memory for the duration of their TTL or the value of `minBidCacheTTL`, whichever is greater. Setting `minBidCacheTTL: 0` causes bids to be dropped as soon as they expire. + +#### Event history TTL + + + +By default, Prebid keeps in memory a log of every event since the initial page load, and makes it available to analytics adapters and [getEvents()](/dev-docs/publisher-api-reference/getEvents.html). +This can cause high memory usage on long-running single-page apps; you can set a limit on how long events are preserved with `eventHistoryTTL`: + +```javascript +pbjs.setConfig({ + eventHistoryTTL: 60 // maximum time (in seconds) that events should be kept in memory +}) +``` + #### Bidder Order Set the order in which bidders are called: From 1a1704c97e90c59bb66071268d9500f5e0389b15 Mon Sep 17 00:00:00 2001 From: AcuityAdsIntegrations <72594990+AcuityAdsIntegrations@users.noreply.github.com> Date: Sat, 30 Sep 2023 20:43:18 +0300 Subject: [PATCH 02/12] AcuityAds Bid Adapter: add gpp support (#4896) * add prebid.js adapter * updates * updates * update Prebid Server documentation * add gpp --- dev-docs/bidders/acuityads.md | 1 + 1 file changed, 1 insertion(+) diff --git a/dev-docs/bidders/acuityads.md b/dev-docs/bidders/acuityads.md index aaa085ad91..fe72496b4c 100644 --- a/dev-docs/bidders/acuityads.md +++ b/dev-docs/bidders/acuityads.md @@ -9,6 +9,7 @@ tcfeu_supported: true usp_supported: true coppa_supported: true schain_supported: true +gpp_supported: true userId: britepoolId, criteo, id5Id, identityLink, liveIntentId, netId, parrableId, pubCommonId, unifiedId media_types: banner, video, native safeframes_ok: true From b722e2c9b3ae4629ca7071a7748158e7cfc51c58 Mon Sep 17 00:00:00 2001 From: mobfxoHB <74364234+mobfxoHB@users.noreply.github.com> Date: Sat, 30 Sep 2023 21:26:22 +0300 Subject: [PATCH 03/12] Mobfox Adapter: gpp support (#4887) * initial * Update mobfoxpb.md * Update mobfoxpb.md * Update mobfoxpb.md * Update mobfoxpb.md Add `key` parameter * updates for prebid v5 * update enable_download * update params * additional info * update info * lint * gpp support --------- Co-authored-by: Aiholkin Co-authored-by: kostiantyn.k --- dev-docs/bidders/mobfoxpb.md | 1 + 1 file changed, 1 insertion(+) diff --git a/dev-docs/bidders/mobfoxpb.md b/dev-docs/bidders/mobfoxpb.md index 513e894f7c..425901a4f7 100644 --- a/dev-docs/bidders/mobfoxpb.md +++ b/dev-docs/bidders/mobfoxpb.md @@ -10,6 +10,7 @@ tcfeu_supported: true pbjs: true pbs: true pbs_app_supported: true +gpp_supported: true gvl_id: 311 enable_download: true sidebarType: 1 From d4fce113d3f27e864004dabbbbbd8ea99b9ecbbd Mon Sep 17 00:00:00 2001 From: Saar Amrani Date: Sat, 30 Sep 2023 23:21:58 +0300 Subject: [PATCH 04/12] IlluminBidAdapter (#4813) * added gpp_supported: true * added illuminBidAdapter docs * Remove wrong gvlid --- dev-docs/bidders/illumin.md | 70 +++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 dev-docs/bidders/illumin.md diff --git a/dev-docs/bidders/illumin.md b/dev-docs/bidders/illumin.md new file mode 100644 index 0000000000..9d67a10c8a --- /dev/null +++ b/dev-docs/bidders/illumin.md @@ -0,0 +1,70 @@ +--- +layout: bidder +title: Illumin +description: Prebid Illumin Bidder Adaptor +biddercode: illumin +filename: illuminBidAdapter +userIds: britepoolId, criteo, id5Id, identityLink, liveIntentId, netId, parrableId, pubCommonId, unifiedId +tcfeu_supported: true +usp_supported: true +coppa_supported: false +schain_supported: true +gpp_supported: true +floors_supported: true +media_types: banner, video +prebid_member: false +safeframes_ok: false +deals_supported: false +pbs_app_supported: false +fpd_supported: false +ortb_blocking_supported: false +multiformat_supported: will-bid-on-one +pbjs: true +sidebarType: 1 +--- + +### Bid Params + +{: .table .table-bordered .table-striped } +| Name | Scope | Description | Example | Type | +|------------|----------|-------------------------------------------------------------------------------------------|------------------------------|----------| +| `cId` | required | The connection ID from Illumin. | `'562524b21b1c1f08117fc7f9'` | `string` | +| `pId` | required | The publisher ID from Illumin. | `'59ac17c192832d0011283fe3'` | `string` | +| `bidFloor` | optional | The minimum bid value desired. Illumin will not respond with bids lower than this value. | `0.90` | `float` | + +## Example + + ```javascript +var adUnits = [{ + code: 'banner-div', + mediaTypes: { + banner: { + sizes: [ + [300, 250], + [728, 90] + ] + } + }, + bids: [{ + bidder: 'illumin', + params: { + cId: '562524b21b1c1f08117fc7f9', // Required - PROVIDED DURING SETUP... + pId: '59ac17c192832d0011283fe3', // Required - PROVIDED DURING SETUP... + bidFloor: 1.23 // Optional + } + }] + } +]; + +// configure pbjs to enable user syncing +pbjs.setConfig({ + userSync: { + filterSettings: { + iframe: { + bidders: 'illumin', + filter: 'include' + } + } + } +}); +``` From 8bcced5d969ea9d0bff926601afd97bf7892b461 Mon Sep 17 00:00:00 2001 From: tkrishnaviant Date: Sat, 30 Sep 2023 13:36:02 -0700 Subject: [PATCH 05/12] Update viant.md - update schain support parameter (#4899) Update viant.md - update schain support parameter --- dev-docs/bidders/viant.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dev-docs/bidders/viant.md b/dev-docs/bidders/viant.md index f855264548..c7507b50a9 100644 --- a/dev-docs/bidders/viant.md +++ b/dev-docs/bidders/viant.md @@ -8,7 +8,7 @@ tcfeu_supported: false coppa_supported: true usp_supported: true gpp_supported: false -schain_supported: false +schain_supported: true userId: uid2, unifiedId pbjs: true prebid_member: true From 2a93c0ab4036ea076d284f1c098c6f3518f1cb2a Mon Sep 17 00:00:00 2001 From: Myhedin Zika <91465570+ZikaMyhedin@users.noreply.github.com> Date: Sat, 30 Sep 2023 22:53:15 +0200 Subject: [PATCH 06/12] Update integr8/md (#4890) --- dev-docs/bidders/integr8.md | 1 + 1 file changed, 1 insertion(+) diff --git a/dev-docs/bidders/integr8.md b/dev-docs/bidders/integr8.md index 251e031048..e812cd99dd 100644 --- a/dev-docs/bidders/integr8.md +++ b/dev-docs/bidders/integr8.md @@ -15,4 +15,5 @@ sidebarType: 1 |---------------|----------|------------------------------------------------------------------------|--------------------|-----------| | `propertyId` | required |Property id | `"12345"` | `string` | | `placementId` | required |Placement id | `"54321"` | `string` | +| `deliveryUrl` | optional |Custom endpoint url for the bid request | `"https://central.sea.integr8.digital/bid"` | `string` | | `data` | optional |Catalog data (contents) and/or inventory data (custom key/value pairs) | `{catalogs: [{ catalogId: "699229", items: ["193", "4", "1"] }], inventory: { category: ["tech"], query: ["iphone 12"] }}` | `object` | From 2a81544df0e4f7c04f836dfdb161ec4f7e117d57 Mon Sep 17 00:00:00 2001 From: bretg Date: Sat, 30 Sep 2023 17:32:09 -0400 Subject: [PATCH 07/12] PBS-Java module: Added get CPU function (#4900) * PBS-Java module: Added get CPU function * linting fixes * more linting fixes * more more linting fixes --- prebid-server/developers/add-a-module-java.md | 37 +++++++++++++------ 1 file changed, 25 insertions(+), 12 deletions(-) diff --git a/prebid-server/developers/add-a-module-java.md b/prebid-server/developers/add-a-module-java.md index 874ec62319..c9f474e84c 100644 --- a/prebid-server/developers/add-a-module-java.md +++ b/prebid-server/developers/add-a-module-java.md @@ -8,7 +8,7 @@ title: Prebid Server | Developers | Adding a Java Module # Prebid Server - Adding a Java Module {: .no_toc} -* TOC +- TOC {:toc } ## Overview @@ -17,7 +17,7 @@ This document details how to make a module for PBS-Java. You will want to be familiar with the following background information: -- the [module overview](/prebid-server/developers/add-a-module.html) +- the [module overview](/prebid-server/developers/add-a-module.html) - the [PBS-Java Modularity Tech Spec](https://docs.google.com/document/d/1VP_pi7L5Iy3ikHMbtC2_rD5RZTVSc3OkTWKvtRS5x5Y/edit#heading=h.oklyk2bogkx4) ### Coding standards @@ -28,7 +28,7 @@ The module’s code style should correspond to the [PBS-Java project code style] The Prebid Server repository contains a maven submodule called `all-modules` located in the `extra/modules` folder. It includes all available PBS modules. So, in order to add a new module, fork the repository and create a folder with the desired name inside the modules folder with the following structure: -``` +```text +- prebid-server-java/ +- extra/ +- modules/ @@ -37,13 +37,13 @@ The Prebid Server repository contains a maven submodule called `all-modules` loc +- pom.xml <- POM of all included modules ``` -A benefit of open sourcing your module in this way is that it can use the parent `all-modules` as a maven dependency. It simplifies management of the PBS-Core and other commonly used dependencies and you will be confident that it works well with the current version of Prebid Server. +A benefit of open sourcing your module in this way is that it can use the parent `all-modules` as a maven dependency. It simplifies management of the PBS-Core and other commonly used dependencies and you will be confident that it works well with the current version of Prebid Server. ### Your module's build file Here's a partial example of your module-specific `pom.xml` file: -``` +```text @@ -60,6 +60,7 @@ Here's a partial example of your module-specific `pom.xml` file: ``` where: + - PREBID_SERVER_VERSION is the current version of Prebid Server. The release team will update this value for all modules with each release, but you need to set it to the version of PBS that you're developing with. - YOUR_MODULE_ARTIFACT_ID is the name of your module JAR file without version and extension. e.g. ortb2-blocking - YOUR_MODULE_TEXTUAL_NAME is unique within the space of all other modules. e.g. instead of naming a module "blocking", a better name would be "ortb2blocking". @@ -68,7 +69,7 @@ where: Add your module within `extra/modules/pom.xml` in the "modules" section: -``` +```text ... YOUR_MODULE_ARTIFACT_ID @@ -79,7 +80,7 @@ Add your module within `extra/modules/pom.xml` in the "modules" section: The structure of your module source code inside the modules directory must have a standard maven-compatible structure: -``` +```text +- src/ +- main/ +- java/ <- source code @@ -95,13 +96,15 @@ The structure of your module source code inside the modules directory must have ## Module Code The quick start is to take a look in two places: + - the [ortb2-blocking module](https://github.com/prebid/prebid-server-java/tree/master/extra/modules/ortb2-blocking) - the [module test cases](https://github.com/prebid/prebid-server-java/tree/master/src/test/java/org/prebid/server/it/hooks) ### Adding module documentation + It is required to add a "README.md" file to the root of your module folder. Recommended this file contains the description of what the implemented module does, links to external documentation and includes maintainer contact info (email, slack, etc). -The documentation must also live on the docs.prebid.org site. Please add a markdown file to https://github.com/prebid/prebid.github.io/tree/master/prebid-server/pbs-modules +The documentation must also live on the docs.prebid.org site. Please add a markdown file to ### Hook Interfaces @@ -124,6 +127,7 @@ These are the available hooks that can be implemented in a module: In a module it is not necessary to implement all mentioned interfaces but only one (or several) required by your functionality. Each hook interface internally extends org.prebid.server.hooks.v1.Hook basic interface with methods should be implemented: + - `code()` - returns module code. - `call(...)` - returns result of hook invocation. @@ -177,7 +181,7 @@ Each hook interface internally extends org.prebid.server.hooks.v1.Hook basic int ); ``` -More test implementations for each hook can be found in unit-tests at https://github.com/prebid/prebid-server-java/tree/master/src/test/java/org/prebid/server/it/hooks folder. +More test implementations for each hook can be found in unit-tests at folder. ### Applying results asynchronously @@ -191,6 +195,16 @@ Thus, for any kind of blocking operations it is recommended to use a Vert.x buil To see how to proceed with async operations, please see similar PBS-Core functionality, for example Currency Conversion Service implementation (class “org.prebid.server.currency.CurrencyConversionService”). +### Available Functions + +#### Getting the localhost CPU + +To support modules that need to obtain information about the local CPU environment (e.g. a traffic-shaping), the code can call this function: + +```java +cpuLoadAverageStats.getCpuLoadAverage(); // returns a float +``` + ### Configuration It's possible to define default module configuration which can be read by the module at PBS startup. Please see the [Configuration](https://docs.google.com/document/d/1VP_pi7L5Iy3ikHMbtC2_rD5RZTVSc3OkTWKvtRS5x5Y/edit#heading=h.mh3urph3k1mk) section of the technical specification. @@ -211,7 +225,7 @@ Analytics adapters can receive these tags in a parameter that's been added to th To get analytics tag you need to go into: -``` +```text AuctionEvent -> AuctionContext -> HookExecutionContext @@ -221,11 +235,10 @@ AuctionEvent -> analyticsTags ``` -The AnalyticsTags object has activities with collection of org.prebid.server.hooks.v1.analytics.Result objects inside. Each Result has the values() method which returns com.fasterxml.jackson.databind.node.ObjectNode. +The AnalyticsTags object has activities with collection of org.prebid.server.hooks.v1.analytics.Result objects inside. Each Result has the values() method which returns com.fasterxml.jackson.databind.node.ObjectNode. It depends on the particular module implementation how to parse their analytics tags, since the internal structure is custom and depends on the module. Therefore, analytics modules that want to report on specific behavior need to be coded to know about that module. See the ortb2blocking module for an example of what analytics tags may be available. - ## Further Reading - [PBS Module Overview](/prebid-server/developers/add-a-module.html) From 96fc2bf6482e3d1a975daa3b6b45c094f534fa13 Mon Sep 17 00:00:00 2001 From: Sam Ghitelman Date: Sun, 1 Oct 2023 04:54:36 -0400 Subject: [PATCH 08/12] Concert: Add supported userIds (#4904) * Updates documentation for concert gpp support (#2) * Concert: Add supported userIds --------- Co-authored-by: Brett Bloxom <38990705+BrettBlox@users.noreply.github.com> --- dev-docs/bidders/concert.md | 1 + 1 file changed, 1 insertion(+) diff --git a/dev-docs/bidders/concert.md b/dev-docs/bidders/concert.md index db2549c837..40f627720a 100644 --- a/dev-docs/bidders/concert.md +++ b/dev-docs/bidders/concert.md @@ -9,6 +9,7 @@ media_types: banner tcfeu_supported: false usp_supported: true gpp_supported: true +userIds: sharedId, unifiedId, uid2 sidebarType: 1 --- From ea7faacf131c8ddce44982b9e970db780a54c96d Mon Sep 17 00:00:00 2001 From: Muki Seiler Date: Sun, 1 Oct 2023 11:18:29 +0200 Subject: [PATCH 09/12] Replace remaining gpp_supported doc in bidder adaptor (#4905) --- dev-docs/bidder-adaptor.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dev-docs/bidder-adaptor.md b/dev-docs/bidder-adaptor.md index b2a6fb4549..c35dc49384 100644 --- a/dev-docs/bidder-adaptor.md +++ b/dev-docs/bidder-adaptor.md @@ -1282,7 +1282,7 @@ registerBidder(spec); * If you support one or more userId modules, add `userId: (list of supported vendors)`. No default value. * If you support video and/or native mediaTypes add `media_types: video, native`. Note that display is added by default. If you don't support display, add "no-display" as the first entry, e.g. `media_types: no-display, native`. No default value. * If you support the COPPA flag, add `coppa_supported: true`. Default is false. - * If you support the IAB's GPP consent string, add `gpp_supported: true`. Default is false. + * If you support the IAB's GPP consent string, add `gpp_sids` with a comma separated list of section names, e.g. `gpp_sids: tcfeu, tcfca, usnat, usstate_all, usp`. Default is None. * If you support the [supply chain](/dev-docs/modules/schain.html) feature, add `schain_supported: true`. Default is false. * If you support passing a demand chain on the response, add `dchain_supported: true`. Default is false. * If your bidder doesn't work well with safeframed creatives, add `safeframes_ok: false`. This will alert publishers to not use safeframed creatives when creating the ad server entries for your bidder. No default value. From 9c09caa278db3f216afc5ec8678ae5e3fc18f728 Mon Sep 17 00:00:00 2001 From: Muki Seiler Date: Sun, 1 Oct 2023 11:25:12 +0200 Subject: [PATCH 10/12] Replace load external js with include (#4906) --- _includes/dev-docs/loads-external-javascript.md | 2 ++ dev-docs/modules/a1MediaRtdProvider.md | 3 +-- dev-docs/modules/aaxBlockmeterRtdProvider.md | 3 +-- dev-docs/modules/arcspanRtdProvider.md | 3 +-- dev-docs/modules/geoedgeRtdProvider.md | 3 +-- dev-docs/modules/medianetRtdProvider.md | 3 +-- 6 files changed, 7 insertions(+), 10 deletions(-) create mode 100644 _includes/dev-docs/loads-external-javascript.md diff --git a/_includes/dev-docs/loads-external-javascript.md b/_includes/dev-docs/loads-external-javascript.md new file mode 100644 index 0000000000..a719625426 --- /dev/null +++ b/_includes/dev-docs/loads-external-javascript.md @@ -0,0 +1,2 @@ +{: .alert.alert-warning :} +Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. diff --git a/dev-docs/modules/a1MediaRtdProvider.md b/dev-docs/modules/a1MediaRtdProvider.md index 61ddc70a4a..d7bcfb070f 100644 --- a/dev-docs/modules/a1MediaRtdProvider.md +++ b/dev-docs/modules/a1MediaRtdProvider.md @@ -13,8 +13,7 @@ sidebarType : 1 # A1Media RTD Module -{: .alert.alert-warning :} -Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. +{% include dev-docs/loads-external-javascript.md %} The A1Media RTD module loads a script for obtaining A1Media user segments, providing the user segment data to bid-requests. diff --git a/dev-docs/modules/aaxBlockmeterRtdProvider.md b/dev-docs/modules/aaxBlockmeterRtdProvider.md index 8bac1a307e..0b3b3bdd29 100644 --- a/dev-docs/modules/aaxBlockmeterRtdProvider.md +++ b/dev-docs/modules/aaxBlockmeterRtdProvider.md @@ -24,8 +24,7 @@ The module enables publishers with an AAX relationship to measure traffic coming AAX can also help publishers monetize this traffic by allowing them to serve [acceptable ads](https://acceptableads.com/about/) to these adblock visitors and recover their lost revenue. [Reach out to us](https://www.aax.media/try-blockmeter/) to know more. -{: .alert.alert-warning :} -Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. +{% include dev-docs/loads-external-javascript.md %} ## Configuration diff --git a/dev-docs/modules/arcspanRtdProvider.md b/dev-docs/modules/arcspanRtdProvider.md index 115cb994a5..ce1aecb4f9 100644 --- a/dev-docs/modules/arcspanRtdProvider.md +++ b/dev-docs/modules/arcspanRtdProvider.md @@ -22,8 +22,7 @@ sidebarType : 1 ArcSpan is a real-time audience monetization platform focused on the needs of the world’s finest publishers and retailers. Unlock the true value of your first-party audience data while providing advertisers the targeting performance they need. -{: .alert.alert-warning :} -Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. +{% include dev-docs/loads-external-javascript.md %} ### Usage diff --git a/dev-docs/modules/geoedgeRtdProvider.md b/dev-docs/modules/geoedgeRtdProvider.md index 17c02deae4..6bae377267 100644 --- a/dev-docs/modules/geoedgeRtdProvider.md +++ b/dev-docs/modules/geoedgeRtdProvider.md @@ -23,8 +23,7 @@ sidebarType : 1 The Geoedge Realtime module lets publishers block bad ads such as automatic redirects, malware, offensive creatives and landing pages. To use this module, you'll need to work with [Geoedge](https://www.geoedge.com/publishers-real-time-protection/) to get an account and cutomer key. -{: .alert.alert-warning :} -Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. +{% include dev-docs/loads-external-javascript.md %} ## Integration diff --git a/dev-docs/modules/medianetRtdProvider.md b/dev-docs/modules/medianetRtdProvider.md index 1dca950a44..2576d8af7a 100644 --- a/dev-docs/modules/medianetRtdProvider.md +++ b/dev-docs/modules/medianetRtdProvider.md @@ -26,8 +26,7 @@ The module currently provisions Media.net's Intelligent Refresh configured by th Intelligent Refresh (IR) module lets publisher refresh their ad inventory without affecting page experience of visitors through configured criteria. The module optionally provides tracking of refresh inventory and appropriate targeting in GAM. Publisher configured criteria is fetched via an external JS payload. -{: .alert.alert-warning :} -Disclosure: This module loads external code that is not open source and has not been reviewed by Prebid.org. +{% include dev-docs/loads-external-javascript.md %} ## Configuration From 3a5c9af4a1d32566eb81663f1880c489d33eaae9 Mon Sep 17 00:00:00 2001 From: Yuriy Velichko Date: Sun, 1 Oct 2023 12:51:16 +0300 Subject: [PATCH 11/12] Prebid SDK - multiformat ad unit for original api (#4889) * mobile: add info about multiformat ad unit and the BidInfo class * mobile: Android - add info about multiformat ad unit and BidInfo class * mobile: description of NativeParameters * mobile: corrections for the android docs * mobile: fix build errors * mobile: fix build errors * mobile: fix build errors * mobile: fix build errors * mobile: fix build errors * mobile: fix build errors --- .../rendering/android-sdk-integration-pb.md | 89 ++- .../rendering/ios-sdk-integration-pb.md | 102 ++- ...ndroid-sdk-integration-gam-original-api.md | 299 +++++++++ .../ios-sdk-integration-gam-original-api.md | 632 ++++++++++++------ 4 files changed, 812 insertions(+), 310 deletions(-) diff --git a/prebid-mobile/modules/rendering/android-sdk-integration-pb.md b/prebid-mobile/modules/rendering/android-sdk-integration-pb.md index 9215c191c5..4c221aaee0 100644 --- a/prebid-mobile/modules/rendering/android-sdk-integration-pb.md +++ b/prebid-mobile/modules/rendering/android-sdk-integration-pb.md @@ -17,7 +17,7 @@ You can use Prebid SDK to monetize your app with a custom ad server or even with ## Transport API -The default ad server for Prebid's Mobile SDK is GAM. The SDK can be expanded to include support for 3rd party ad servers through the fetchDemand function. This function returns the Prebid Server bidder key/values (targeting keys), which can then be passed to the ad server of choice. +The default ad server for Prebid's Mobile SDK is GAM. The SDK can be expanded to include support for 3rd party ad servers through the fetchDemand function. This function returns the Prebid Server bidder key/values (targeting keys), which can then be passed to the ad server of choice. In this mode, the publisher will be responsible for the following actions: @@ -39,46 +39,43 @@ This approach is avaliable for the following ad formats: The basic integration steps for these ad units you can find at the page for integration using [Original API](/prebid-mobile/pbm-api/android/android-sdk-integration-gam-original-api.html). The diference is that you should use the `fetchDemand` function with following signature: ```kotlin -public void fetchDemand(@NonNull Object adObj, - @NonNull OnCompleteListener2 listener) { ... } - -public interface OnCompleteListener2 { - /** - * This method will be called when PrebidMobile finishes attaching keywords to unmodifiableMap. - * @param resultCode see {@link ResultCode} class definition for details - * @param unmodifiableMap a map of targeting Key/Value pairs - */ - @MainThread - void onComplete(ResultCode resultCode, - @Nullable Map unmodifiableMap); -} +public void fetchDemand(OnFetchDemandResult listener) { ... } + +public interface OnFetchDemandResult { + void onComplete(@NonNull BidInfo bidInfo); +} ``` Examples: -```kotlin -private fun loadRewardedVideo() { - adUnit?.fetchDemand { resultCode, unmodifiableMap -> - val keywords: Map = HashMap(unmodifiableMap) +``` kotlin +adUnit?.fetchDemand { result -> + if(result.getResultCode() == ResultCode.SUCCESS) { + val keywords = resultCode.targetingKeywords - adServerObject.loadRewardedVideo(ADUNITID_REWARDED, keywords) + makeAdRequest(keywords) } } ``` +The `BidInfo` provides the following properties: + +* `resultCode` - the object of type `ResultCode` describing the status of the bid request. +* `targetingKeywords` - the targeting keywords of the winning bid +* `exp` - the number of seconds that may elapse between the auction and the actual impression. In this case, it indicates the approximate TTL of the bid in the Prebid Cache. Note that the actual expiration time of the bid will be less than this number due to the network and operational overhead. The Prebid SDK doesn't make any adjustments to this value. +* `nativeAdCacheId` - the local cache ID of the winning bid. Applied only to the `native` ad format. + ## Rendering API -The integration and usage of the Rendering API is similar to any other Ad SDK. It sends the bid requests to the Prebid Server and renders the winning bid. +The integration and usage of the Rendering API is similar to any other Ad SDK. It sends the bid requests to the Prebid Server and renders the winning bid. ![Rendering with GAM as the Primary Ad Server](/assets/images/prebid-mobile/modules/rendering/Prebid-In-App-Bidding-Overview-Pure-Prebid.png) - ### Banner API Integration example: - -```kotlin +``` kotlin // 1. Create an Ad View bannerView = BannerView(requireContext(), configId, adSize) bannerView?.setBannerListener(this) @@ -90,8 +87,8 @@ viewContainer?.addView(bannerView) bannerView?.loadAd() ``` -{% capture warning_note %} -Pay attention that the `loadAd()` should be called on the main thread. +{% capture warning_note %} +Pay attention that the `loadAd()` should be called on the main thread. {% endcapture %} {% include /alerts/alert_warning.html content=warning_note %} @@ -100,23 +97,23 @@ Pay attention that the `loadAd()` should be called on the main thread. Initialize the `BannerAdView` with properties: -- `configId` - an ID of a [Stored Impression](/prebid-server/features/pbs-storedreqs.html) on the Prebid server -- `size` - the size of the ad unit which will be used in the bid request. +* `configId` - an ID of a [Stored Impression](/prebid-server/features/pbs-storedreqs.html) on the Prebid server +* `size` - the size of the ad unit which will be used in the bid request. #### Step 2: Load the Ad {:.no_toc} Call `loadAd()` and SDK will: -- make bid request to Prebid -- render the winning bid on display +* make bid request to Prebid +* render the winning bid on display #### Outstream Video {:.no_toc} For **Banner Video** you will also need to specify the `bannerView.videoPlacementType`: -```kotlin +``` kotlin bannerView.videoPlacementType = PlacementType.IN_BANNER // or any other available type ``` @@ -124,7 +121,7 @@ bannerView.videoPlacementType = PlacementType.IN_BANNER // or any other availabl Integration example: -```kotlin +``` kotlin // 1. Create an Interstitial Ad Unit interstitialAdUnit = InterstitialAdUnit(requireContext(), configId, minSizePercentage) interstitialAdUnit?.setInterstitialAdUnitListener(this) @@ -137,27 +134,27 @@ interstitialAdUnit?.loadAd() interstitialAdUnit?.show() ``` -{% capture warning_note %} -Pay attention that the `loadAd()` should be called on the main thread. +{% capture warning_note %} +Pay attention that the `loadAd()` should be called on the main thread. {% endcapture %} {% include /alerts/alert_warning.html content=warning_note %} The **default** ad format for interstitial is **DISPLAY**. In order to make a `multiformat bid request`, set the respective values into the `adUnitFormats` parameter. -``` +``` kotlin interstitialAdUnit = InterstitialAdUnit( - requireContext(), - configId, + requireContext(), + configId, EnumSet.of(AdUnitFormat.BANNER, AdUnitFormat.VIDEO)) ``` #### Step 1: Create an Ad Unit {:.no_toc} -Initialize the `InterstitialAdUnit ` with properties: +Initialize the `InterstitialAdUnit` with properties: -- `configId` - an ID of a [Stored Impression](/prebid-server/features/pbs-storedreqs.html) on the Prebid server -- `minSizePercentage` - specifies the minimum width and height percent an ad may occupy of a device’s real estate. +* `configId` - an ID of a [Stored Impression](/prebid-server/features/pbs-storedreqs.html) on the Prebid server +* `minSizePercentage` - specifies the minimum width and height percent an ad may occupy of a device’s real estate. You can also assign the listener for processing ad events. @@ -173,7 +170,7 @@ Call the `loadAd()` to make a bid request. Wait until the ad is loaded and present it to the user in any suitable time. -```kotlin +``` kotlin override fun onAdLoaded(interstitialAdUnit: InterstitialAdUnit) { //Ad is ready for display } @@ -183,11 +180,11 @@ override fun onAdLoaded(interstitialAdUnit: InterstitialAdUnit) { Integration example: -```kotlin +``` kotlin // 1. Create an Ad Unit rewardedAdUnit = RewardedAdUnit(requireContext(), configId) rewardedAdUnit?.setRewardedAdUnitListener(this) - + // 2. Execute the loadAd function rewardedAdUnit?.loadAd() @@ -197,8 +194,8 @@ rewardedAdUnit?.loadAd() rewardedAdUnit?.show() ``` -{% capture warning_note %} -Pay attention that the `loadAd()` should be called on the main thread. +{% capture warning_note %} +Pay attention that the `loadAd()` should be called on the main thread. {% endcapture %} {% include /alerts/alert_warning.html content=warning_note %} @@ -207,7 +204,7 @@ Pay attention that the `loadAd()` should be called on the main thread. Create the `RewardedAdUnit` object with parameters: -- `adUnitId` - an ID of Stored Impression on the Prebid server. +* `adUnitId` - an ID of Stored Impression on the Prebid server. #### Step 2: Load the Ad {:.no_toc} @@ -219,7 +216,7 @@ Call the `loadAd()` to make a bid request. Wait until the ad is loaded and present it to the user in any suitable time. -```kotlin +``` kotlin override fun onAdLoaded(rewardedAdUnit: RewardedAdUnit) { //Ad is ready for display } diff --git a/prebid-mobile/modules/rendering/ios-sdk-integration-pb.md b/prebid-mobile/modules/rendering/ios-sdk-integration-pb.md index 5282ec6b82..8fe5952a0f 100644 --- a/prebid-mobile/modules/rendering/ios-sdk-integration-pb.md +++ b/prebid-mobile/modules/rendering/ios-sdk-integration-pb.md @@ -17,17 +17,17 @@ You can use Prebid SDK to monetize your app with a custom ad server or even with ## Transport API -The default ad server for Prebid's Mobile SDK is GAM. The SDK can be expanded to include support for 3rd party ad servers through the fetchDemand function. This function returns the Prebid Server bidder key/values (targeting keys), which can then be passed to the ad server of choice. +The default ad server for Prebid's Mobile SDK is GAM. The SDK can be expanded to include support for 3rd party ad servers through the fetchDemand function. This function returns additional bid information like Prebid Server bidder key/values (targeting keys), which can then be passed to the ad server of choice. In this mode, the publisher will be responsible for the following actions: -* Call fetchDemand with extended targetingDict callback -* Retrieve targeting keys from extended fetchDemand function +* Call the `fetchDemand` method with specific callback +* Retrieve targeting keys from the `BidInfo` callback parameter * Convert targeting keys into the format for your ad server * Pass converted keys to your ad server * Render ad with Prebid Universal Creative or custom renderer -This approach is avaliable for the following ad formats: +This approach is available for the following ad formats: * Display Banner via `BannerAdUnit` * Video Banner and Instream Video via `VideoAdUnit` @@ -35,42 +35,37 @@ This approach is avaliable for the following ad formats: * Video Interstitial via `VideoInterstitialAdUnit` * Rewarded Video via `RewardedVideoAdUnit` * Native Styles via `NativeRequest` +* Multiformat ad unit via `PrebidAdUnit` The basic integration steps for these ad units you can find at the page for integration using [Original API](/prebid-mobile/pbm-api/ios/ios-sdk-integration-gam-original-api.html). The diference is that you should use the `fetchDemand` function with following signature: -```swift -dynamic public func fetchDemand( - completion: @escaping(_ result: ResultCode, - _ kvResultDict: [String : String]?) -> Void) +``` swift +public func fetchDemand(adObject: AnyObject, request: PrebidRequest, + completion: @escaping (BidInfo) -> Void) ``` Examples: -```swift -func loadBanner() { - - //adUnit is BannerAdUnit type - adUnit.fetchDemand { [weak self] (resultCode: ResultCode, targetingDict: [String : String]?) in - - self?.adServerRequest.customTargeting = targetingDict - self?.adServerBanner.load(self?.adServerRequest) - } -} +``` swift +adUnit.fetchDemand(adObject: gamRequest, request: prebidRequest) { [weak self] bidInfo in + guard let self = self else { return } -func loadRewardedVideo() { - let adUnit = RewardedVideoAdUnit(configId: "1001-1") - adUnit.fetchDemand { [weak self] (resultCode: ResultCode, targetingDict: [String : String]?) in - //Publisher should provide support for converting keys into format of 3rd party ad server and loading ads - let keywords = convertDictToAdServerKeywords(dict: targetingDict) - AdServerLoadAds.loadAd(withAdUnitID: "46d2ebb3ccd340b38580b5d3581c6434", keywords: keywords) - } + let keywords = convertDictToAdServerKeywords(dict: bidInfo.targetingKeywords) + AdServerLoadAds.loadAd(withAdUnitID: "46d2ebb3ccd340b38580b5d3581c6434", keywords: keywords) } ``` +The `BidInfo` provides the following properties: + +* `resultCode` - the object of type `ResultCode` describing the status of the bid request. +* `targetingKeywords` - the targeting keywords of the winning bid +* `exp` - the number of seconds that may elapse between the auction and the actual impression. In this case, it indicates the approximate TTL of the bid in the Prebid Cache. Note that the actual expiration time of the bid will be less than this number due to the network and operational overhead. The Prebid SDK doesn't make any adjustments to this value. +* `nativeAdCacheId` - the local cache ID of the winning bid. Applied only to the `native` ad format. + ## Rendering API -The Rendering API integration and usage are similar to any other Ad SDK. In this case, Prebid SDK sends the bid requests to the Prebid Server and renders the winning bid. +The Rendering API integration and usage are similar to any other Ad SDK. In this case, Prebid SDK sends the bid requests to the Prebid Server and renders the winning bid. ![In-App Bidding with Prebid](/assets/images/prebid-mobile/modules/rendering/Prebid-In-App-Bidding-Overview-Pure-Prebid.png) @@ -78,14 +73,14 @@ The Rendering API integration and usage are similar to any other Ad SDK. In this Integration example: -```swift +``` swift // 1. Create an Ad View let banner = BannerView(frame: CGRect(origin: .zero, size: adSize), configID: CONFIG_ID, adSize: adSize) - + banner.delegate = self - + // 2. Load an Ad banner.loadAd() ``` @@ -95,24 +90,24 @@ banner.loadAd() Initialize the `BannerAdView` with properties: -- `frame` - the frame rectangle for the view -- `configID` - an ID of the Stored Impression on the Prebid Server -- `size` - the size of the ad unit which will be used in the bid request. +* `frame` - the frame rectangle for the view +* `configID` - an ID of the Stored Impression on the Prebid Server +* `size` - the size of the ad unit which will be used in the bid request. #### Step 2: Load the Ad {:.no_toc} Call the method `loadAd()` which will: -- make a bid request to the Prebid Server. -- render the winning bid on display. +* make a bid request to the Prebid Server. +* render the winning bid on display. #### Outstream Video {:.no_toc} For **Banner Video** you also need to specify the ad format: -```swift +``` swift banner.adFormat = .video ``` @@ -120,13 +115,13 @@ banner.adFormat = .video Integration example: -```swift +``` swift // 1. Create an Interstitial Ad Unit interstitial = InterstitialRenderingAdUnit(configID: CONFIG_ID, minSizePercentage: CGSize(width: 30, height: 30)) - + interstitial.delegate = self - + // 2. Load an Ad interstitial.loadAd() @@ -141,14 +136,14 @@ if interstitial.isReady { The **default** ad format for interstitial is **.banner**. In order to make a `multiformat bid request`, set the respective values into the `adFormats` property. -```swift -// Make bid request for video ad +``` swift +// Make bid request for video ad adUnit?.adFormats = [.video] -// Make bid request for both video and banner ads +// Make bid request for both video and banner ads adUnit?.adFormats = [.video, .banner] -// Make bid request for banner ad (default behaviour) +// Make bid request for banner ad (default behaviour) adUnit?.adFormats = [.banner] ``` @@ -157,9 +152,9 @@ adUnit?.adFormats = [.banner] {:.no_toc} Initialize the Interstitial Ad Unit with properties: - -- `configID` - an ID of Stored Impression on the Prebid Server -- `minSizePercentage` - specifies the minimum width and height percent an ad may occupy of a device’s real estate. + +* `configID` - an ID of Stored Impression on the Prebid Server +* `minSizePercentage` - specifies the minimum width and height percent an ad may occupy of a device’s real estate. > **NOTE:** minSizePercentage - plays an important role in a bidding process for banner ads. If provided space is not enough demand partners won't respond with the bids. @@ -173,9 +168,9 @@ Call the method `loadAd()` which will make a bid request to Prebid server. Wait until the ad will be loaded and present it to the user in any suitable time. -```swift +``` swift // MARK: InterstitialRenderingAdUnitDelegate - + func interstitialDidReceiveAd(_ interstitial: InterstitialRenderingAdUnit) { // Now the ad is ready for display } @@ -185,11 +180,11 @@ func interstitialDidReceiveAd(_ interstitial: InterstitialRenderingAdUnit) { Integration example: -```swift +``` swift // 1. Create an Ad Unit rewardedAd = RewardedAdUnit(configID: CONFIG_ID) rewardedAd.delegate = self - + // 2. Load an Ad rewardedAd.loadAd() @@ -201,13 +196,12 @@ if rewardedAd.isReady { } ``` - #### Step 1: Create Rewarded Ad Unit {:.no_toc} Create the `RewardedAdUnit` object with parameter: -- `configID` - an ID of Stored Impression on the Prebid Server +* `configID` - an ID of Stored Impression on the Prebid Server #### Step 2: Load the Ad {:.no_toc} @@ -219,10 +213,10 @@ Call the `loadAd()` method which will make a bid request to Prebid server. Wait until the ad will be loaded and present it to the user in any suitable time. -```swift +``` swift // MARK: RewardedAdUnitDelegate - + func rewardedAdDidReceiveAd(_ rewardedAd: RewardedAdUnit) { // Now the ad is ready for display -} +} ``` diff --git a/prebid-mobile/pbm-api/android/android-sdk-integration-gam-original-api.md b/prebid-mobile/pbm-api/android/android-sdk-integration-gam-original-api.md index b8f2909ca4..3e7559b162 100755 --- a/prebid-mobile/pbm-api/android/android-sdk-integration-gam-original-api.md +++ b/prebid-mobile/pbm-api/android/android-sdk-integration-gam-original-api.md @@ -1120,6 +1120,305 @@ Without it the SDK won't be able to recognize the Prebid line item. Once the Prebid line item is recognized you should extract the ad from the winning bid and init the view properties with native assets data. +## Multiformat API + +Starting with version `2.1.5` Prebid SDK supports the fully multiformat ad unit. It allows to run bid requests with any combination of `banner`, `video`, and `native` formats. + +The following code demonstrates the integration of multiformat ad unit. + +``` kotlin +private fun createAd() { + // random() only for test cases, in production use only one config id + val configId = listOf(CONFIG_ID_BANNER, CONFIG_ID_VIDEO, CONFIG_ID_NATIVE).random() + + // Step 1: Create a PrebidAdUnit + prebidAdUnit = PrebidAdUnit(configId) + + // Step 2: Create PrebidRequest + val prebidRequest = PrebidRequest() + + // Step 3: Setup the parameters + prebidRequest.setBannerParameters(createBannerParameters()) + prebidRequest.setVideoParameters(createVideoParameters()) + prebidRequest.setNativeParameters(createNativeParameters()) + + // Step 4: Make a bid request + val gamRequest = AdManagerAdRequest.Builder().build() + prebidAdUnit?.fetchDemand(prebidRequest, gamRequest) { + // Step 5: Load an Ad + + loadGam(gamRequest) + } +} + +private fun createBannerParameters(): BannerParameters { + val parameters = BannerParameters() + parameters.api = listOf(Signals.Api.MRAID_3, Signals.Api.OMID_1) + + return parameters +} + +private fun createVideoParameters(): VideoParameters { + return VideoParameters(listOf("video/mp4")) +} + +private fun createNativeParameters(): NativeParameters { + val assets = mutableListOf() + + val title = NativeTitleAsset() + title.setLength(90) + title.isRequired = true + assets.add(title) + + val icon = NativeImageAsset(20, 20, 20, 20) + icon.imageType = NativeImageAsset.IMAGE_TYPE.ICON + icon.isRequired = true + assets.add(icon) + + val image = NativeImageAsset(200, 200, 200, 200) + image.imageType = NativeImageAsset.IMAGE_TYPE.MAIN + image.isRequired = true + assets.add(image) + + val data = NativeDataAsset() + data.len = 90 + data.dataType = NativeDataAsset.DATA_TYPE.SPONSORED + data.isRequired = true + assets.add(data) + + val body = NativeDataAsset() + body.isRequired = true + body.dataType = NativeDataAsset.DATA_TYPE.DESC + assets.add(body) + + val cta = NativeDataAsset() + cta.isRequired = true + cta.dataType = NativeDataAsset.DATA_TYPE.CTATEXT + assets.add(cta) + + val nativeParameters = NativeParameters(assets) + nativeParameters.addEventTracker( + NativeEventTracker( + NativeEventTracker.EVENT_TYPE.IMPRESSION, + arrayListOf(NativeEventTracker.EVENT_TRACKING_METHOD.IMAGE) + ) + ) + nativeParameters.setContextType(NativeAdUnit.CONTEXT_TYPE.SOCIAL_CENTRIC) + nativeParameters.setPlacementType(NativeAdUnit.PLACEMENTTYPE.CONTENT_FEED) + nativeParameters.setContextSubType(NativeAdUnit.CONTEXTSUBTYPE.GENERAL_SOCIAL) + + return nativeParameters +} +``` + +If you use Custom Native Ads follow the [guide](https://developers.google.com/ad-manager/mobile-ads-sdk/ios/native-banner) on how to implement processing of the ad response of the respective type. The following code snipet demonstrates how you can process the banner, video and in-banner native (Native Styles) ad resposnse: + +``` kotlin +private fun loadGam(gamRequest: AdManagerAdRequest) { + val onBannerLoaded = OnAdManagerAdViewLoadedListener { adView -> + showBannerAd(adView) + } + + val onNativeLoaded = OnNativeAdLoadedListener { nativeAd -> + showNativeAd(nativeAd, adWrapperView) + } + + val onPrebidNativeAdLoaded = OnCustomFormatAdLoadedListener { customNativeAd -> + showPrebidNativeAd(customNativeAd) + } + + // Prepare the lisners for multiformat Ad Response + val adLoader = AdLoader.Builder(this, AD_UNIT_ID) + .forAdManagerAdView(onBannerLoaded, AdSize.BANNER, AdSize.MEDIUM_RECTANGLE) + .forNativeAd(onNativeLoaded) + .forCustomFormatAd(CUSTOM_FORMAT_ID, onPrebidNativeAdLoaded, null) + .withAdListener(AdListenerWithToast(this)) + .withAdManagerAdViewOptions(AdManagerAdViewOptions.Builder().build()) + .build() + + adLoader.loadAd(gamRequest) +} +``` + +The methods managing the prebid and GAM ads: + +``` kotlin +private fun showBannerAd(adView: AdManagerAdView) { + adWrapperView.addView(adView) + AdViewUtils.findPrebidCreativeSize(adView, object : AdViewUtils.PbFindSizeListener { + override fun success(width: Int, height: Int) { + adView.setAdSizes(AdSize(width, height)) + } + + override fun failure(error: PbFindSizeError) {} + }) +} + +private fun showNativeAd(ad: NativeAd, wrapper: ViewGroup) { + val nativeContainer = View.inflate(wrapper.context, R.layout.layout_native, null) + + val icon = nativeContainer.findViewById(R.id.imgIcon) + val iconUrl = ad.icon?.uri?.toString() + if (iconUrl != null) { + ImageUtils.download(iconUrl, icon) + } + + val title = nativeContainer.findViewById(R.id.tvTitle) + title.text = ad.headline + + val image = nativeContainer.findViewById(R.id.imgImage) + val imageUrl = ad.images.getOrNull(0)?.uri?.toString() + if (imageUrl != null) { + ImageUtils.download(imageUrl, image) + } + + val description = nativeContainer.findViewById(R.id.tvDesc) + description.text = ad.body + + val cta = nativeContainer.findViewById