Skip to content

Commit

Permalink
Merge branch 'master' into prebid-4.0
Browse files Browse the repository at this point in the history
  • Loading branch information
jsnellbaker committed Jul 23, 2020
2 parents bed2915 + 6e71525 commit 02cdf47
Show file tree
Hide file tree
Showing 22 changed files with 1,624 additions and 65 deletions.
110 changes: 110 additions & 0 deletions modules/boldwinBidAdapter.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,110 @@
import {registerBidder} from '../src/adapters/bidderFactory.js';
import { BANNER, NATIVE, VIDEO } from '../src/mediaTypes.js';
import * as utils from '../src/utils.js';

const BIDDER_CODE = 'boldwin';
const AD_URL = 'https://ssp.videowalldirect.com/?c=o&m=multi';
const SYNC_URL = 'https://cs.videowalldirect.com/?c=o&m=cookie'

function isBidResponseValid(bid) {
if (!bid.requestId || !bid.cpm || !bid.creativeId ||
!bid.ttl || !bid.currency) {
return false;
}
switch (bid.mediaType) {
case BANNER:
return Boolean(bid.width && bid.height && bid.ad);
case VIDEO:
return Boolean(bid.vastUrl);
case NATIVE:
return Boolean(bid.native && bid.native.title && bid.native.image && bid.native.impressionTrackers);
default:
return false;
}
}

export const spec = {
code: BIDDER_CODE,
supportedMediaTypes: [BANNER, VIDEO, NATIVE],

isBidRequestValid: (bid) => {
return Boolean(bid.bidId && bid.params && !isNaN(parseInt(bid.params.placementId)));
},

buildRequests: (validBidRequests = [], bidderRequest) => {
let winTop = window;
let location;
try {
location = new URL(bidderRequest.refererInfo.referer)
winTop = window.top;
} catch (e) {
location = winTop.location;
utils.logMessage(e);
};
let placements = [];
let request = {
'deviceWidth': winTop.screen.width,
'deviceHeight': winTop.screen.height,
'language': (navigator && navigator.language) ? navigator.language.split('-')[0] : '',
'secure': 1,
'host': location.host,
'page': location.pathname,
'placements': placements
};
if (bidderRequest) {
if (bidderRequest.uspConsent) {
request.ccpa = bidderRequest.uspConsent;
}
if (bidderRequest.gdprConsent) {
request.gdpr = bidderRequest.gdprConsent
}
}
const len = validBidRequests.length;

for (let i = 0; i < len; i++) {
let bid = validBidRequests[i];
let sizes
if (bid.mediaTypes) {
if (bid.mediaTypes[BANNER] && bid.mediaTypes[BANNER].sizes) {
sizes = bid.mediaTypes[BANNER].sizes
} else if (bid.mediaTypes[VIDEO] && bid.mediaTypes[VIDEO].playerSize) {
sizes = bid.mediaTypes[VIDEO].playerSize
}
}
placements.push({
placementId: bid.params.placementId,
bidId: bid.bidId,
sizes: sizes || [],
wPlayer: sizes ? sizes[0] : 0,
hPlayer: sizes ? sizes[1] : 0,
traffic: bid.params.traffic || BANNER,
schain: bid.schain || {}
});
}
return {
method: 'POST',
url: AD_URL,
data: request
};
},

interpretResponse: (serverResponse) => {
let response = [];
for (let i = 0; i < serverResponse.body.length; i++) {
let resItem = serverResponse.body[i];
if (isBidResponseValid(resItem)) {
response.push(resItem);
}
}
return response;
},

getUserSyncs: () => {
return [{
type: 'image',
url: SYNC_URL
}];
}
};

registerBidder(spec);
53 changes: 53 additions & 0 deletions modules/boldwinBidAdapter.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# Overview

```
Module Name: boldwin Bidder Adapter
Module Type: boldwin Bidder Adapter
```

# Description

Module that connects to boldwin demand sources

# Test Parameters
```
var adUnits = [
// Will return static test banner
{
code: 'placementId_0',
mediaTypes: {
banner: {
sizes: [[300, 250]],
}
},
bids: [
{
bidder: 'boldwin',
params: {
placementId: 0,
traffic: 'banner'
}
}
]
},
// Will return test vast xml. All video params are stored under placement in publishers UI
{
code: 'placementId_0',
mediaTypes: {
video: {
playerSize: [640, 480],
context: 'instream'
}
},
bids: [
{
bidder: 'boldwin',
params: {
placementId: 0,
traffic: 'video'
}
}
]
}
];
```
5 changes: 0 additions & 5 deletions modules/consentManagementUsp.js
Original file line number Diff line number Diff line change
Expand Up @@ -158,11 +158,6 @@ export function requestBidsHook(fn, reqBidsConfigObj) {
timer: null
};

// in case we already have consent (eg during bid refresh)
if (consentData) {
return exitModule(null, hookConfig);
}

