@@ -3,8 +3,10 @@ import { registerBidder } from 'src/adapters/bidderFactory';
3
3
import { parse } from 'src/url' ;
4
4
import * as utils from 'src/utils' ;
5
5
import find from 'core-js/library/fn/array/find' ;
6
+ import JSEncrypt from 'jsencrypt/bin/jsencrypt' ;
7
+ import sha256 from 'crypto-js/sha256' ;
6
8
7
- const ADAPTER_VERSION = 11 ;
9
+ const ADAPTER_VERSION = 14 ;
8
10
const BIDDER_CODE = 'criteo' ;
9
11
const CDB_ENDPOINT = '//bidder.criteo.com/cdb' ;
10
12
const CRITEO_VENDOR_ID = 91 ;
@@ -17,6 +19,13 @@ const PROFILE_ID_PUBLISHERTAG = 185;
17
19
// Unminified source code can be found in: https://github.com/Prebid-org/prebid-js-external-js-criteo/blob/master/dist/prod.js
18
20
const PUBLISHER_TAG_URL = '//static.criteo.net/js/ld/publishertag.prebid.js' ;
19
21
22
+ export const FAST_BID_PUBKEY = `-----BEGIN PUBLIC KEY-----
23
+ MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDO1BjAITkFTtP0IMzmF7qsqhpu
24
+ y1dGaTPHnjMU9mRZsrnfR3C0sEN5pYEzEcFRPnkJjJuhH8Rnh5+CE+LcKg0Z8ZZ7
25
+ OmOSj0/qnYTAYCu0cR5LiyWG79KlIgUyMbp92ulGg24gAyGrVn4+v/4c53WlOEUp
26
+ 4YWvb82G0CD5NcDNpQIDAQAB
27
+ -----END PUBLIC KEY-----` ;
28
+
20
29
/** @type {BidderSpec } */
21
30
export const spec = {
22
31
code : BIDDER_CODE ,
@@ -251,20 +260,52 @@ function createNativeAd(id, payload, callback) {
251
260
</script>` ;
252
261
}
253
262
263
+ export function cryptoVerify ( key , hash , code ) {
264
+ var jse = new JSEncrypt ( ) ;
265
+ jse . setPublicKey ( key ) ;
266
+ return jse . verify ( code , hash , sha256 ) ;
267
+ }
268
+
269
+ function validateFastBid ( fastBid ) {
270
+ // The value stored must contain the file's encrypted hash as first line
271
+ const firstLineEnd = fastBid . indexOf ( '\n' ) ;
272
+ const firstLine = fastBid . substr ( 0 , firstLineEnd ) . trim ( ) ;
273
+ if ( firstLine . substr ( 0 , 9 ) !== '// Hash: ' ) {
274
+ utils . logWarn ( 'No hash found in FastBid' ) ;
275
+ return false ;
276
+ }
277
+
278
+ // Remove the hash part from the locally stored value
279
+ const fileEncryptedHash = firstLine . substr ( 9 ) ;
280
+ const publisherTag = fastBid . substr ( firstLineEnd + 1 ) ;
281
+
282
+ // Verify the hash using cryptography
283
+ try {
284
+ return cryptoVerify ( FAST_BID_PUBKEY , fileEncryptedHash , publisherTag ) ;
285
+ } catch ( e ) {
286
+ utils . logWarn ( 'Failed to verify Criteo FastBid' ) ;
287
+ return undefined ;
288
+ }
289
+ }
290
+
254
291
/**
255
292
* @return {boolean }
256
293
*/
257
294
function tryGetCriteoFastBid ( ) {
258
295
try {
259
296
const fastBid = localStorage . getItem ( 'criteo_fast_bid' ) ;
260
297
if ( fastBid !== null ) {
261
- eval ( fastBid ) ; // eslint-disable-line no-eval
262
- return true ;
298
+ if ( validateFastBid ( fastBid ) === false ) {
299
+ utils . logWarn ( 'Invalid Criteo FastBid found' ) ;
300
+ localStorage . removeItem ( 'criteo_fast_bid' ) ;
301
+ } else {
302
+ utils . logInfo ( 'Using Criteo FastBid' ) ;
303
+ eval ( fastBid ) ; // eslint-disable-line no-eval
304
+ }
263
305
}
264
306
} catch ( e ) {
265
307
// Unable to get fast bid
266
308
}
267
- return false ;
268
309
}
269
310
270
311
registerBidder ( spec ) ;
0 commit comments