• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

prebid / Prebid.js / 18594521186

17 Oct 2025 01:40PM UTC coverage: 96.238% (-0.001%) from 96.239%
18594521186

push

github

web-flow
Semantiq RTD module: fix incorrect property name (#14027)

Co-authored-by: Alexandr Kim <alexandr.kim@audienzz.ch>

52437 of 64151 branches covered (81.74%)

1 of 1 new or added line in 1 file covered. (100.0%)

401 existing lines in 53 files now uncovered.

200307 of 208138 relevant lines covered (96.24%)

125.2 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

92.78
/modules/dataControllerModule/index.js
1
/**
1✔
2
 * This module validates the configuration and filters data accordingly
3
 * @module modules/dataController
4
 */
5
import {config} from '../../src/config.js';
6
import {getHook, module} from '../../src/hook.js';
7
import {deepAccess, deepSetValue, prefixLog} from '../../src/utils.js';
8
import {startAuction} from '../../src/prebid.js';
9
import {timedAuctionHook} from '../../src/utils/perfMetrics.js';
10

11
const LOG_PRE_FIX = 'Data_Controller : ';
1✔
12
const ALL = '*';
1✔
13
const MODULE_NAME = 'dataController';
1✔
14
const GLOBAL = {};
1✔
15
let _dataControllerConfig;
16

17
const _logger = prefixLog(LOG_PRE_FIX);
1✔
18

19
/**
20
 * BidderRequests hook to intiate module and reset data object
21
 */
22
export const filterBidData = timedAuctionHook('dataController', function filterBidData(fn, req) {
1✔
23
  if (_dataControllerConfig.filterEIDwhenSDA) {
7✔
24
    filterEIDs(req.adUnits, req.ortb2Fragments);
4✔
25
  }
26

27
  if (_dataControllerConfig.filterSDAwhenEID) {
7✔
28
    filterSDA(req.adUnits, req.ortb2Fragments);
3✔
29
  }
30
  fn.call(this, req);
7✔
31
  return req;
7✔
32
});
33

34
function containsConfiguredEIDS(eidSourcesMap, bidderCode) {
35
  if (_dataControllerConfig.filterSDAwhenEID.includes(ALL)) {
3✔
36
    return true;
1✔
37
  }
38
  const bidderEIDs = eidSourcesMap.get(bidderCode);
2✔
39
  if (bidderEIDs === undefined) {
2!
40
    return false;
×
41
  }
42
  return _dataControllerConfig.filterSDAwhenEID.some((source) => bidderEIDs.has(source));
2✔
43
}
44

45
function containsConfiguredSDA(segmentMap, bidderCode) {
46
  if (_dataControllerConfig.filterEIDwhenSDA.includes(ALL)) {
4✔
47
    return true;
1✔
48
  }
49
  return hasValue(segmentMap.get(bidderCode)) || hasValue(segmentMap.get(GLOBAL))
3✔
50
}
51

52
function hasValue(bidderSegment) {
53
  return bidderSegment === undefined
5✔
54
    ? false
55
    : _dataControllerConfig.filterEIDwhenSDA.some((segment) => bidderSegment.has(segment));
3✔
56
}
57

58
function getSegmentConfig(ortb2Fragments) {
59
  const bidderSDAMap = new Map();
4✔
60
  const globalObject = deepAccess(ortb2Fragments, 'global') || {};
4✔
61

62
  collectSegments(bidderSDAMap, GLOBAL, globalObject);
4✔
63
  if (ortb2Fragments.bidder) {
4✔
64
    for (const [key, value] of Object.entries(ortb2Fragments.bidder)) {
3✔
65
      collectSegments(bidderSDAMap, key, value);
3✔
66
    }
67
  }
68
  return bidderSDAMap;
4✔
69
}
70

71
function collectSegments(bidderSDAMap, key, data) {
72
  const segmentSet = constructSegment(deepAccess(data, 'user.data') || []);
7✔
73
  if (segmentSet && segmentSet.size > 0) bidderSDAMap.set(key, segmentSet);
7✔
74
}
75

76
function constructSegment(userData) {
77
  let segmentSet;
78
  if (userData) {
7✔
79
    segmentSet = new Set();
7✔
80
    for (let i = 0; i < userData.length; i++) {
7✔
81
      const segments = userData[i].segment;
4✔
82
      let segmentPrefix = '';
4✔
83
      if (userData[i].name) {
4✔
84
        segmentPrefix = userData[i].name + ':';
4✔
85
      }
86

87
      if (userData[i].ext && userData[i].ext.segtax) {
4✔
88
        segmentPrefix += userData[i].ext.segtax + ':';
4✔
89
      }
90
      for (let j = 0; j < segments.length; j++) {
4✔
91
        segmentSet.add(segmentPrefix + segments[j].id);
8✔
92
      }
93
    }
94
  }
95

96
  return segmentSet;
7✔
97
}
98

99
function getEIDsSource(adUnits) {
100
  const bidderEIDSMap = new Map();
3✔
101
  adUnits.forEach(adUnit => {
3✔
102
    (adUnit.bids || []).forEach(bid => {
3!
103
      const userEIDs = deepAccess(bid, 'userIdAsEids') || [];
3!
104

105
      if (userEIDs) {
3✔
106
        const sourceSet = new Set();
3✔
107
        for (let i = 0; i < userEIDs.length; i++) {
3✔
108
          const source = userEIDs[i].source;
3✔
109
          sourceSet.add(source);
3✔
110
        }
111
        bidderEIDSMap.set(bid.bidder, sourceSet);
3✔
112
      }
113
    });
114
  });
115

116
  return bidderEIDSMap;
3✔
117
}
118

119
function filterSDA(adUnits, ortb2Fragments) {
120
  const bidderEIDSMap = getEIDsSource(adUnits);
3✔
121
  let resetGlobal = false;
3✔
122
  for (const [key, value] of Object.entries(ortb2Fragments.bidder)) {
3✔
123
    const resetSDA = containsConfiguredEIDS(bidderEIDSMap, key);
3✔
124
    if (resetSDA) {
3✔
125
      deepSetValue(value, 'user.data', []);
2✔
126
      resetGlobal = true;
2✔
127
    }
128
  }
129
  if (resetGlobal) {
3✔
130
    deepSetValue(ortb2Fragments, 'global.user.data', [])
2✔
131
  }
132
}
133

134
function filterEIDs(adUnits, ortb2Fragments) {
135
  const segementMap = getSegmentConfig(ortb2Fragments);
4✔
136
  let globalEidUpdate = false;
4✔
137
  adUnits.forEach(adUnit => {
4✔
138
    adUnit.bids.forEach(bid => {
4✔
139
      const resetEID = containsConfiguredSDA(segementMap, bid.bidder);
4✔
140
      if (resetEID) {
4✔
141
        globalEidUpdate = true;
3✔
142
        bid.userIdAsEids = [];
3✔
143
        bid.userId = {};
3✔
144
        if (ortb2Fragments.bidder) {
3✔
145
          const bidderFragment = ortb2Fragments.bidder[bid.bidder];
2✔
146
          const userExt = deepAccess(bidderFragment, 'user.ext.eids') || [];
2✔
147
          if (userExt) {
2✔
148
            deepSetValue(bidderFragment, 'user.ext.eids', [])
2✔
149
          }
150
        }
151
      }
152
    });
153
  });
154

155
  if (globalEidUpdate) {
4✔
156
    deepSetValue(ortb2Fragments, 'global.user.ext.eids', [])
3✔
157
  }
158
  return adUnits;
4✔
159
}
160

161
export function init() {
162
  const confListener = config.getConfig(MODULE_NAME, dataControllerConfig => {
8✔
163
    const dataController = dataControllerConfig && dataControllerConfig.dataController;
8✔
164
    if (!dataController) {
8!
UNCOV
165
      _logger.logInfo(`Data Controller is not configured`);
×
UNCOV
166
      startAuction.getHooks({hook: filterBidData}).remove();
×
UNCOV
167
      return;
×
168
    }
169

170
    if (dataController.filterEIDwhenSDA && dataController.filterSDAwhenEID) {
8!
UNCOV
171
      _logger.logInfo(`Data Controller can be configured with either filterEIDwhenSDA or filterSDAwhenEID`);
×
UNCOV
172
      startAuction.getHooks({hook: filterBidData}).remove();
×
UNCOV
173
      return;
×
174
    }
175
    confListener(); // unsubscribe config listener
8✔
176
    _dataControllerConfig = dataController;
8✔
177

178
    getHook('startAuction').before(filterBidData);
8✔
179
  });
180
}
181

182
init();
1✔
183
module(MODULE_NAME, init);
1✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc