-
Notifications
You must be signed in to change notification settings - Fork 2.1k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add Geoedge RTD provider submodule (#5869)
* Add Geoedge RTD provider submodule * Add Geoedge RTD provider submodule accroding to RTD phase 3 * Add tests * Add docs * Add integration example * Add as child module of RTD for easier builds * Update RTD submodule interface See https://docs.prebid.org/dev-docs/add-rtd-submodule.html * Update tests * Update integration example remove unnecessary param * Update docs * Update RTD submodule provider * Remove getConfig * Get params from init * Use beforeInit * Update docs Extend and document the wap param * Update tests * Remove unused config module * Update integreation example Relevant opening and inline comments * Update Geoedge RTD submodule provider * Hardcode HTTPS scheme * Rename to "donePreload" for clarity * Use regex to replace macros instead of loop * Update tests Preload request scheme is now always HTTPS * Remove integration example HTML page As for @Fawke request at #5869 (comment) Co-authored-by: daniel manan <mmndaniel@gmail.com> Co-authored-by: bretg <bgorsline@gmail.com>
- Loading branch information
1 parent
015c48b
commit 1f24ee4
Showing
4 changed files
with
393 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,213 @@ | ||
/** | ||
* This module adds geoedge provider to the real time data module | ||
* The {@link module:modules/realTimeData} module is required | ||
* The module will fetch creative wrapper from geoedge server | ||
* The module will place geoedge RUM client on bid responses markup | ||
* @module modules/geoedgeProvider | ||
* @requires module:modules/realTimeData | ||
*/ | ||
|
||
/** | ||
* @typedef {Object} ModuleParams | ||
* @property {string} key | ||
* @property {?Object} bidders | ||
* @property {?boolean} wap | ||
* @property {?string} keyName | ||
*/ | ||
|
||
import { submodule } from '../src/hook.js'; | ||
import { ajax } from '../src/ajax.js'; | ||
import { generateUUID, insertElement, isEmpty, logError } from '../src/utils.js'; | ||
|
||
/** @type {string} */ | ||
const SUBMODULE_NAME = 'geoedge'; | ||
/** @type {string} */ | ||
export const WRAPPER_URL = 'https://wrappers.geoedge.be/wrapper.html'; | ||
/** @type {string} */ | ||
/* eslint-disable no-template-curly-in-string */ | ||
export const HTML_PLACEHOLDER = '${creative}'; | ||
/** @type {string} */ | ||
const PV_ID = generateUUID(); | ||
/** @type {string} */ | ||
const HOST_NAME = 'https://rumcdn.geoedge.be'; | ||
/** @type {string} */ | ||
const FILE_NAME = 'grumi.js'; | ||
/** @type {function} */ | ||
export let getClientUrl = (key) => `${HOST_NAME}/${key}/${FILE_NAME}`; | ||
/** @type {string} */ | ||
export let wrapper | ||
/** @type {boolean} */; | ||
let wrapperReady; | ||
/** @type {boolean} */; | ||
let preloaded; | ||
|
||
/** | ||
* fetches the creative wrapper | ||
* @param {function} sucess - success callback | ||
*/ | ||
export function fetchWrapper(success) { | ||
if (wrapperReady) { | ||
return success(wrapper); | ||
} | ||
ajax(WRAPPER_URL, success); | ||
} | ||
|
||
/** | ||
* sets the wrapper and calls preload client | ||
* @param {string} responseText | ||
*/ | ||
export function setWrapper(responseText) { | ||
wrapperReady = true; | ||
wrapper = responseText; | ||
} | ||
|
||
/** | ||
* preloads the client | ||
* @param {string} key | ||
*/ | ||
export function preloadClient(key) { | ||
let link = document.createElement('link'); | ||
link.rel = 'preload'; | ||
link.as = 'script'; | ||
link.href = getClientUrl(key); | ||
link.onload = () => { preloaded = true }; | ||
insertElement(link); | ||
} | ||
|
||
/** | ||
* creates identity function for string replace without special replacement patterns | ||
* @param {string} str | ||
* @return {function} | ||
*/ | ||
function replacer(str) { | ||
return function () { | ||
return str; | ||
} | ||
} | ||
|
||
export function wrapHtml(wrapper, html) { | ||
return wrapper.replace(HTML_PLACEHOLDER, replacer(html)); | ||
} | ||
|
||
/** | ||
* generate macros dictionary from bid response | ||
* @param {Object} bid | ||
* @param {string} key | ||
* @return {Object} | ||
*/ | ||
function getMacros(bid, key) { | ||
return { | ||
'${key}': key, | ||
'%%ADUNIT%%': bid.adUnitCode, | ||
'%%WIDTH%%': bid.width, | ||
'%%HEIGHT%%': bid.height, | ||
'%%PATTERN:hb_adid%%': bid.adId, | ||
'%%PATTERN:hb_bidder%%': bid.bidderCode, | ||
'%_isHb!': true, | ||
'%_hbcid!': bid.creativeId || '', | ||
'%%PATTERN:hb_pb%%': bid.pbHg, | ||
'%%SITE%%': location.hostname, | ||
'%_pimp%': PV_ID | ||
}; | ||
} | ||
|
||
/** | ||
* replace macro placeholders in a string with values from a dictionary | ||
* @param {string} wrapper | ||
* @param {Object} macros | ||
* @return {string} | ||
*/ | ||
function replaceMacros(wrapper, macros) { | ||
var re = new RegExp('\\' + Object.keys(macros).join('|'), 'gi'); | ||
|
||
return wrapper.replace(re, function(matched) { | ||
return macros[matched]; | ||
}); | ||
} | ||
|
||
/** | ||
* build final creative html with creative wrapper | ||
* @param {Object} bid | ||
* @param {string} wrapper | ||
* @param {string} html | ||
* @return {string} | ||
*/ | ||
function buildHtml(bid, wrapper, html, key) { | ||
let macros = getMacros(bid, key); | ||
wrapper = replaceMacros(wrapper, macros); | ||
return wrapHtml(wrapper, html); | ||
} | ||
|
||
/** | ||
* muatates the bid ad property | ||
* @param {Object} bid | ||
* @param {string} ad | ||
*/ | ||
function mutateBid(bid, ad) { | ||
bid.ad = ad; | ||
} | ||
|
||
/** | ||
* wraps a bid object with the creative wrapper | ||
* @param {Object} bid | ||
* @param {string} key | ||
*/ | ||
export function wrapBidResponse(bid, key) { | ||
let wrapped = buildHtml(bid, wrapper, bid.ad, key); | ||
mutateBid(bid, wrapped); | ||
} | ||
|
||
/** | ||
* checks if bidder's bids should be monitored | ||
* @param {string} bidder | ||
* @return {boolean} | ||
*/ | ||
function isSupportedBidder(bidder, paramsBidders) { | ||
return isEmpty(paramsBidders) || paramsBidders[bidder] === true; | ||
} | ||
|
||
/** | ||
* checks if bid should be monitored | ||
* @param {Object} bid | ||
* @return {boolean} | ||
*/ | ||
function shouldWrap(bid, params) { | ||
let supportedBidder = isSupportedBidder(bid.bidderCode, params.bidders); | ||
let donePreload = params.wap ? preloaded : true; | ||
return wrapperReady && supportedBidder && donePreload; | ||
} | ||
|
||
function conditionallyWrap(bidResponse, config, userConsent) { | ||
let params = config.params; | ||
if (shouldWrap(bidResponse, params)) { | ||
wrapBidResponse(bidResponse, params.key); | ||
} | ||
} | ||
|
||
function init(config, userConsent) { | ||
let params = config.params; | ||
if (!params || !params.key) { | ||
logError('missing key for geoedge RTD module provider'); | ||
return false; | ||
} | ||
preloadClient(params.key); | ||
return true; | ||
} | ||
|
||
/** @type {RtdSubmodule} */ | ||
export const geoedgeSubmodule = { | ||
/** | ||
* used to link submodule with realTimeData | ||
* @type {string} | ||
*/ | ||
name: SUBMODULE_NAME, | ||
init, | ||
onBidResponseEvent: conditionallyWrap | ||
}; | ||
|
||
export function beforeInit() { | ||
fetchWrapper(setWrapper); | ||
submodule('realTimeData', geoedgeSubmodule); | ||
} | ||
|
||
beforeInit(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
## Overview | ||
|
||
Module Name: Geoedge Rtd provider | ||
Module Type: Rtd Provider | ||
Maintainer: guy.books@geoedge.com | ||
|
||
The Geoedge Realtime module let pusblishers to 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. | ||
|
||
## Integration | ||
|
||
1) Build the geoedge RTD module into the Prebid.js package with: | ||
|
||
``` | ||
gulp build --modules=geoedgeRtdProvider,... | ||
``` | ||
|
||
2) Use `setConfig` to instruct Prebid.js to initilize the geoedge module, as specified below. | ||
|
||
## Configuration | ||
|
||
This module is configured as part of the `realTimeData.dataProviders` object: | ||
|
||
```javascript | ||
pbjs.setConfig({ | ||
realTimeData: { | ||
dataProviders: [{ | ||
name: 'geoedge', | ||
params: { | ||
key: '123123', | ||
bidders: { | ||
'bidderA': true, // monitor bids form this bidder | ||
'bidderB': false // do not monitor bids form this bidder. | ||
}, | ||
wap: true | ||
} | ||
}] | ||
} | ||
}); | ||
``` | ||
|
||
Parameters details: | ||
|
||
{: .table .table-bordered .table-striped } | ||
|Name |Type |Description |Notes | | ||
| :------------ | :------------ | :------------ |:------------ | | ||
|name | String | Real time data module name |Required, always 'geoedge' | | ||
|params | Object | | | | ||
|params.key | String | Customer key |Required, contact Geoedge to get your key | | ||
|params.bidders | Object | Bidders to monitor |Optional, list of bidder to include / exclude from monitoring. Omitting this will monitor bids from all bidders. | | ||
|params.wap |Boolean |Wrap after preload |Optional, defaults to `false`. Set to `true` if you want to monitor only after the module has preloaded the monitoring client. | | ||
|
||
## Example | ||
|
||
To view an integration example: | ||
|
||
1) in your cli run: | ||
|
||
``` | ||
gulp serve --modules=appnexusBidAdapter,geoedgeRtdProvider | ||
``` | ||
|
||
2) in your browser, navigate to: | ||
|
||
``` | ||
http://localhost:9999/integrationExamples/gpt/geoedgeRtdProvider_example.html | ||
``` |
Oops, something went wrong.