@adhese/sdk 0.3.0 → 0.5.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/dist/cjs/index.js CHANGED
@@ -1,12 +1,7 @@
1
1
  "use strict";
2
- var __defProp = Object.defineProperty;
3
- var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
4
- var __publicField = (obj, key, value) => {
5
- __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
6
- return value;
7
- };
8
2
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
9
3
  const sdkDevtools = require("@adhese/sdk-devtools");
4
+ const runtimeCore = require("@vue/runtime-core");
10
5
  const lodashEs = require("lodash-es");
11
6
  const zod = require("zod");
12
7
  async function waitForDomLoad() {
@@ -68,91 +63,132 @@ function createEvent() {
68
63
  removeListener
69
64
  };
70
65
  }
66
+ function renderIframe(ad, element) {
67
+ const iframe = document.createElement("iframe");
68
+ iframe.srcdoc = `
69
+ <!DOCTYPE html>
70
+ <html>
71
+ <head>
72
+ <style>
73
+ body {
74
+ margin: 0;
75
+ padding: 0;
76
+ overflow: hidden;
77
+ }
78
+ </style>
79
+ </head>
80
+ <body>
81
+ ${String(ad.tag)}
82
+ </body>
83
+ `.replaceAll(/\s+/g, " ").trim();
84
+ iframe.style.border = "none";
85
+ iframe.style.width = ad.width ?? "auto";
86
+ iframe.style.height = ad.height ?? "auto";
87
+ element.replaceChildren(iframe);
88
+ }
89
+ function renderInline(ad, element) {
90
+ element.style.width = ad.width ?? "auto";
91
+ element.style.height = ad.height ?? "auto";
92
+ element.innerHTML = String(ad.tag);
93
+ }
94
+ function generateName(location, format, slot) {
95
+ return `${location}${slot ? `${slot}` : ""}-${format}`;
96
+ }
71
97
  async function findDomSlots(context) {
72
98
  await waitForDomLoad();
73
- return (await Promise.all(Array.from(document.querySelectorAll(".adunit")).filter((element) => Boolean(element.dataset.format)).map((element) => createSlot({
99
+ return Array.from(document.querySelectorAll(".adunit")).filter((element) => {
100
+ var _a;
101
+ if (!element.dataset.format)
102
+ return false;
103
+ const name = generateName(
104
+ context.location,
105
+ element.dataset.format,
106
+ element.dataset.slot
107
+ );
108
+ return !((_a = context.getAll) == null ? void 0 : _a.call(context).some((activeSlot) => activeSlot.name.value === name));
109
+ }).map((element) => createSlot({
74
110
  format: element.dataset.format,
75
111
  containingElement: element,
76
112
  slot: element.dataset.slot,
77
113
  context
78
- })))).filter((slot) => {
114
+ })).filter((slot) => {
79
115
  var _a;
80
- return !((_a = context.getAll) == null ? void 0 : _a.call(context).some((activeSlot) => activeSlot.getName() === slot.getName()));
116
+ return !((_a = context.getAll) == null ? void 0 : _a.call(context).some((activeSlot) => activeSlot.name.value === slot.name.value));
81
117
  });
82
118
  }
83
- async function createSlotManager({
119
+ function createSlotManager({
84
120
  initialSlots = [],
85
121
  context
86
122
  }) {
87
- const slots = /* @__PURE__ */ new Map();
88
- await Promise.allSettled(initialSlots.map(async (slot) => add({
89
- ...slot,
90
- lazyLoading: false
91
- })));
92
- function getAll() {
93
- return Array.from(slots).map(([, slot]) => slot);
94
- }
95
- async function add(options) {
96
- var _a, _b;
97
- const slot = await createSlot({
98
- ...options,
99
- onDispose,
100
- onNameChange,
101
- context
123
+ const scope = runtimeCore.effectScope();
124
+ return scope.run(() => {
125
+ const slots = runtimeCore.shallowReactive(/* @__PURE__ */ new Map());
126
+ runtimeCore.watchEffect(() => {
127
+ var _a;
128
+ (_a = context.events) == null ? void 0 : _a.changeSlots.dispatch(Array.from(slots.values()));
102
129
  });
103
- function onDispose() {
104
- var _a2, _b2;
105
- slots.delete(slot.getName());
106
- logger.debug("Slot removed", {
130
+ function getAll() {
131
+ return Array.from(slots).map(([, slot]) => slot);
132
+ }
133
+ function add(options) {
134
+ var _a;
135
+ const slot = createSlot({
136
+ ...options,
137
+ onDispose,
138
+ context
139
+ });
140
+ function onDispose() {
141
+ var _a2;
142
+ slots.delete(slot.name.value);
143
+ logger.debug("Slot removed", {
144
+ slot,
145
+ slots: Array.from(slots)
146
+ });
147
+ (_a2 = context.events) == null ? void 0 : _a2.removeSlot.dispatch(slot);
148
+ }
149
+ slots.set(slot.name.value, slot);
150
+ runtimeCore.watch(slot.name, (newName, previousName) => {
151
+ slots.set(newName, slot);
152
+ slots.delete(previousName);
153
+ });
154
+ logger.debug("Slot added", {
107
155
  slot,
108
- slots: Array.from(slots)
156
+ slots: Array.from(slots.values())
109
157
  });
110
- (_a2 = context.events) == null ? void 0 : _a2.removeSlot.dispatch(slot);
111
- (_b2 = context.events) == null ? void 0 : _b2.changeSlots.dispatch(Array.from(slots.values()));
158
+ (_a = context.events) == null ? void 0 : _a.addSlot.dispatch(slot);
159
+ return slot;
112
160
  }
113
- slots.set(slot.getName(), slot);
114
- function onNameChange(newName, previousName) {
115
- var _a2;
116
- slots.set(newName, slot);
117
- slots.delete(previousName);
118
- (_a2 = context.events) == null ? void 0 : _a2.changeSlots.dispatch(Array.from(slots.values()));
161
+ async function findDomSlots$1() {
162
+ const domSlots = await findDomSlots(
163
+ context
164
+ );
165
+ for (const slot of domSlots)
166
+ slots.set(slot.name.value, slot);
167
+ return domSlots;
119
168
  }
120
- logger.debug("Slot added", {
121
- slot,
122
- slots: Array.from(slots.values())
123
- });
124
- (_a = context.events) == null ? void 0 : _a.addSlot.dispatch(slot);
125
- (_b = context.events) == null ? void 0 : _b.changeSlots.dispatch(Array.from(slots.values()));
126
- return slot;
127
- }
128
- async function findDomSlots$1() {
129
- var _a;
130
- const domSlots = await findDomSlots(
131
- context
132
- );
133
- for (const slot of domSlots) {
134
- slots.set(slot.getName(), slot);
135
- (_a = context.events) == null ? void 0 : _a.changeSlots.dispatch(Array.from(slots.values()));
169
+ function get(name) {
170
+ return slots.get(name);
136
171
  }
137
- return domSlots;
138
- }
139
- function get(name) {
140
- return slots.get(name);
141
- }
142
- function dispose() {
143
- var _a;
144
- for (const slot of slots.values())
145
- slot.dispose();
146
- slots.clear();
147
- (_a = context.events) == null ? void 0 : _a.changeSlots.dispatch(Array.from(slots.values()));
148
- }
149
- return {
150
- getAll,
151
- add,
152
- findDomSlots: findDomSlots$1,
153
- get,
154
- dispose
155
- };
172
+ function dispose() {
173
+ for (const slot of slots.values())
174
+ slot.dispose();
175
+ slots.clear();
176
+ scope.stop();
177
+ }
178
+ for (const options of initialSlots) {
179
+ add({
180
+ ...options,
181
+ lazyLoading: false
182
+ });
183
+ }
184
+ return {
185
+ getAll,
186
+ add,
187
+ findDomSlots: findDomSlots$1,
188
+ get,
189
+ dispose
190
+ };
191
+ });
156
192
  }
157
193
  function onTcfConsentChange(callback) {
158
194
  var _a;
@@ -272,7 +308,7 @@ const logger = createLogger({
272
308
  scope: "Adhese SDK"
273
309
  });
274
310
  function createParameters(options, queryDetector) {
275
- const parameters = new MapWithEvents();
311
+ const parameters = /* @__PURE__ */ new Map();
276
312
  if (options.logReferrer)
277
313
  parameters.set("re", btoa(document.referrer));
278
314
  if (options.logUrl)
@@ -299,230 +335,231 @@ function setupLogging(mergedOptions) {
299
335
  function isPreviewMode() {
300
336
  return window.location.search.includes("adhesePreviewCreativeId");
301
337
  }
302
- class MapWithEvents extends Map {
303
- constructor() {
304
- super(...arguments);
305
- __publicField(this, "listeners", /* @__PURE__ */ new Set());
338
+ function createHook({
339
+ onRun,
340
+ onAdd
341
+ }) {
342
+ const callbacks = /* @__PURE__ */ new Set();
343
+ function run() {
344
+ for (const callback of callbacks)
345
+ callback();
346
+ onRun == null ? void 0 : onRun();
306
347
  }
307
- addEventListener(listener) {
308
- this.listeners.add(listener);
348
+ function add(callback) {
349
+ callbacks.add(callback);
350
+ onAdd == null ? void 0 : onAdd();
309
351
  }
310
- removeEventListener(listener) {
311
- this.listeners.delete(listener);
352
+ return [run, add];
353
+ }
354
+ let resolveOnInitPromise = () => {
355
+ };
356
+ let isInit = false;
357
+ new Promise((resolve) => {
358
+ resolveOnInitPromise = resolve;
359
+ });
360
+ const [runOnInit, onInit] = createHook({
361
+ onRun() {
362
+ isInit = true;
363
+ resolveOnInitPromise();
364
+ logger.debug("Initialization completed");
365
+ },
366
+ onAdd() {
367
+ if (isInit)
368
+ runOnInit();
312
369
  }
313
- set(key, value) {
314
- const set = super.set(key, value);
315
- this.listeners.forEach((listener) => {
316
- listener();
370
+ });
371
+ function createAdhese(options) {
372
+ const scope = runtimeCore.effectScope();
373
+ return scope.run(() => {
374
+ const mergedOptions = {
375
+ host: `https://ads-${options.account}.adhese.com`,
376
+ poolHost: `https://pool-${options.account}.adhese.com`,
377
+ location: "homepage",
378
+ requestType: "POST",
379
+ debug: false,
380
+ initialSlots: [],
381
+ findDomSlotsOnLoad: false,
382
+ consent: false,
383
+ logReferrer: true,
384
+ logUrl: true,
385
+ eagerRendering: false,
386
+ viewabilityTracking: true,
387
+ ...options
388
+ };
389
+ setupLogging(mergedOptions);
390
+ const context = runtimeCore.reactive({
391
+ location: mergedOptions.location,
392
+ consent: mergedOptions.consent,
393
+ debug: mergedOptions.debug,
394
+ getAll,
395
+ get,
396
+ options: mergedOptions,
397
+ logger
317
398
  });
318
- return set;
319
- }
320
- clear() {
321
- super.clear();
322
- this.listeners.forEach((listener) => {
323
- listener();
399
+ context.events = createEventManager();
400
+ function getLocation() {
401
+ return context.location;
402
+ }
403
+ function setLocation(newLocation) {
404
+ var _a;
405
+ context.location = newLocation;
406
+ (_a = context.events) == null ? void 0 : _a.locationChange.dispatch(newLocation);
407
+ }
408
+ const queryDetector = createQueryDetector({
409
+ onChange: onQueryChange,
410
+ queries: mergedOptions.queries
324
411
  });
325
- }
326
- delete(key) {
327
- const deleted = super.delete(key);
328
- this.listeners.forEach((listener) => {
329
- listener();
412
+ context.parameters = createParameters(mergedOptions, queryDetector);
413
+ runtimeCore.watch(
414
+ context.parameters,
415
+ onParametersChange,
416
+ {
417
+ deep: true,
418
+ immediate: true
419
+ }
420
+ );
421
+ function onParametersChange() {
422
+ var _a;
423
+ if (context.parameters)
424
+ (_a = context.events) == null ? void 0 : _a.parametersChange.dispatch(context.parameters);
425
+ }
426
+ async function onQueryChange() {
427
+ var _a, _b;
428
+ const query = queryDetector.getQuery();
429
+ (_a = context.parameters) == null ? void 0 : _a.set("dt", query);
430
+ (_b = context.parameters) == null ? void 0 : _b.set("br", query);
431
+ await fetchAndRenderAllSlots();
432
+ }
433
+ function getConsent() {
434
+ return context.consent;
435
+ }
436
+ function setConsent(newConsent) {
437
+ var _a, _b;
438
+ (_a = context.parameters) == null ? void 0 : _a.set("tl", newConsent ? "all" : "none");
439
+ context.consent = newConsent;
440
+ (_b = context.events) == null ? void 0 : _b.consentChange.dispatch(newConsent);
441
+ }
442
+ const slotManager = createSlotManager({
443
+ initialSlots: mergedOptions.initialSlots,
444
+ context
330
445
  });
331
- return deleted;
332
- }
333
- /**
334
- * Remove all listeners and clear the map.
335
- */
336
- dispose() {
337
- this.listeners.clear();
338
- super.clear();
339
- }
340
- }
341
- async function createAdhese(options) {
342
- var _a;
343
- const mergedOptions = {
344
- host: `https://ads-${options.account}.adhese.com`,
345
- poolHost: `https://pool-${options.account}.adhese.com`,
346
- location: "homepage",
347
- requestType: "POST",
348
- debug: false,
349
- initialSlots: [],
350
- findDomSlotsOnLoad: false,
351
- consent: false,
352
- logReferrer: true,
353
- logUrl: true,
354
- eagerRendering: false,
355
- viewabilityTracking: true,
356
- ...options
357
- };
358
- setupLogging(mergedOptions);
359
- const context = new Proxy({
360
- location: mergedOptions.location,
361
- consent: mergedOptions.consent,
362
- debug: mergedOptions.debug,
363
- getAll,
364
- get,
365
- options: mergedOptions,
366
- logger
367
- }, {});
368
- context.events = createEventManager();
369
- function getLocation() {
370
- return context.location;
371
- }
372
- function setLocation(newLocation) {
373
- var _a2;
374
- context.location = newLocation;
375
- (_a2 = context.events) == null ? void 0 : _a2.locationChange.dispatch(newLocation);
376
- }
377
- const queryDetector = createQueryDetector({
378
- onChange: onQueryChange,
379
- queries: mergedOptions.queries
380
- });
381
- context.parameters = createParameters(mergedOptions, queryDetector);
382
- context.parameters.addEventListener(onParametersChange);
383
- let unmountDevtools;
384
- if (mergedOptions.debug || window.location.search.includes("adhese_debug=true") || isPreviewMode()) {
385
- unmountDevtools = await sdkDevtools.createDevtools(context);
386
- (_a = context.events) == null ? void 0 : _a.debugChange.dispatch(true);
387
- }
388
- function onParametersChange() {
389
- var _a2;
390
- if (context.parameters)
391
- (_a2 = context.events) == null ? void 0 : _a2.parametersChange.dispatch(context.parameters);
392
- }
393
- async function onQueryChange() {
394
- var _a2, _b;
395
- const query = queryDetector.getQuery();
396
- (_a2 = context.parameters) == null ? void 0 : _a2.set("dt", query);
397
- (_b = context.parameters) == null ? void 0 : _b.set("br", query);
398
- await fetchAndRenderAllSlots();
399
- }
400
- function getConsent() {
401
- return context.consent;
402
- }
403
- function setConsent(newConsent) {
404
- var _a2, _b;
405
- (_a2 = context.parameters) == null ? void 0 : _a2.set("tl", newConsent ? "all" : "none");
406
- context.consent = newConsent;
407
- (_b = context.events) == null ? void 0 : _b.consentChange.dispatch(newConsent);
408
- }
409
- const slotManager = await createSlotManager({
410
- initialSlots: mergedOptions.initialSlots,
411
- context
412
- });
413
- function getAll() {
414
- return slotManager.getAll();
415
- }
416
- function get(name) {
417
- return slotManager.get(name);
418
- }
419
- async function addSlot(slotOptions) {
420
- const slot = await slotManager.add(slotOptions);
421
- if (!slot.lazyLoading) {
422
- const ad = await requestAd({
423
- slot,
424
- host: mergedOptions.host,
425
- parameters: context.parameters,
426
- account: mergedOptions.account,
446
+ function getAll() {
447
+ return slotManager.getAll() ?? [];
448
+ }
449
+ function get(name) {
450
+ return slotManager.get(name);
451
+ }
452
+ async function addSlot(slotOptions) {
453
+ if (!slotManager)
454
+ throw new Error("Slot manager not initialized");
455
+ const slot = slotManager.add(slotOptions);
456
+ if (!slot.lazyLoading) {
457
+ slot.ad.value = await requestAd({
458
+ slot,
459
+ context
460
+ });
461
+ }
462
+ return slot;
463
+ }
464
+ async function findDomSlots2() {
465
+ const domSlots = (await slotManager.findDomSlots() ?? []).filter((slot) => !slot.lazyLoading);
466
+ if (domSlots.length <= 0)
467
+ return [];
468
+ const ads = await requestAds({
469
+ slots: domSlots,
427
470
  context
428
471
  });
429
- await slot.setAd(ad);
472
+ for (const ad of ads) {
473
+ const slot = slotManager.get(ad.slotName);
474
+ if (slot)
475
+ slot.ad.value = ad;
476
+ }
477
+ return domSlots;
430
478
  }
431
- return slot;
432
- }
433
- async function findDomSlots2() {
434
- const domSlots = (await slotManager.findDomSlots()).filter((slot) => !slot.lazyLoading);
435
- const ads = await requestAds({
436
- host: mergedOptions.host,
437
- slots: domSlots,
438
- method: mergedOptions.requestType,
439
- account: mergedOptions.account,
440
- parameters: context.parameters,
441
- context
479
+ let unmountDevtools;
480
+ async function toggleDebug() {
481
+ var _a, _b;
482
+ context.debug = !context.debug;
483
+ if (context.debug && !unmountDevtools) {
484
+ unmountDevtools = await sdkDevtools.createDevtools(context);
485
+ logger.setMinLogLevelThreshold("debug");
486
+ logger.debug("Debug mode enabled");
487
+ (_a = context.events) == null ? void 0 : _a.debugChange.dispatch(true);
488
+ } else {
489
+ logger.debug("Debug mode disabled");
490
+ unmountDevtools == null ? void 0 : unmountDevtools();
491
+ unmountDevtools = void 0;
492
+ logger.setMinLogLevelThreshold("info");
493
+ (_b = context.events) == null ? void 0 : _b.debugChange.dispatch(false);
494
+ }
495
+ return context.debug;
496
+ }
497
+ async function fetchAndRenderAllSlots() {
498
+ const slots = (slotManager.getAll() ?? []).filter((slot) => !slot.lazyLoading);
499
+ if (slots.length === 0)
500
+ return;
501
+ const ads = await requestAds({
502
+ slots,
503
+ context
504
+ });
505
+ for (const ad of ads) {
506
+ const slot = slotManager.get(ad.slotName);
507
+ if (slot)
508
+ slot.ad.value = ad;
509
+ }
510
+ }
511
+ const disposeOnTcfConsentChange = onTcfConsentChange(async (data) => {
512
+ var _a, _b;
513
+ if (!data.tcString)
514
+ return;
515
+ logger.debug("TCF v2 consent data received", {
516
+ data
517
+ });
518
+ (_a = context.parameters) == null ? void 0 : _a.set("xt", data.tcString);
519
+ (_b = context.parameters) == null ? void 0 : _b.delete("tl");
520
+ await fetchAndRenderAllSlots();
442
521
  });
443
- await Promise.allSettled(ads.map((ad) => {
444
- var _a2;
445
- return (_a2 = slotManager.get(ad.slotName)) == null ? void 0 : _a2.setAd(ad);
446
- }));
447
- return domSlots;
448
- }
449
- async function toggleDebug() {
450
- var _a2, _b;
451
- context.debug = !context.debug;
452
- if (context.debug && !unmountDevtools) {
453
- unmountDevtools = await sdkDevtools.createDevtools(context);
454
- logger.setMinLogLevelThreshold("debug");
455
- logger.debug("Debug mode enabled");
456
- (_a2 = context.events) == null ? void 0 : _a2.debugChange.dispatch(true);
457
- } else {
458
- logger.debug("Debug mode disabled");
522
+ function dispose() {
523
+ var _a, _b;
459
524
  unmountDevtools == null ? void 0 : unmountDevtools();
460
- unmountDevtools = void 0;
461
- logger.setMinLogLevelThreshold("info");
462
- (_b = context.events) == null ? void 0 : _b.debugChange.dispatch(false);
525
+ queryDetector.dispose();
526
+ slotManager.dispose();
527
+ queryDetector.dispose();
528
+ disposeOnTcfConsentChange();
529
+ (_a = context.parameters) == null ? void 0 : _a.clear();
530
+ logger.resetLogs();
531
+ (_b = context.events) == null ? void 0 : _b.dispose();
532
+ logger.info("Adhese instance disposed");
533
+ scope.stop();
463
534
  }
464
- return context.debug;
465
- }
466
- async function fetchAndRenderAllSlots() {
467
- const slots = slotManager.getAll().filter((slot) => !slot.lazyLoading);
468
- if (slots.length === 0)
469
- return;
470
- const ads = await requestAds({
471
- host: mergedOptions.host,
472
- slots,
473
- method: mergedOptions.requestType,
474
- account: mergedOptions.account,
535
+ onInit(async () => {
536
+ var _a;
537
+ if ((slotManager.getAll().length ?? 0) > 0)
538
+ await fetchAndRenderAllSlots().catch(logger.error);
539
+ if (mergedOptions.findDomSlotsOnLoad)
540
+ await findDomSlots2();
541
+ if (mergedOptions.debug || window.location.search.includes("adhese_debug=true") || isPreviewMode()) {
542
+ unmountDevtools = await sdkDevtools.createDevtools(context);
543
+ (_a = context.events) == null ? void 0 : _a.debugChange.dispatch(true);
544
+ }
545
+ });
546
+ runOnInit();
547
+ return {
548
+ ...mergedOptions,
549
+ ...slotManager,
475
550
  parameters: context.parameters,
551
+ events: context.events,
552
+ getLocation,
553
+ setLocation,
554
+ getConsent,
555
+ setConsent,
556
+ addSlot,
557
+ findDomSlots: findDomSlots2,
558
+ dispose,
559
+ toggleDebug,
476
560
  context
477
- });
478
- await Promise.allSettled(ads.map((ad) => {
479
- var _a2;
480
- return (_a2 = slotManager.get(ad.slotName)) == null ? void 0 : _a2.setAd(ad);
481
- }));
482
- }
483
- const disposeOnTcfConsentChange = onTcfConsentChange(async (data) => {
484
- var _a2, _b;
485
- if (!data.tcString)
486
- return;
487
- logger.debug("TCF v2 consent data received", {
488
- data
489
- });
490
- (_a2 = context.parameters) == null ? void 0 : _a2.set("xt", data.tcString);
491
- (_b = context.parameters) == null ? void 0 : _b.delete("tl");
492
- await fetchAndRenderAllSlots();
561
+ };
493
562
  });
494
- if (slotManager.getAll().length > 0)
495
- await fetchAndRenderAllSlots().catch(logger.error);
496
- function dispose() {
497
- var _a2, _b, _c;
498
- queryDetector.dispose();
499
- slotManager.dispose();
500
- queryDetector.dispose();
501
- disposeOnTcfConsentChange();
502
- (_a2 = context.parameters) == null ? void 0 : _a2.dispose();
503
- (_b = context.parameters) == null ? void 0 : _b.clear();
504
- logger.resetLogs();
505
- (_c = context.events) == null ? void 0 : _c.dispose();
506
- unmountDevtools == null ? void 0 : unmountDevtools();
507
- logger.info("Adhese instance disposed");
508
- }
509
- if (mergedOptions.findDomSlotsOnLoad)
510
- await slotManager.findDomSlots();
511
- return {
512
- ...mergedOptions,
513
- ...slotManager,
514
- parameters: context.parameters,
515
- events: context.events,
516
- getLocation,
517
- setLocation,
518
- getConsent,
519
- setConsent,
520
- addSlot,
521
- findDomSlots: findDomSlots2,
522
- dispose,
523
- toggleDebug,
524
- context
525
- };
526
563
  }
527
564
  function addTrackingPixel(url) {
528
565
  const img = document.createElement("img");
@@ -535,118 +572,7 @@ function addTrackingPixel(url) {
535
572
  img.style.top = "0";
536
573
  return document.body.appendChild(img);
537
574
  }
538
- function renderIframe(ad, element) {
539
- const iframe = document.createElement("iframe");
540
- iframe.srcdoc = `
541
- <!DOCTYPE html>
542
- <html>
543
- <head>
544
- <style>
545
- body {
546
- margin: 0;
547
- padding: 0;
548
- overflow: hidden;
549
- }
550
- </style>
551
- </head>
552
- <body>
553
- ${ad.tag}
554
- </body>
555
- `.replaceAll(/\s+/g, " ").trim();
556
- iframe.style.border = "none";
557
- iframe.style.width = ad.width ? `${ad.width}px` : "100%";
558
- iframe.style.height = ad.height ? `${ad.height}px` : "100%";
559
- element.replaceChildren(iframe);
560
- }
561
- function renderInline(ad, element) {
562
- element.style.width = ad.width ? `${ad.width}px` : "100%";
563
- element.style.height = ad.height ? `${ad.height}px` : "100%";
564
- element.innerHTML = ad.tag;
565
- }
566
- const renderFunctions = {
567
- iframe: renderIframe,
568
- inline: renderInline
569
- };
570
- async function createSlot(options) {
571
- var _a;
572
- const {
573
- containingElement,
574
- slot,
575
- context,
576
- renderMode = "iframe"
577
- } = options;
578
- await waitForDomLoad();
579
- const parameters = new Map(Object.entries(options.parameters ?? {}));
580
- let format;
581
- let queryDetector = null;
582
- if (typeof options.format === "string") {
583
- format = options.format;
584
- } else {
585
- queryDetector = createQueryDetector({
586
- onChange: setFormat,
587
- queries: Object.fromEntries(options.format.map((item) => [item.format, item.query]))
588
- });
589
- format = queryDetector.getQuery();
590
- }
591
- async function setFormat(newFormat) {
592
- var _a2;
593
- const oldName = getName();
594
- format = newFormat;
595
- (_a2 = options.onNameChange) == null ? void 0 : _a2.call(options, getName(), oldName);
596
- const newAd = await requestAd({
597
- slot: {
598
- getName,
599
- parameters
600
- },
601
- account: context.options.account,
602
- host: context.options.host,
603
- parameters: context.parameters,
604
- context
605
- });
606
- cleanElement();
607
- await setAd(newAd);
608
- }
609
- function getFormat() {
610
- return format;
611
- }
612
- let element = typeof containingElement === "string" || !containingElement ? document.querySelector(`.adunit[data-format="${format}"]#${containingElement}${slot ? `[data-slot="${slot}"]` : ""}`) : containingElement;
613
- function getElement() {
614
- if (renderMode === "iframe")
615
- return (element == null ? void 0 : element.querySelector("iframe")) ?? null;
616
- return (element == null ? void 0 : element.innerHTML) ? element.firstElementChild : null;
617
- }
618
- let impressionTrackingPixelElement = null;
619
- let viewabilityTrackingPixelElement = null;
620
- let isInViewport = false;
621
- let ad = null;
622
- function getAd() {
623
- return ad;
624
- }
625
- async function setAd(newAd) {
626
- var _a2, _b;
627
- ad = newAd;
628
- if (isInViewport || context.options.eagerRendering)
629
- await render(ad);
630
- if (element) {
631
- element.style.width = `${ad.width}px`;
632
- element.style.height = `${ad.height}px`;
633
- }
634
- await ((_b = context.events) == null ? void 0 : _b.changeSlots.dispatchAsync(Array.from(((_a2 = context.getAll) == null ? void 0 : _a2.call(context)) ?? [])));
635
- }
636
- const renderIntersectionObserver = new IntersectionObserver((entries) => {
637
- isInViewport = entries.some((entry) => entry.isIntersecting);
638
- if (isInViewport) {
639
- (async () => {
640
- if (!ad && options.lazyLoading)
641
- await render();
642
- else if (ad)
643
- await render(ad);
644
- })().catch(logger.error);
645
- }
646
- }, {
647
- rootMargin: ((_a = options.lazyLoadingOptions) == null ? void 0 : _a.rootMargin) ?? "200px",
648
- threshold: 0
649
- });
575
+ function useViewabilityObserver({ context, ad, name, element }) {
650
576
  let timeoutId = null;
651
577
  const {
652
578
  threshold,
@@ -658,17 +584,19 @@ async function createSlot(options) {
658
584
  rootMargin: "0px",
659
585
  ...context.options.viewabilityTrackingOptions
660
586
  };
587
+ const trackingPixel = runtimeCore.ref(null);
588
+ const isTracked = runtimeCore.computed(() => Boolean(trackingPixel.value));
661
589
  const viewabilityObserver = new IntersectionObserver(([entry]) => {
662
- if (context.options.viewabilityTracking && !viewabilityTrackingPixelElement && ad) {
590
+ if (context.options.viewabilityTracking && !trackingPixel.value && ad) {
663
591
  const ratio = lodashEs.round(entry.intersectionRatio, 1);
664
592
  if (ratio >= threshold && !timeoutId) {
665
593
  timeoutId = setTimeout(() => {
666
- var _a2, _b;
594
+ var _a, _b, _c;
667
595
  timeoutId = null;
668
- if (ad == null ? void 0 : ad.viewableImpressionCounter) {
669
- viewabilityTrackingPixelElement = addTrackingPixel(ad.viewableImpressionCounter);
670
- logger.debug(`Viewability tracking pixel fired for ${getName()}`);
671
- (_b = context.events) == null ? void 0 : _b.changeSlots.dispatch(Array.from(((_a2 = context.getAll) == null ? void 0 : _a2.call(context)) ?? []));
596
+ if ((_a = ad.value) == null ? void 0 : _a.viewableImpressionCounter) {
597
+ trackingPixel.value = addTrackingPixel(ad.value.viewableImpressionCounter);
598
+ logger.debug(`Viewability tracking pixel fired for ${name.value}`);
599
+ (_c = context.events) == null ? void 0 : _c.changeSlots.dispatch(Array.from(((_b = context.getAll) == null ? void 0 : _b.call(context)) ?? []));
672
600
  }
673
601
  }, duration);
674
602
  } else if (ratio < threshold && timeoutId) {
@@ -680,90 +608,218 @@ async function createSlot(options) {
680
608
  rootMargin,
681
609
  threshold: Array.from({ length: 11 }, (_, i) => i * 0.1)
682
610
  });
683
- if (element && context.options.viewabilityTracking)
684
- viewabilityObserver.observe(element);
685
- if (element)
686
- renderIntersectionObserver.observe(element);
687
- async function render(adToRender) {
688
- var _a2, _b;
689
- await waitForDomLoad();
690
- ad = adToRender ?? ad ?? await requestAd({
691
- slot: {
692
- getName,
693
- parameters
694
- },
695
- account: context.options.account,
696
- host: context.options.host,
697
- parameters: context.parameters,
698
- context
699
- });
700
- if (!element) {
701
- const error = `Could not create slot for format ${format}. No element found.`;
702
- logger.error(error, options);
703
- throw new Error(error);
704
- }
705
- if (context.debug)
706
- element.style.position = "relative";
707
- renderFunctions[renderMode](ad, element);
708
- if ((ad == null ? void 0 : ad.impressionCounter) && !impressionTrackingPixelElement) {
709
- impressionTrackingPixelElement = addTrackingPixel(ad.impressionCounter);
710
- logger.debug(`Impression tracking pixel fired for ${getName()}`);
711
- }
712
- logger.debug("Slot rendered", {
713
- renderedElement: element,
714
- location: context.location,
715
- format,
716
- containingElement
717
- });
718
- renderIntersectionObserver.disconnect();
719
- await ((_b = context.events) == null ? void 0 : _b.changeSlots.dispatchAsync(Array.from(((_a2 = context.getAll) == null ? void 0 : _a2.call(context)) ?? [])));
720
- return element;
721
- }
722
- function cleanElement() {
723
- if (!element)
724
- return;
725
- element.innerHTML = "";
726
- element.style.position = "";
727
- element.style.width = "";
728
- element.style.height = "";
729
- }
730
- function getName() {
731
- return `${context.location}${slot ? `${slot}` : ""}-${format}`;
611
+ function observe(newElement, oldElement) {
612
+ if (oldElement)
613
+ viewabilityObserver.unobserve(oldElement);
614
+ if (newElement && context.options.viewabilityTracking)
615
+ viewabilityObserver.observe(newElement);
616
+ return () => {
617
+ if (newElement)
618
+ viewabilityObserver.unobserve(newElement);
619
+ };
732
620
  }
733
- function dispose() {
734
- var _a2;
735
- cleanElement();
736
- impressionTrackingPixelElement == null ? void 0 : impressionTrackingPixelElement.remove();
737
- viewabilityTrackingPixelElement == null ? void 0 : viewabilityTrackingPixelElement.remove();
738
- element = null;
739
- ad = null;
740
- renderIntersectionObserver.disconnect();
621
+ runtimeCore.watch(element, observe);
622
+ observe(element.value);
623
+ return [isTracked, () => {
624
+ var _a;
625
+ (_a = trackingPixel.value) == null ? void 0 : _a.remove();
741
626
  viewabilityObserver.disconnect();
742
- (_a2 = options.onDispose) == null ? void 0 : _a2.call(options);
743
- queryDetector == null ? void 0 : queryDetector.dispose();
744
- }
745
- function isViewabilityTracked() {
746
- return Boolean(viewabilityTrackingPixelElement);
747
- }
748
- function isImpressionTracked() {
749
- return Boolean(impressionTrackingPixelElement);
627
+ }];
628
+ }
629
+ function useRenderIntersectionObserver({ ad, options, element, render }) {
630
+ var _a;
631
+ const isInViewport = runtimeCore.ref(false);
632
+ const renderIntersectionObserver = new IntersectionObserver((entries) => {
633
+ isInViewport.value = entries.some((entry) => entry.isIntersecting);
634
+ if (isInViewport.value) {
635
+ (async () => {
636
+ if (!ad.value && options.lazyLoading)
637
+ await render();
638
+ await render(ad.value ?? void 0);
639
+ })().catch(logger.error);
640
+ }
641
+ }, {
642
+ rootMargin: ((_a = options.lazyLoadingOptions) == null ? void 0 : _a.rootMargin) ?? "200px",
643
+ threshold: 0
644
+ });
645
+ function observe(newElement, oldElement) {
646
+ if (oldElement)
647
+ renderIntersectionObserver.unobserve(oldElement);
648
+ if (newElement)
649
+ renderIntersectionObserver.observe(newElement);
650
+ return () => {
651
+ if (newElement)
652
+ renderIntersectionObserver.unobserve(newElement);
653
+ };
750
654
  }
751
- return {
752
- location: context.location,
753
- lazyLoading: options.lazyLoading ?? false,
754
- slot,
755
- parameters,
756
- setFormat,
757
- getFormat,
758
- render,
759
- getElement,
760
- getName,
761
- getAd,
762
- setAd,
763
- isViewabilityTracked,
764
- isImpressionTracked,
765
- dispose
766
- };
655
+ runtimeCore.watch(element, observe);
656
+ observe(element.value);
657
+ return [isInViewport, () => {
658
+ renderIntersectionObserver.disconnect();
659
+ }];
660
+ }
661
+ const renderFunctions = {
662
+ iframe: renderIframe,
663
+ inline: renderInline
664
+ };
665
+ function createSlot(options) {
666
+ const scope = runtimeCore.effectScope();
667
+ return scope.run(() => {
668
+ const {
669
+ containingElement,
670
+ slot,
671
+ context,
672
+ renderMode = "iframe"
673
+ } = options;
674
+ const parameters = runtimeCore.reactive(new Map(Object.entries(options.parameters ?? {})));
675
+ let queryDetector = null;
676
+ if (typeof options.format !== "string") {
677
+ queryDetector = createQueryDetector({
678
+ onChange: onQueryChange,
679
+ queries: Object.fromEntries(options.format.map((item) => [item.format, item.query]))
680
+ });
681
+ }
682
+ const format = runtimeCore.ref(queryDetector ? queryDetector.getQuery() : options.format);
683
+ function onQueryChange(newFormat) {
684
+ format.value = newFormat;
685
+ }
686
+ const ad = runtimeCore.ref(null);
687
+ const name = runtimeCore.computed(() => generateName(context.location, format.value, slot));
688
+ runtimeCore.watch(name, async (newName, oldName) => {
689
+ var _a;
690
+ if (newName === oldName)
691
+ return;
692
+ (_a = options.onNameChange) == null ? void 0 : _a.call(options, newName, oldName);
693
+ const newAd = await requestAd({
694
+ slot: {
695
+ name: newName,
696
+ parameters
697
+ },
698
+ context
699
+ });
700
+ cleanElement();
701
+ ad.value = newAd;
702
+ });
703
+ const isDomLoaded = useDomLoaded();
704
+ const element = runtimeCore.computed(
705
+ () => {
706
+ if (!(typeof containingElement === "string" || !containingElement))
707
+ return containingElement;
708
+ if (!isDomLoaded.value)
709
+ return null;
710
+ return document.querySelector(`.adunit[data-format="${format.value}"]#${containingElement}${slot ? `[data-slot="${slot}"]` : ""}`);
711
+ }
712
+ );
713
+ function getElement() {
714
+ var _a, _b;
715
+ if (renderMode === "iframe")
716
+ return ((_a = element.value) == null ? void 0 : _a.querySelector("iframe")) ?? null;
717
+ return ((_b = element.value) == null ? void 0 : _b.innerHTML) ? element.value.firstElementChild : null;
718
+ }
719
+ const [isInViewport, disposeRenderIntersectionObserver] = useRenderIntersectionObserver({
720
+ ad,
721
+ options,
722
+ element,
723
+ render
724
+ });
725
+ runtimeCore.watch([ad, isInViewport], async ([newAd, newIsInViewport], [oldAd]) => {
726
+ var _a, _b;
727
+ if (!newAd || lodashEs.isEqual(newAd, oldAd))
728
+ return;
729
+ if (newIsInViewport || context.options.eagerRendering)
730
+ await render(newAd);
731
+ if (element.value) {
732
+ element.value.style.width = `${newAd.width}px`;
733
+ element.value.style.height = `${newAd.height}px`;
734
+ }
735
+ (_b = context.events) == null ? void 0 : _b.changeSlots.dispatch(Array.from(((_a = context.getAll) == null ? void 0 : _a.call(context)) ?? []));
736
+ });
737
+ const [
738
+ isViewabilityTracked,
739
+ disposeViewabilityObserver
740
+ ] = useViewabilityObserver({
741
+ context,
742
+ ad,
743
+ name,
744
+ element
745
+ });
746
+ const impressionTrackingPixelElement = runtimeCore.ref(null);
747
+ const isImpressionTracked = runtimeCore.computed(() => Boolean(impressionTrackingPixelElement.value));
748
+ async function render(adToRender) {
749
+ var _a, _b, _c, _d;
750
+ await waitForDomLoad();
751
+ ad.value = adToRender ?? ad.value ?? await requestAd({
752
+ slot: {
753
+ name,
754
+ parameters
755
+ },
756
+ context
757
+ });
758
+ ad.value = ((_a = options.onBeforeRender) == null ? void 0 : _a.call(options, ad.value)) ?? ad.value;
759
+ if (!element.value) {
760
+ const error = `Could not create slot for format ${format.value}. No element found.`;
761
+ logger.error(error, options);
762
+ throw new Error(error);
763
+ }
764
+ if (context.debug)
765
+ element.value.style.position = "relative";
766
+ renderFunctions[renderMode](ad.value, element.value);
767
+ if (((_b = ad.value) == null ? void 0 : _b.impressionCounter) && !impressionTrackingPixelElement.value) {
768
+ impressionTrackingPixelElement.value = addTrackingPixel((_c = ad.value) == null ? void 0 : _c.impressionCounter);
769
+ logger.debug(`Impression tracking pixel fired for ${name.value}`);
770
+ }
771
+ logger.debug("Slot rendered", {
772
+ renderedElement: element,
773
+ location: context.location,
774
+ format,
775
+ containingElement
776
+ });
777
+ (_d = options.onRender) == null ? void 0 : _d.call(options, element.value);
778
+ disposeRenderIntersectionObserver();
779
+ return element.value;
780
+ }
781
+ function cleanElement() {
782
+ if (!element.value)
783
+ return;
784
+ element.value.innerHTML = "";
785
+ element.value.style.position = "";
786
+ element.value.style.width = "";
787
+ element.value.style.height = "";
788
+ }
789
+ function dispose() {
790
+ var _a, _b;
791
+ cleanElement();
792
+ (_a = impressionTrackingPixelElement.value) == null ? void 0 : _a.remove();
793
+ ad.value = null;
794
+ disposeRenderIntersectionObserver();
795
+ disposeViewabilityObserver();
796
+ (_b = options.onDispose) == null ? void 0 : _b.call(options);
797
+ queryDetector == null ? void 0 : queryDetector.dispose();
798
+ scope.stop();
799
+ }
800
+ return {
801
+ location: context.location,
802
+ lazyLoading: options.lazyLoading ?? false,
803
+ slot,
804
+ parameters,
805
+ format,
806
+ name,
807
+ ad,
808
+ isViewabilityTracked,
809
+ isImpressionTracked,
810
+ render,
811
+ getElement,
812
+ dispose
813
+ };
814
+ });
815
+ }
816
+ function useDomLoaded() {
817
+ const isDomLoaded = runtimeCore.ref(false);
818
+ onInit(async () => {
819
+ await waitForDomLoad();
820
+ isDomLoaded.value = true;
821
+ });
822
+ return isDomLoaded;
767
823
  }
768
824
  const numberLike = zod.union([zod.coerce.string().regex(/^\d+$/), zod.literal("")]).transform((value) => value === "" ? void 0 : Number(value));
769
825
  const booleanLike = zod.union([zod.coerce.boolean(), zod.literal("")]);
@@ -782,13 +838,48 @@ const dateLike = zod.union([zod.coerce.string(), zod.literal("")]).transform((va
782
838
  return void 0;
783
839
  return date;
784
840
  });
785
- const baseAdResponseScheme = zod.object({
841
+ const cssValueLike = zod.union([zod.coerce.string(), zod.literal(""), zod.number()]).transform((value) => {
842
+ if (value === "" || value === 0 || value === "0")
843
+ return void 0;
844
+ if (numberLike.parse(value))
845
+ return `${numberLike.parse(value)}px`;
846
+ return String(value);
847
+ });
848
+ const isJson = zod.string().transform((value, { addIssue }) => {
849
+ try {
850
+ return JSON.parse(value.replaceAll("'", '"'));
851
+ } catch (error) {
852
+ addIssue({
853
+ code: zod.ZodIssueCode.custom,
854
+ message: `Invalid JSON: ${error.message}`
855
+ });
856
+ return zod.NEVER;
857
+ }
858
+ });
859
+ const isHtmlString = zod.string().transform((value, { addIssue }) => {
860
+ var _a;
861
+ const htmlParser = new DOMParser();
862
+ try {
863
+ const html = htmlParser.parseFromString(value, "text/html");
864
+ if (((_a = html.body) == null ? void 0 : _a.children.length) === 0)
865
+ throw new Error("Invalid HTML");
866
+ return value;
867
+ } catch (error) {
868
+ addIssue({
869
+ code: zod.ZodIssueCode.custom,
870
+ message: error.message
871
+ });
872
+ return zod.NEVER;
873
+ }
874
+ });
875
+ const isJsonOrHtmlString = zod.union([isJson, isHtmlString]);
876
+ const isJsonOrHtmlOptionalString = zod.union([zod.coerce.string(), isJsonOrHtmlString]).transform((value) => {
877
+ if (value === "")
878
+ return void 0;
879
+ return value;
880
+ }).optional();
881
+ const baseSchema = zod.object({
786
882
  adDuration: numberLike.optional(),
787
- adDuration2nd: numberLike.optional(),
788
- adDuration3rd: numberLike.optional(),
789
- adDuration4th: numberLike.optional(),
790
- adDuration5th: numberLike.optional(),
791
- adDuration6th: numberLike.optional(),
792
883
  adFormat: zod.string().optional(),
793
884
  adType: zod.string(),
794
885
  additionalCreativeTracker: urlLike.optional(),
@@ -800,34 +891,27 @@ const baseAdResponseScheme = zod.object({
800
891
  advertiserId: zod.string().optional(),
801
892
  altText: zod.string().optional(),
802
893
  auctionable: booleanLike.optional(),
803
- body: zod.string().optional(),
894
+ body: isJsonOrHtmlOptionalString,
804
895
  clickTag: urlLike.optional(),
805
896
  comment: zod.string().optional(),
806
897
  creativeName: zod.string().optional(),
807
898
  deliveryGroupId: zod.string().optional(),
808
899
  deliveryMultiples: zod.string().optional(),
809
- dm: zod.string().optional(),
810
900
  ext: zod.string().optional(),
811
901
  extension: zod.object({
812
902
  mediaType: zod.string(),
813
903
  prebid: zod.unknown().optional()
814
904
  }).optional(),
815
- extraField1: zod.string().optional(),
816
- extraField2: zod.string().optional(),
817
- height: numberLike.optional(),
818
- height3rd: numberLike.optional(),
819
- height4th: numberLike.optional(),
820
- height5th: numberLike.optional(),
821
- height6th: numberLike.optional(),
822
- heightLarge: numberLike.optional(),
905
+ height: cssValueLike.optional(),
823
906
  id: zod.string().optional(),
824
907
  impressionCounter: urlLike.optional(),
825
908
  libId: zod.string().optional(),
826
909
  orderId: zod.string().optional(),
827
910
  orderName: zod.string().optional(),
828
911
  orderProperty: zod.string().optional(),
829
- origin: zod.string().optional(),
912
+ origin: zod.union([zod.literal("JERLICIA"), zod.literal("DALE")]),
830
913
  originData: zod.unknown().optional(),
914
+ originInstance: zod.string().optional(),
831
915
  poolPath: urlLike.optional(),
832
916
  preview: booleanLike.optional(),
833
917
  priority: numberLike.optional(),
@@ -836,12 +920,7 @@ const baseAdResponseScheme = zod.object({
836
920
  slotID: zod.string(),
837
921
  slotName: zod.string(),
838
922
  swfSrc: urlLike.optional(),
839
- swfSrc2nd: zod.string().optional(),
840
- swfSrc3rd: zod.string().optional(),
841
- swfSrc4th: zod.string().optional(),
842
- swfSrc5th: zod.string().optional(),
843
- swfSrc6th: zod.string().optional(),
844
- tag: zod.string(),
923
+ tag: isJsonOrHtmlOptionalString,
845
924
  tagUrl: urlLike.optional(),
846
925
  timeStamp: dateLike.optional(),
847
926
  trackedImpressionCounter: urlLike.optional(),
@@ -849,14 +928,21 @@ const baseAdResponseScheme = zod.object({
849
928
  trackingUrl: urlLike.optional(),
850
929
  url: urlLike.optional(),
851
930
  viewableImpressionCounter: urlLike.optional(),
852
- width: numberLike.optional(),
853
- width3rd: numberLike.optional(),
854
- width4th: numberLike.optional(),
855
- width5th: numberLike.optional(),
856
- width6th: numberLike.optional(),
857
- widthLarge: numberLike.optional()
931
+ width: cssValueLike.optional(),
932
+ widthLarge: cssValueLike.optional()
858
933
  });
859
- const adResponseSchema = baseAdResponseScheme.extend({
934
+ const jerliciaSchema = zod.object({
935
+ origin: zod.literal("JERLICIA"),
936
+ tag: isJsonOrHtmlString
937
+ }).passthrough();
938
+ const daleSchema = zod.object({
939
+ origin: zod.literal("DALE"),
940
+ body: isJsonOrHtmlString
941
+ }).passthrough().transform(({ body, ...data }) => ({
942
+ ...data,
943
+ tag: body
944
+ }));
945
+ const adResponseSchema = baseSchema.extend({
860
946
  additionalCreatives: zod.lazy(() => zod.union([adResponseSchema.array(), zod.string()]).optional())
861
947
  });
862
948
  const adSchema = adResponseSchema.transform(({
@@ -871,6 +957,21 @@ const adSchema = adResponseSchema.transform(({
871
957
  additionalCreatives: Array.isArray(additionalCreatives) ? additionalCreatives.map((creative) => adSchema.parse(creative)) : additionalCreatives
872
958
  };
873
959
  });
960
+ function parseResponse(response) {
961
+ const schemaMap = {
962
+ /* eslint-disable ts/naming-convention */
963
+ JERLICIA: jerliciaSchema,
964
+ DALE: daleSchema
965
+ /* eslint-enable ts/naming-convention */
966
+ };
967
+ const preParsed = adResponseSchema.array().parse(response);
968
+ return preParsed.map((item) => {
969
+ const schema = schemaMap[item.origin];
970
+ if (!schema)
971
+ return adSchema.parse(item);
972
+ return schema.parse(item);
973
+ });
974
+ }
874
975
  async function requestPreviews(account) {
875
976
  const previewObjects = getPreviewObjects();
876
977
  const list = (await Promise.allSettled(previewObjects.filter((previewObject) => "adhesePreviewCreativeId" in previewObject).map(async (previewObject) => {
@@ -916,16 +1017,16 @@ function getPreviewObjects() {
916
1017
  return previewObjects;
917
1018
  }
918
1019
  function requestWithPost({
919
- host,
1020
+ context: { options: { host }, parameters },
920
1021
  ...options
921
1022
  }) {
922
1023
  const payload = {
923
1024
  ...options,
924
1025
  slots: options.slots.map((slot) => ({
925
- slotname: slot.getName(),
1026
+ slotname: runtimeCore.toValue(slot.name),
926
1027
  parameters: parseParameters(slot.parameters)
927
1028
  })),
928
- parameters: options.parameters && parseParameters(options.parameters)
1029
+ parameters: parameters && parseParameters(parameters)
929
1030
  };
930
1031
  return fetch(`${new URL(host).href}json`, {
931
1032
  method: "POST",
@@ -936,8 +1037,8 @@ function requestWithPost({
936
1037
  }
937
1038
  });
938
1039
  }
939
- async function requestWithGet(options) {
940
- return fetch(new URL(`${options.host}/json/sl${options.slots.map((slot) => slot.getName()).join("/sl")}`), {
1040
+ async function requestWithGet({ context, slots }) {
1041
+ return fetch(new URL(`${context.options.host}/json/sl${slots.map((slot) => runtimeCore.toValue(slot.name)).join("/sl")}`), {
941
1042
  method: "GET",
942
1043
  headers: {
943
1044
  // eslint-disable-next-line ts/naming-convention
@@ -953,23 +1054,19 @@ function parseParameters(parameters) {
953
1054
  return false;
954
1055
  }));
955
1056
  }
956
- async function requestAds({
957
- method = "POST",
958
- context,
959
- ...options
960
- }) {
961
- var _a, _b, _c, _d;
1057
+ async function requestAds(options) {
1058
+ var _a, _b, _c, _d, _e;
1059
+ const { context } = options;
962
1060
  try {
963
1061
  (_a = context.events) == null ? void 0 : _a.requestAd.dispatch({
964
1062
  ...options,
965
- context,
966
- method
1063
+ context
967
1064
  });
968
- const [response, previews] = await Promise.all([(method == null ? void 0 : method.toUpperCase()) === "POST" ? requestWithPost(options) : requestWithGet(options), requestPreviews(options.account)]);
1065
+ const [response, previews] = await Promise.all([((_b = context.options.requestType) == null ? void 0 : _b.toUpperCase()) === "POST" ? requestWithPost(options) : requestWithGet(options), requestPreviews(context.options.account)]);
969
1066
  logger.debug("Received response", response);
970
1067
  if (!response.ok)
971
1068
  throw new Error(`Failed to request ad: ${response.status} ${response.statusText}`);
972
- const result = adSchema.array().parse(await response.json());
1069
+ const result = parseResponse(await response.json());
973
1070
  logger.debug("Parsed ad", result);
974
1071
  if (previews.length > 0)
975
1072
  logger.info(`Found ${previews.length} ${previews.length === 1 ? "preview" : "previews"}. Replacing ads in response with preview items`, previews);
@@ -981,18 +1078,18 @@ async function requestAds({
981
1078
  };
982
1079
  });
983
1080
  if (matchedPreviews.length > 0)
984
- (_b = context.events) == null ? void 0 : _b.previewReceived.dispatch(matchedPreviews);
1081
+ (_c = context.events) == null ? void 0 : _c.previewReceived.dispatch(matchedPreviews);
985
1082
  const mergedResult = [
986
1083
  ...result.filter((ad) => !previews.some((preview) => preview.libId === ad.libId)),
987
1084
  ...matchedPreviews
988
1085
  ];
989
1086
  if (mergedResult.length === 0)
990
1087
  throw new Error("No ads found");
991
- (_c = context.events) == null ? void 0 : _c.responseReceived.dispatch(mergedResult);
1088
+ (_d = context.events) == null ? void 0 : _d.responseReceived.dispatch(mergedResult);
992
1089
  return mergedResult;
993
1090
  } catch (error) {
994
1091
  logger.error(String(error));
995
- (_d = context.events) == null ? void 0 : _d.requestError.dispatch(error);
1092
+ (_e = context.events) == null ? void 0 : _e.requestError.dispatch(error);
996
1093
  throw error;
997
1094
  }
998
1095
  }