if (!uspCallMap[consentAPI]) {
utils.logWarn(`USP framework (${consentAPI}) is not a supported framework. Aborting consentManagement module and resuming auction.`);
return hookConfig.nextFn.apply(hookConfig.context, hookConfig.args);
Expand Down
2 changes: 1 addition & 1 deletion modules/ixBidAdapter.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import isInteger from 'core-js-pure/features/number/is-integer.js';
import { registerBidder } from '../src/adapters/bidderFactory.js';

const BIDDER_CODE = 'ix';
const SECURE_BID_URL = 'https://as-sec.casalemedia.com/cygnus';
const SECURE_BID_URL = 'https://htlb.casalemedia.com/cygnus';
const SUPPORTED_AD_TYPES = [BANNER, VIDEO];
const BANNER_ENDPOINT_VERSION = 7.2;
const VIDEO_ENDPOINT_VERSION = 8.1;
Expand Down
79 changes: 66 additions & 13 deletions modules/medianetAnalyticsAdapter.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import CONSTANTS from '../src/constants.json';
import * as utils from '../src/utils.js';
import { ajax } from '../src/ajax.js';
import { getRefererInfo } from '../src/refererDetection.js';
import { getPriceGranularity, AUCTION_IN_PROGRESS, AUCTION_COMPLETED } from '../src/auction.js'
import { AUCTION_COMPLETED, AUCTION_IN_PROGRESS, getPriceGranularity } from '../src/auction.js'

const analyticsType = 'endpoint';
const ENDPOINT = 'https://pb-logs.media.net/log?logid=kfk&evtid=prebid_analytics_events_client';
Expand All @@ -29,6 +29,7 @@ const ERROR_CONFIG_FETCH = 'analytics_config_ajax_fail';
const BID_SUCCESS = 1;
const BID_NOBID = 2;
const BID_TIMEOUT = 3;
const BID_FLOOR_REJECTED = 12;
const DUMMY_BIDDER = '-2';

const CONFIG_PENDING = 0;
Expand Down Expand Up @@ -151,7 +152,7 @@ class PageDetail {
this.canonical_url = canonicalUrl;
this.og_url = ogUrl;
this.twitter_url = twitterUrl;
this.screen = this._getWindowSize()
this.screen = this._getWindowSize();
}

_getTopWindowReferrer() {
Expand Down Expand Up @@ -201,9 +202,9 @@ class PageDetail {
}

class AdSlot {
constructor(mediaTypes, bannerSizes, tmax, supplyAdCode, adext) {
constructor(mediaTypes, allMediaTypeSizes, tmax, supplyAdCode, adext, context, adSize) {
this.mediaTypes = mediaTypes;
this.bannerSizes = bannerSizes;
this.allMediaTypeSizes = allMediaTypeSizes;
this.tmax = tmax;
this.supplyAdCode = supplyAdCode;
this.adext = adext;
Expand All @@ -213,6 +214,8 @@ class AdSlot {
// shouldBeLogged is assigned when requested,
// since we are waiting for logging percent response
this.shouldBeLogged = undefined;
this.context = context;
this.adSize = adSize; // old ad unit sizes
}

getShouldBeLogged() {
Expand All @@ -226,10 +229,12 @@ class AdSlot {
return Object.assign({
supcrid: this.supplyAdCode,
mediaTypes: this.mediaTypes && this.mediaTypes.join('|'),
szs: this.bannerSizes.join('|'),
szs: this.allMediaTypeSizes.map(sz => sz.join('x')).join('|'),
tmax: this.tmax,
targ: JSON.stringify(this.targeting),
ismn: this.medianetPresent
ismn: this.medianetPresent,
vplcmtt: this.context,
sz2: this.adSize.map(sz => sz.join('x')).join('|'),
},
this.adext && {'adext': JSON.stringify(this.adext)},
);
Expand Down Expand Up @@ -261,6 +266,8 @@ class Bid {
this.crid = undefined;
this.pubcrid = undefined;
this.mpvid = undefined;
this.floorPrice = undefined;
this.floorRule = undefined;
}

get size() {
Expand Down Expand Up @@ -290,6 +297,8 @@ class Bid {
crid: this.crid,
pubcrid: this.pubcrid,
mpvid: this.mpvid,
bidflr: this.floorPrice,
flrrule: this.floorRule,
ext: JSON.stringify(this.ext)
}
}
Expand All @@ -306,6 +315,7 @@ class Auction {
this.setTargetingTime = undefined;
this.auctionEndTime = undefined;
this.bidWonTime = undefined;
this.floorData = {};
}

hasEnded() {
Expand All @@ -319,13 +329,22 @@ class Auction {
tts: this.setTargetingTime - this.auctionInitTime,
wts: this.bidWonTime - this.auctionInitTime,
aucstatus: this.status,
acid: this.acid
acid: this.acid,
flrdata: this._mergeFieldsToLog({
ln: this.floorData.location,
skp: this.floorData.skipped,
enfj: utils.deepAccess(this.floorData, 'enforcements.enforceJS'),
enfd: utils.deepAccess(this.floorData, 'enforcements.floorDeals'),
sr: this.floorData.skipRate,
fs: this.floorData.fetchStatus
}),
flrver: this.floorData.modelVersion
}
}

addSlot(supplyAdCode, { mediaTypes, bannerSizes, tmax, adext }) {
addSlot(supplyAdCode, { mediaTypes, allMediaTypeSizes, tmax, adext, context, adSize }) {
if (supplyAdCode && this.adSlots[supplyAdCode] === undefined) {
this.adSlots[supplyAdCode] = new AdSlot(mediaTypes, bannerSizes, tmax, supplyAdCode, adext);
this.adSlots[supplyAdCode] = new AdSlot(mediaTypes, allMediaTypeSizes, tmax, supplyAdCode, adext, context, adSize);
this.addBid(
new Bid('-1', DUMMY_BIDDER, 'client', '-1', supplyAdCode)
);
Expand All @@ -351,13 +370,27 @@ class Auction {
getWinnerAdslotBid(adslot) {
return this.getAdslotBids(adslot).filter((bid) => bid.winner);
}

_mergeFieldsToLog(objParams) {
let logParams = [];
let value;
for (const param of Object.keys(objParams)) {
value = objParams[param];
logParams.push(param + '=' + (value === undefined ? '' : value));
}
return logParams.join('||');
}
}

function auctionInitHandler({auctionId, timestamp}) {
function auctionInitHandler({auctionId, timestamp, bidderRequests}) {
if (auctionId && auctions[auctionId] === undefined) {
auctions[auctionId] = new Auction(auctionId);
auctions[auctionId].auctionInitTime = timestamp;
}
const floorData = utils.deepAccess(bidderRequests, '0.bids.0.floorData');
if (floorData) {
auctions[auctionId].floorData = {...floorData};
}
}

function bidRequestedHandler({ auctionId, auctionStart, bids, start, timeout, uspConsent, gdpr }) {
Expand All @@ -375,13 +408,16 @@ function bidRequestedHandler({ auctionId, auctionStart, bids, start, timeout, us
const { adUnitCode, bidder, mediaTypes, sizes, bidId, src } = bid;
if (!auctions[auctionId].adSlots[adUnitCode]) {
auctions[auctionId].auctionStartTime = auctionStart;
const sizeObject = _getSizes(mediaTypes, sizes);
auctions[auctionId].addSlot(
adUnitCode,
Object.assign({},
(mediaTypes instanceof Object) && { mediaTypes: Object.keys(mediaTypes) },
{ bannerSizes: utils.deepAccess(mediaTypes, 'banner.sizes') || sizes || [] },
{ allMediaTypeSizes: [].concat(sizeObject.banner, sizeObject.native, sizeObject.video) },
{ adext: utils.deepAccess(mediaTypes, 'banner.ext') || '' },
{ tmax: timeout }
{ tmax: timeout },
{ context: utils.deepAccess(mediaTypes, 'video.context') || '' },
{ adSize: sizeObject.banner }
)
);
}
Expand All @@ -395,6 +431,17 @@ function bidRequestedHandler({ auctionId, auctionStart, bids, start, timeout, us
});
}

function _getSizes(mediaTypes, sizes) {
const banner = utils.deepAccess(mediaTypes, 'banner.sizes') || sizes || [];
const native = utils.deepAccess(mediaTypes, 'native') ? [[1, 1]] : [];
const playerSize = utils.deepAccess(mediaTypes, 'video.playerSize') || [];
let video = [];
if (playerSize.length === 2) {
video = [playerSize]
}
return { banner, native, video }
}

function bidResponseHandler(bid) {
const { width, height, mediaType, cpm, requestId, timeToRespond, auctionId, dealId } = bid;
const {originalCpm, bidderCode, creativeId, adId, currency} = bid;
Expand All @@ -411,6 +458,8 @@ function bidResponseHandler(bid) {
{ cpm, width, height, mediaType, timeToRespond, dealId, creativeId },
{ adId, currency }
);
bidObj.floorPrice = utils.deepAccess(bid, 'floorData.floorValue');
bidObj.floorRule = utils.deepAccess(bid, 'floorData.floorRule');
bidObj.originalCpm = originalCpm || cpm;
let dfpbd = utils.deepAccess(bid, 'adserverTargeting.hb_pb');
if (!dfpbd) {
Expand All @@ -419,7 +468,11 @@ function bidResponseHandler(bid) {
dfpbd = bid[priceGranularityKey] || cpm;
}
bidObj.dfpbd = dfpbd;
bidObj.status = BID_SUCCESS;
if (bid.status === CONSTANTS.BID_STATUS.BID_REJECTED) {
bidObj.status = BID_FLOOR_REJECTED;
} else {
bidObj.status = BID_SUCCESS;
}

if (bidderCode === MEDIANET_BIDDER_CODE && bid.ext instanceof Object) {
Object.assign(
Expand Down
Loading

0 comments on commit 02cdf47

Please sign in to comment.