prebid.js 6.7.0 → 6.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.js +8 -1
- package/integrationExamples/gpt/{haloRtdProvider_example.html → hadronRtdProvider_example.html} +9 -9
- package/integrationExamples/gpt/idImportLibrary_example.html +2 -2
- package/integrationExamples/gpt/userId_example.html +2 -2
- package/integrationExamples/gpt/weboramaRtdProvider_example.html +154 -115
- package/integrationExamples/gpt/x-domain/creative.html +63 -29
- package/modules/.submodules.json +3 -0
- package/modules/adagioBidAdapter.js +0 -8
- package/modules/adagioBidAdapter.md +1 -1
- package/modules/adkernelBidAdapter.js +2 -1
- package/modules/adnuntiusRtdProvider.js +96 -0
- package/modules/adnuntiusRtdProvider.md +41 -0
- package/modules/adotBidAdapter.js +516 -567
- package/modules/adotBidAdapter.md +6 -44
- package/modules/adpod.js +12 -14
- package/modules/adyoulikeBidAdapter.js +2 -0
- package/modules/appnexusBidAdapter.js +14 -2
- package/modules/asealBidAdapter.js +58 -0
- package/modules/asealBidAdapter.md +52 -0
- package/modules/brandmetricsRtdProvider.js +168 -0
- package/modules/brandmetricsRtdProvider.md +40 -0
- package/modules/conversantBidAdapter.js +7 -0
- package/modules/criteoBidAdapter.js +9 -0
- package/modules/currency.js +27 -5
- package/modules/displayioBidAdapter.js +157 -0
- package/modules/displayioBidAdapter.md +148 -0
- package/modules/dspxBidAdapter.js +69 -29
- package/modules/dspxBidAdapter.md +2 -1
- package/modules/e_volutionBidAdapter.js +158 -0
- package/modules/gridBidAdapter.js +15 -1
- package/modules/gumgumBidAdapter.js +52 -38
- package/modules/hadronIdSystem.js +96 -0
- package/modules/hadronIdSystem.md +35 -0
- package/modules/hadronRtdProvider.js +254 -0
- package/modules/hadronRtdProvider.md +126 -0
- package/modules/haloIdSystem.md +4 -35
- package/modules/haloRtdProvider.md +3 -126
- package/modules/imRtdProvider.js +10 -0
- package/modules/improvedigitalBidAdapter.js +5 -0
- package/modules/interactiveOffersBidAdapter.js +9 -6
- package/modules/iqzoneBidAdapter.js +10 -3
- package/modules/iqzoneBidAdapter.md +16 -0
- package/modules/ixBidAdapter.js +2 -6
- package/modules/kubientBidAdapter.js +50 -19
- package/modules/lunamediahbBidAdapter.js +32 -4
- package/modules/malltvBidAdapter.js +7 -3
- package/modules/malltvBidAdapter.md +64 -51
- package/modules/mass.js +3 -5
- package/modules/mediakeysBidAdapter.js +0 -5
- package/modules/medianetAnalyticsAdapter.js +1 -1
- package/modules/mediasquareBidAdapter.js +9 -1
- package/modules/nextMillenniumBidAdapter.js +1 -0
- package/modules/oguryBidAdapter.js +7 -14
- package/modules/prebidServerBidAdapter/index.js +61 -39
- package/modules/priceFloors.js +20 -12
- package/modules/pubmaticBidAdapter.js +1 -1
- package/modules/richaudienceBidAdapter.js +8 -3
- package/modules/riseBidAdapter.js +17 -6
- package/modules/rtbhouseBidAdapter.js +2 -0
- package/modules/rubiconAnalyticsAdapter.js +5 -0
- package/modules/rubiconBidAdapter.js +2 -2
- package/modules/sizeMappingV2.js +1 -8
- package/modules/sortableAnalyticsAdapter.js +5 -4
- package/modules/sovrnBidAdapter.js +93 -18
- package/modules/sovrnBidAdapter.md +80 -2
- package/modules/sspBCBidAdapter.js +53 -20
- package/modules/telariaBidAdapter.js +22 -29
- package/modules/trustpidSystem.js +197 -0
- package/modules/trustpidSystem.md +45 -0
- package/modules/undertoneBidAdapter.js +17 -1
- package/modules/userId/eids.js +16 -1
- package/modules/userId/eids.md +10 -2
- package/modules/userId/userId.md +17 -2
- package/modules/vibrantmediaBidAdapter.js +220 -0
- package/modules/vibrantmediaBidAdapter.md +92 -0
- package/modules/vidoomyBidAdapter.js +8 -0
- package/modules/vidoomyBidAdapter.md +4 -2
- package/modules/weboramaRtdProvider.js +264 -34
- package/modules/weboramaRtdProvider.md +110 -40
- package/modules/yahoosspBidAdapter.js +3 -1
- package/modules/yieldoneBidAdapter.js +6 -0
- package/package.json +2 -1
- package/src/adRendering.js +38 -0
- package/src/adapterManager.js +24 -19
- package/src/adapters/bidderFactory.js +14 -11
- package/src/adloader.js +2 -1
- package/src/auction.js +138 -115
- package/src/auctionIndex.js +85 -0
- package/src/auctionManager.js +3 -0
- package/src/bidderSettings.js +69 -0
- package/src/bidfactory.js +18 -6
- package/src/native.js +29 -21
- package/src/prebid.js +3 -19
- package/src/secureCreatives.js +128 -45
- package/src/targeting.js +11 -2
- package/src/utils.js +14 -17
- package/src/video.js +10 -11
- package/src/videoCache.js +10 -9
- package/test/fixtures/fixtures.js +2 -1
- package/test/helpers/indexStub.js +28 -0
- package/test/helpers/syncPromise.js +71 -0
- package/test/spec/auctionmanager_spec.js +268 -89
- package/test/spec/config_spec.js +24 -1
- package/test/spec/modules/adagioBidAdapter_spec.js +0 -10
- package/test/spec/modules/adnuntiusRtdProvider_spec.js +145 -0
- package/test/spec/modules/adotBidAdapter_spec.js +294 -3124
- package/test/spec/modules/adpod_spec.js +91 -156
- package/test/spec/modules/adyoulikeBidAdapter_spec.js +4 -0
- package/test/spec/modules/appnexusBidAdapter_spec.js +27 -0
- package/test/spec/modules/asealBidAdapter_spec.js +144 -0
- package/test/spec/modules/brandmetricsRtdProvider_spec.js +191 -0
- package/test/spec/modules/conversantBidAdapter_spec.js +54 -2
- package/test/spec/modules/criteoBidAdapter_spec.js +21 -0
- package/test/spec/modules/currency_spec.js +36 -15
- package/test/spec/modules/displayioBidAdapter_spec.js +239 -0
- package/test/spec/modules/dspxBidAdapter_spec.js +20 -15
- package/test/spec/modules/e_volutionBidAdapter_spec.js +242 -0
- package/test/spec/modules/eids_spec.js +2 -2
- package/test/spec/modules/gridBidAdapter_spec.js +18 -0
- package/test/spec/modules/gumgumBidAdapter_spec.js +49 -3
- package/test/spec/modules/hadronIdSystem_spec.js +57 -0
- package/test/spec/modules/hadronRtdProvider_spec.js +762 -0
- package/test/spec/modules/imRtdProvider_spec.js +30 -1
- package/test/spec/modules/improvedigitalBidAdapter_spec.js +19 -0
- package/test/spec/modules/iqzoneBidAdapter_spec.js +1 -0
- package/test/spec/modules/ixBidAdapter_spec.js +1 -1
- package/test/spec/modules/kubientBidAdapter_spec.js +182 -84
- package/test/spec/modules/lunamediahbBidAdapter_spec.js +27 -1
- package/test/spec/modules/mass_spec.js +2 -14
- package/test/spec/modules/mediakeysBidAdapter_spec.js +9 -5
- package/test/spec/modules/mediasquareBidAdapter_spec.js +25 -1
- package/test/spec/modules/oguryBidAdapter_spec.js +63 -5
- package/test/spec/modules/prebidServerBidAdapter_spec.js +43 -6
- package/test/spec/modules/priceFloors_spec.js +83 -24
- package/test/spec/modules/pubmaticBidAdapter_spec.js +40 -0
- package/test/spec/modules/riseBidAdapter_spec.js +30 -4
- package/test/spec/modules/rubiconAnalyticsAdapter_spec.js +31 -1
- package/test/spec/modules/rubiconBidAdapter_spec.js +1 -1
- package/test/spec/modules/sortableAnalyticsAdapter_spec.js +2 -3
- package/test/spec/modules/sovrnBidAdapter_spec.js +413 -333
- package/test/spec/modules/sspBCBidAdapter_spec.js +7 -7
- package/test/spec/modules/telariaBidAdapter_spec.js +1 -3
- package/test/spec/modules/trustpidSystem_spec.js +232 -0
- package/test/spec/modules/undertoneBidAdapter_spec.js +55 -2
- package/test/spec/modules/userId_spec.js +39 -39
- package/test/spec/modules/vibrantmediaBidAdapter_spec.js +1237 -0
- package/test/spec/modules/vidoomyBidAdapter_spec.js +7 -1
- package/test/spec/modules/weboramaRtdProvider_spec.js +536 -20
- package/test/spec/modules/yahoosspBidAdapter_spec.js +10 -0
- package/test/spec/modules/yieldoneBidAdapter_spec.js +33 -0
- package/test/spec/native_spec.js +62 -40
- package/test/spec/unit/core/adapterManager_spec.js +22 -0
- package/test/spec/unit/core/auctionIndex_spec.js +129 -0
- package/test/spec/unit/core/bidderFactory_spec.js +65 -12
- package/test/spec/unit/core/bidderSettings_spec.js +123 -0
- package/test/spec/unit/core/targeting_spec.js +93 -0
- package/test/spec/unit/pbjs_api_spec.js +80 -42
- package/test/spec/unit/secureCreatives_spec.js +143 -24
- package/test/spec/videoCache_spec.js +18 -19
- package/test/spec/video_spec.js +51 -61
|
@@ -62,6 +62,12 @@ export const spec = {
|
|
|
62
62
|
payload.lr_env = idlEnv;
|
|
63
63
|
}
|
|
64
64
|
|
|
65
|
+
// IMID
|
|
66
|
+
const imuid = deepAccess(bidRequest, 'userId.imuid');
|
|
67
|
+
if (isStr(imuid) && !isEmpty(imuid)) {
|
|
68
|
+
payload.imuid = imuid;
|
|
69
|
+
}
|
|
70
|
+
|
|
65
71
|
return {
|
|
66
72
|
method: 'GET',
|
|
67
73
|
url: ENDPOINT_URL,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "prebid.js",
|
|
3
|
-
"version": "6.
|
|
3
|
+
"version": "6.11.0",
|
|
4
4
|
"description": "Header Bidding Management Library",
|
|
5
5
|
"main": "src/prebid.js",
|
|
6
6
|
"scripts": {
|
|
@@ -30,6 +30,7 @@
|
|
|
30
30
|
},
|
|
31
31
|
"devDependencies": {
|
|
32
32
|
"@babel/core": "^7.8.4",
|
|
33
|
+
"@babel/eslint-parser": "^7.16.5",
|
|
33
34
|
"@babel/preset-env": "^7.8.4",
|
|
34
35
|
"@jsdevtools/coverage-istanbul-loader": "^3.0.3",
|
|
35
36
|
"@wdio/browserstack-service": "^6.1.4",
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import {logError} from './utils.js';
|
|
2
|
+
import events from './events.js';
|
|
3
|
+
import CONSTANTS from './constants.json';
|
|
4
|
+
|
|
5
|
+
const {AD_RENDER_FAILED, AD_RENDER_SUCCEEDED} = CONSTANTS.EVENTS;
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Emit the AD_RENDER_FAILED event.
|
|
9
|
+
*
|
|
10
|
+
* @param reason one of the values in CONSTANTS.AD_RENDER_FAILED_REASON
|
|
11
|
+
* @param message failure description
|
|
12
|
+
* @param bid? bid response object that failed to render
|
|
13
|
+
* @param id? adId that failed to render
|
|
14
|
+
*/
|
|
15
|
+
export function emitAdRenderFail({ reason, message, bid, id }) {
|
|
16
|
+
const data = { reason, message };
|
|
17
|
+
if (bid) data.bid = bid;
|
|
18
|
+
if (id) data.adId = id;
|
|
19
|
+
|
|
20
|
+
logError(message);
|
|
21
|
+
events.emit(AD_RENDER_FAILED, data);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* Emit the AD_RENDER_SUCCEEDED event.
|
|
26
|
+
*
|
|
27
|
+
* @param doc document object that was used to `.write` the ad. Should be `null` if unavailable (e.g. for documents in
|
|
28
|
+
* a cross-origin frame).
|
|
29
|
+
* @param bid bid response object for the ad that was rendered
|
|
30
|
+
* @param id adId that was rendered.
|
|
31
|
+
*/
|
|
32
|
+
export function emitAdRenderSucceeded({ doc, bid, id }) {
|
|
33
|
+
const data = { doc };
|
|
34
|
+
if (bid) data.bid = bid;
|
|
35
|
+
if (id) data.adId = id;
|
|
36
|
+
|
|
37
|
+
events.emit(AD_RENDER_SUCCEEDED, data);
|
|
38
|
+
}
|
package/src/adapterManager.js
CHANGED
|
@@ -1,12 +1,28 @@
|
|
|
1
1
|
/** @module adaptermanger */
|
|
2
2
|
|
|
3
3
|
import {
|
|
4
|
-
_each,
|
|
5
|
-
|
|
6
|
-
|
|
4
|
+
_each,
|
|
5
|
+
bind,
|
|
6
|
+
deepAccess,
|
|
7
|
+
deepClone,
|
|
8
|
+
flatten,
|
|
9
|
+
generateUUID,
|
|
10
|
+
getBidderCodes,
|
|
11
|
+
getDefinedParams,
|
|
12
|
+
getUniqueIdentifierStr,
|
|
13
|
+
getUserConfiguredParams,
|
|
14
|
+
groupBy,
|
|
15
|
+
isArray,
|
|
16
|
+
isValidMediaTypes,
|
|
17
|
+
logError,
|
|
18
|
+
logInfo,
|
|
19
|
+
logMessage,
|
|
20
|
+
logWarn,
|
|
21
|
+
shuffle,
|
|
22
|
+
timestamp
|
|
7
23
|
} from './utils.js';
|
|
8
24
|
import { getLabels, resolveStatus } from './sizeMapping.js';
|
|
9
|
-
import {
|
|
25
|
+
import { decorateAdUnitsWithNativeParams, nativeAdapters } from './native.js';
|
|
10
26
|
import { newBidder } from './adapters/bidderFactory.js';
|
|
11
27
|
import { ajaxBuilder } from './ajax.js';
|
|
12
28
|
import { config, RANDOM } from './config.js';
|
|
@@ -62,15 +78,8 @@ function getBids({bidderCode, auctionId, bidderRequestId, adUnits, labels, src})
|
|
|
62
78
|
if (active) {
|
|
63
79
|
result.push(adUnit.bids.filter(bid => bid.bidder === bidderCode)
|
|
64
80
|
.reduce((bids, bid) => {
|
|
65
|
-
const nativeParams =
|
|
66
|
-
adUnit.nativeParams || deepAccess(adUnit, 'mediaTypes.native');
|
|
67
|
-
if (nativeParams) {
|
|
68
|
-
bid = Object.assign({}, bid, {
|
|
69
|
-
nativeParams: processNativeAdUnitParams(nativeParams),
|
|
70
|
-
});
|
|
71
|
-
}
|
|
72
|
-
|
|
73
81
|
bid = Object.assign({}, bid, getDefinedParams(adUnit, [
|
|
82
|
+
'nativeParams',
|
|
74
83
|
'ortb2Imp',
|
|
75
84
|
'mediaType',
|
|
76
85
|
'renderer',
|
|
@@ -209,6 +218,7 @@ adapterManager.makeBidRequests = hook('sync', function (adUnits, auctionStart, a
|
|
|
209
218
|
* @see {@link https://github.com/prebid/Prebid.js/issues/4149|Issue}
|
|
210
219
|
*/
|
|
211
220
|
events.emit(CONSTANTS.EVENTS.BEFORE_REQUEST_BIDS, adUnits);
|
|
221
|
+
decorateAdUnitsWithNativeParams(adUnits);
|
|
212
222
|
|
|
213
223
|
let bidderCodes = getBidderCodes(adUnits);
|
|
214
224
|
if (config.getConfig('bidderSequence') === RANDOM) {
|
|
@@ -404,12 +414,7 @@ adapterManager.callBids = (adUnits, bidRequests, addBidResponse, doneCb, request
|
|
|
404
414
|
s2sAdapter.callBids(
|
|
405
415
|
s2sBidRequest,
|
|
406
416
|
serverBidRequests,
|
|
407
|
-
|
|
408
|
-
let bidderRequest = getBidderRequest(serverBidRequests, bid.bidderCode, adUnitCode);
|
|
409
|
-
if (bidderRequest) {
|
|
410
|
-
addBidResponse.call(bidderRequest, adUnitCode, bid)
|
|
411
|
-
}
|
|
412
|
-
},
|
|
417
|
+
addBidResponse,
|
|
413
418
|
() => doneCbs.forEach(done => done()),
|
|
414
419
|
s2sAjax
|
|
415
420
|
);
|
|
@@ -442,7 +447,7 @@ adapterManager.callBids = (adUnits, bidRequests, addBidResponse, doneCb, request
|
|
|
442
447
|
adapter.callBids,
|
|
443
448
|
adapter,
|
|
444
449
|
bidRequest,
|
|
445
|
-
addBidResponse
|
|
450
|
+
addBidResponse,
|
|
446
451
|
adapterDone,
|
|
447
452
|
ajax,
|
|
448
453
|
onTimelyResponse,
|
|
@@ -9,10 +9,11 @@ import CONSTANTS from '../constants.json';
|
|
|
9
9
|
import events from '../events.js';
|
|
10
10
|
import includes from 'core-js-pure/features/array/includes.js';
|
|
11
11
|
import { ajax } from '../ajax.js';
|
|
12
|
-
import { logWarn, logError, parseQueryStringParameters, delayExecution, parseSizesInput,
|
|
12
|
+
import { logWarn, logError, parseQueryStringParameters, delayExecution, parseSizesInput, flatten, uniques, timestamp, deepAccess, isArray, isPlainObject } from '../utils.js';
|
|
13
13
|
import { ADPOD } from '../mediaTypes.js';
|
|
14
14
|
import { getHook, hook } from '../hook.js';
|
|
15
15
|
import { getCoreStorageManager } from '../storageManager.js';
|
|
16
|
+
import {auctionManager} from '../auctionManager.js';
|
|
16
17
|
|
|
17
18
|
export const storage = getCoreStorageManager('bidderFactory');
|
|
18
19
|
|
|
@@ -36,6 +37,7 @@ export const storage = getCoreStorageManager('bidderFactory');
|
|
|
36
37
|
* });
|
|
37
38
|
*
|
|
38
39
|
* @see BidderSpec for the full API and more thorough descriptions.
|
|
40
|
+
*
|
|
39
41
|
*/
|
|
40
42
|
|
|
41
43
|
/**
|
|
@@ -130,7 +132,7 @@ export const storage = getCoreStorageManager('bidderFactory');
|
|
|
130
132
|
*/
|
|
131
133
|
|
|
132
134
|
// common params for all mediaTypes
|
|
133
|
-
const COMMON_BID_RESPONSE_KEYS = ['
|
|
135
|
+
const COMMON_BID_RESPONSE_KEYS = ['cpm', 'ttl', 'creativeId', 'netRevenue', 'currency'];
|
|
134
136
|
|
|
135
137
|
const DEFAULT_REFRESHIN_DAYS = 1;
|
|
136
138
|
|
|
@@ -187,7 +189,7 @@ export function newBidder(spec) {
|
|
|
187
189
|
const adUnitCodesHandled = {};
|
|
188
190
|
function addBidWithCode(adUnitCode, bid) {
|
|
189
191
|
adUnitCodesHandled[adUnitCode] = true;
|
|
190
|
-
if (isValid(adUnitCode, bid
|
|
192
|
+
if (isValid(adUnitCode, bid)) {
|
|
191
193
|
addBidResponse(adUnitCode, bid);
|
|
192
194
|
}
|
|
193
195
|
}
|
|
@@ -230,7 +232,7 @@ export function newBidder(spec) {
|
|
|
230
232
|
// Server requests have returned and been processed. Since `ajax` accepts a single callback,
|
|
231
233
|
// we need to rig up a function which only executes after all the requests have been responded.
|
|
232
234
|
const onResponse = delayExecution(configEnabledCallback(afterAllResponses), requests.length)
|
|
233
|
-
requests.forEach(
|
|
235
|
+
requests.forEach(requestObject => events.emit(CONSTANTS.EVENTS.BEFORE_BIDDER_HTTP, bidderRequest, requestObject));
|
|
234
236
|
requests.forEach(processRequest);
|
|
235
237
|
|
|
236
238
|
function formatGetParameters(data) {
|
|
@@ -451,16 +453,17 @@ export function getIabSubCategory(bidderCode, category) {
|
|
|
451
453
|
}
|
|
452
454
|
|
|
453
455
|
// check that the bid has a width and height set
|
|
454
|
-
function validBidSize(adUnitCode, bid,
|
|
456
|
+
function validBidSize(adUnitCode, bid, {index = auctionManager.index} = {}) {
|
|
455
457
|
if ((bid.width || parseInt(bid.width, 10) === 0) && (bid.height || parseInt(bid.height, 10) === 0)) {
|
|
456
458
|
bid.width = parseInt(bid.width, 10);
|
|
457
459
|
bid.height = parseInt(bid.height, 10);
|
|
458
460
|
return true;
|
|
459
461
|
}
|
|
460
462
|
|
|
461
|
-
const
|
|
463
|
+
const bidRequest = index.getBidRequest(bid);
|
|
464
|
+
const mediaTypes = index.getMediaTypes(bid);
|
|
462
465
|
|
|
463
|
-
const sizes =
|
|
466
|
+
const sizes = (bidRequest && bidRequest.sizes) || (mediaTypes && mediaTypes.banner && mediaTypes.banner.sizes);
|
|
464
467
|
const parsedSizes = parseSizesInput(sizes);
|
|
465
468
|
|
|
466
469
|
// if a banner impression has one valid size, we assign that size to any bid
|
|
@@ -476,7 +479,7 @@ function validBidSize(adUnitCode, bid, bidRequests) {
|
|
|
476
479
|
}
|
|
477
480
|
|
|
478
481
|
// Validate the arguments sent to us by the adapter. If this returns false, the bid should be totally ignored.
|
|
479
|
-
export function isValid(adUnitCode, bid,
|
|
482
|
+
export function isValid(adUnitCode, bid, {index = auctionManager.index} = {}) {
|
|
480
483
|
function hasValidKeys() {
|
|
481
484
|
let bidKeys = Object.keys(bid);
|
|
482
485
|
return COMMON_BID_RESPONSE_KEYS.every(key => includes(bidKeys, key) && !includes([undefined, null], bid[key]));
|
|
@@ -501,15 +504,15 @@ export function isValid(adUnitCode, bid, bidRequests) {
|
|
|
501
504
|
return false;
|
|
502
505
|
}
|
|
503
506
|
|
|
504
|
-
if (bid.mediaType === 'native' && !nativeBidIsValid(bid,
|
|
507
|
+
if (bid.mediaType === 'native' && !nativeBidIsValid(bid, {index})) {
|
|
505
508
|
logError(errorMessage('Native bid missing some required properties.'));
|
|
506
509
|
return false;
|
|
507
510
|
}
|
|
508
|
-
if (bid.mediaType === 'video' && !isValidVideoBid(bid,
|
|
511
|
+
if (bid.mediaType === 'video' && !isValidVideoBid(bid, {index})) {
|
|
509
512
|
logError(errorMessage(`Video bid does not have required vastUrl or renderer property`));
|
|
510
513
|
return false;
|
|
511
514
|
}
|
|
512
|
-
if (bid.mediaType === 'banner' && !validBidSize(adUnitCode, bid,
|
|
515
|
+
if (bid.mediaType === 'banner' && !validBidSize(adUnitCode, bid, {index})) {
|
|
513
516
|
logError(errorMessage(`Banner bids require a width and height`));
|
|
514
517
|
return false;
|
|
515
518
|
}
|