@streamlayer/feature-gamification 1.19.1 → 1.20.1

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.
@@ -2,6 +2,7 @@ import { StreamLayerContext } from '@streamlayer/sdk-web-interfaces';
2
2
  import { type GamificationBackground } from '../background';
3
3
  import { getPromotionDetail } from '../queries';
4
4
  type AdvertisementData = Exclude<Awaited<ReturnType<typeof getPromotionDetail>>, undefined>;
5
+ type AdvertisementEvent = 'video-rendered' | `video-quartile-${25 | 50 | 75}` | 'muted' | 'unmuted' | 'replayed' | 'played' | 'ended' | 'banner-showed';
5
6
  export type Advertisement = {
6
7
  data?: AdvertisementData;
7
8
  externalAd?: {
@@ -13,11 +14,15 @@ export type Advertisement = {
13
14
  isViewed?: boolean;
14
15
  isOpened?: boolean;
15
16
  isPaused?: boolean;
17
+ isMuted?: boolean;
16
18
  hasNotification?: boolean;
17
19
  close?: () => void;
18
20
  togglePause?: (flag: boolean) => void;
19
21
  error?: string;
22
+ toggleMute?: (flag: boolean) => void;
20
23
  ctx?: Record<string, unknown>;
24
+ isEventFired?: (event: AdvertisementEvent) => boolean;
25
+ fireEvent?: (event: AdvertisementEvent) => void;
21
26
  };
22
27
  /**
23
28
  * @name Advertisement
@@ -26,6 +26,12 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
26
26
  const transport = instance.transport;
27
27
  const logger = createLogger('advertisement');
28
28
  const storage = new AdvertisementStorage();
29
+ const fireEvent = (id, event) => {
30
+ storage.fireEvent(id, event);
31
+ };
32
+ const isEventFired = (id, event) => {
33
+ return storage.isEventFired(id, event);
34
+ };
29
35
  const $store = createMapStore({});
30
36
  const $activeAdvertisement = $activePromotionId($slStreamId, transport);
31
37
  const open = (options) => {
@@ -35,15 +41,20 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
35
41
  if (!id) {
36
42
  return;
37
43
  }
38
- eventBus.emit('advertisement', {
39
- action: 'opened',
40
- payload: {
41
- id,
42
- type,
43
- hasBanner: adHasBanner(payload.data),
44
- openedFrom: options?.fromNotification ? 'notification' : 'auto',
45
- },
46
- });
44
+ const isOpened = $store.get()?.isOpened;
45
+ if (!isOpened) {
46
+ $store.setKey('isOpened', true);
47
+ // trigger POLLS_OPENED
48
+ eventBus.emit('advertisement', {
49
+ action: 'opened',
50
+ payload: {
51
+ id,
52
+ type,
53
+ hasBanner: adHasBanner(payload.data),
54
+ openedFrom: options?.fromNotification ? 'notification' : 'auto',
55
+ },
56
+ });
57
+ }
47
58
  if (options?.fromNotification) {
48
59
  $store.setKey('hasNotification', false);
49
60
  eventBus.emit('advertisement', {
@@ -65,6 +76,7 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
65
76
  logger.debug({ id }, 'markAsViewed: %o');
66
77
  storage.setShowed(id);
67
78
  $store.setKey('isOpened', true);
79
+ // skipped
68
80
  eventBus.emit('advertisement', {
69
81
  action: 'viewed',
70
82
  payload: {
@@ -89,12 +101,17 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
89
101
  hasNotification: response?.notification?.enabled === NotificationEnabled.NOTIFICATION_ENABLED,
90
102
  close: () => hide(response?.question.id),
91
103
  togglePause: (status) => pause(response?.question.id, status),
104
+ toggleMute: (status) => mute(response?.question.id, status),
92
105
  isViewed: response && !!storage.isViewed(response.question.id),
106
+ fireEvent: (event) => fireEvent(advertisementId, event),
107
+ isEventFired: (event) => isEventFired(advertisementId, event),
93
108
  }))
94
109
  .catch((error) => $store.set({
95
110
  loading: false,
96
111
  error,
97
112
  data: undefined,
113
+ fireEvent: () => { },
114
+ isEventFired: () => false,
98
115
  }));
99
116
  }
100
117
  else {
@@ -105,7 +122,10 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
105
122
  hasNotification: data?.notification?.enabled === NotificationEnabled.NOTIFICATION_ENABLED,
106
123
  close: () => hide(data.question.id),
107
124
  togglePause: (status) => pause(data.question.id, status),
125
+ toggleMute: (status) => mute(data.question.id, status),
108
126
  isViewed: !!storage.isViewed(data.question.id),
127
+ fireEvent: (event) => fireEvent(advertisementId, event),
128
+ isEventFired: (event) => isEventFired(advertisementId, event),
109
129
  });
110
130
  }
111
131
  };
@@ -115,8 +135,8 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
115
135
  return;
116
136
  }
117
137
  if (active.data?.promotion?.type === PromotionType.EXTERNAL_AD && !active?.externalAd) {
118
- if (active.data.promotion.adCampaigns?.gamOptions && active.data.promotion.adCampaigns?.gamBaseUrl) {
119
- const gamUrl = processGamAdvertisement(active.data.promotion.adCampaigns);
138
+ if (active.data.promotion.adCampaigns?.desktopWebSettings) {
139
+ const gamUrl = processGamAdvertisement(active.data.promotion.adCampaigns.desktopWebSettings);
120
140
  $store.setKey('externalAd', { type: 'gam', url: gamUrl });
121
141
  }
122
142
  }
@@ -169,6 +189,11 @@ export const advertisement = ($slStreamId, $feedSubscription, instance) => {
169
189
  $store.setKey('isPaused', status);
170
190
  }
171
191
  };
192
+ const mute = (notificationId, status) => {
193
+ if ($store.get()?.data?.question.id === notificationId) {
194
+ $store.setKey('isMuted', status);
195
+ }
196
+ };
172
197
  const connect = () => {
173
198
  if (connected) {
174
199
  return;
@@ -3,4 +3,6 @@ export declare class AdvertisementStorage extends Storage {
3
3
  constructor();
4
4
  setShowed: (advertId: string) => void;
5
5
  isViewed: (advertId: string) => string | undefined;
6
+ fireEvent: (advertId: string, event: string) => void;
7
+ isEventFired: (advertId: string, event: string) => boolean;
6
8
  }
@@ -2,6 +2,7 @@ import { Storage } from '@streamlayer/sdk-web-storage';
2
2
  var KEY_PREFIX;
3
3
  (function (KEY_PREFIX) {
4
4
  KEY_PREFIX["SHOWED"] = "showed";
5
+ KEY_PREFIX["EVENT"] = "ev";
5
6
  })(KEY_PREFIX || (KEY_PREFIX = {}));
6
7
  export class AdvertisementStorage extends Storage {
7
8
  constructor() {
@@ -13,4 +14,10 @@ export class AdvertisementStorage extends Storage {
13
14
  isViewed = (advertId) => {
14
15
  return this.read(KEY_PREFIX.SHOWED, advertId);
15
16
  };
17
+ fireEvent = (advertId, event) => {
18
+ this.write(KEY_PREFIX.EVENT, event, advertId, 'true');
19
+ };
20
+ isEventFired = (advertId, event) => {
21
+ return this.read(KEY_PREFIX.EVENT, event, advertId) === 'true';
22
+ };
16
23
  }
@@ -35,6 +35,11 @@ export declare const parsePromotion: (response: SubscriptionResponse) => {
35
35
  activatedBy?: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").ActivatedBy;
36
36
  activatedByTriggerId?: string;
37
37
  activatedByTriggerName?: string;
38
+ templateId?: string;
39
+ adUnit: import("@streamlayer/sdk-web-types").AdUnit;
40
+ moduleId?: string;
41
+ isModuleOverridden?: boolean;
42
+ format: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").CardFormat;
38
43
  };
39
44
  notification: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionNotification | undefined;
40
45
  promotion: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionOptions_PromotionOptions | undefined;
@@ -77,6 +77,7 @@ export declare class Gamification extends AbstractFeature<'games', PlainMessage<
77
77
  closeQuestion: (questionId?: string) => void;
78
78
  openUser: (friendId: string) => Promise<void>;
79
79
  closeUser: () => void;
80
+ openOnboarding: () => void;
80
81
  /**
81
82
  * Show in-app notification for active question
82
83
  * for interactive questions we show notification only if interactiveAllowed
@@ -3,6 +3,8 @@ import { AbstractFeature, ApiStore, SingleStore, createSingleStore, eventBus, }
3
3
  import { QuestionStatus, QuestionType, FeatureType, SilenceSetting, PickHistoryStatus, UseAsNotification, } from '@streamlayer/sdk-web-types';
4
4
  import { NotificationType } from '@streamlayer/sdk-web-notifications';
5
5
  import '@streamlayer/sdk-web-core/store';
6
+ import { onStart } from 'nanostores';
7
+ import { AdUnit, FactoidMediaMode, NotificationUseContentTexts, } from '@streamlayer/sl-eslib/interactive/interactive.common_pb';
6
8
  import * as queries from './queries';
7
9
  import * as actions from './queries/actions';
8
10
  import { leaderboard } from './leaderboard';
@@ -250,6 +252,13 @@ export class Gamification extends AbstractFeature {
250
252
  predictionResult: status === QuestionStatus.RESOLVED,
251
253
  questionTitle: question?.subject,
252
254
  },
255
+ inApp: {
256
+ notification: question.notification,
257
+ appearance: question.appearance,
258
+ sponsorship: question.sponsorship,
259
+ adUnit: question?.adUnit,
260
+ sponsorLogo: question.promotion?.sponsor?.logo,
261
+ },
253
262
  },
254
263
  });
255
264
  }
@@ -258,6 +267,9 @@ export class Gamification extends AbstractFeature {
258
267
  }));
259
268
  // update feed list on question update received from subscription
260
269
  // add new question to the top of the list
270
+ onStart(this.feedList.getStore(), () => {
271
+ this.cancels.add(this.feedList.subscribe(() => { }));
272
+ });
261
273
  this.cancels.add(this.background.feedSubscription.addListener('feed-subscription-questions-list', (response) => {
262
274
  const feedList = [...(this.feedList.getStore().value?.data || [])];
263
275
  const feedItem = response.data?.attributes?.feedItem;
@@ -275,7 +287,9 @@ export class Gamification extends AbstractFeature {
275
287
  return;
276
288
  }
277
289
  // allow only insight cards when onboarding not completed
278
- if (!this.isInteractiveAllowed && InteractiveQuestionTypes.has(feedItem.attributes.type)) {
290
+ if (!this.isInteractiveAllowed &&
291
+ InteractiveQuestionTypes.has(feedItem.attributes.type) &&
292
+ feedItem?.attributes?.adUnit !== AdUnit.STANDART) {
279
293
  return;
280
294
  }
281
295
  if (questionIndex !== -1) {
@@ -341,6 +355,7 @@ export class Gamification extends AbstractFeature {
341
355
  eventBus.emit('poll', {
342
356
  action: 'received',
343
357
  payload: {
358
+ isAd: feedItem.attributes?.adUnit == AdUnit.UNSET,
344
359
  questionId: feedItem.id,
345
360
  questionType: feedItem.attributes?.type,
346
361
  },
@@ -377,6 +392,7 @@ export class Gamification extends AbstractFeature {
377
392
  action: 'voted',
378
393
  payload: {
379
394
  questionId,
395
+ isAd: question?.adUnit == AdUnit.UNSET,
380
396
  questionType: question.type,
381
397
  },
382
398
  });
@@ -408,6 +424,7 @@ export class Gamification extends AbstractFeature {
408
424
  eventBus.emit('poll', {
409
425
  action: 'voted',
410
426
  payload: {
427
+ isAd: poll.attributes?.adUnit == AdUnit.UNSET,
411
428
  questionId,
412
429
  questionType: question.questionType,
413
430
  },
@@ -467,6 +484,7 @@ export class Gamification extends AbstractFeature {
467
484
  }
468
485
  };
469
486
  openQuestion = (questionId, question) => {
487
+ console.log('openQuestion', questionId, question);
470
488
  if (!questionId) {
471
489
  return () => { };
472
490
  }
@@ -478,21 +496,35 @@ export class Gamification extends AbstractFeature {
478
496
  animateHiding: false,
479
497
  });
480
498
  let questionType = question?.attributes?.type;
499
+ let hasBanner = question?.attributes?.adUnit === AdUnit.STANDART && !!question?.attributes?.adPromotion?.banner?.imageUrl;
481
500
  if (!questionType && !openedFromBetPack) {
482
501
  const feedList = this.feedList.getStore().value?.data || [];
483
- questionType = feedList.find((item) => item.id === questionId)?.attributes?.type;
502
+ const itemFromFeed = feedList.find((item) => item.id === questionId)?.attributes;
503
+ questionType = itemFromFeed?.type;
504
+ hasBanner = itemFromFeed?.adUnit === AdUnit.STANDART && !!itemFromFeed?.adPromotion?.banner?.imageUrl;
484
505
  }
485
506
  const flags = {
486
507
  eventId: this.background.slStreamId.get() || '',
487
508
  userId: this.background.userId.get() || '',
488
509
  organizationId: this.background.organizationId.get() || '',
489
510
  };
511
+ eventBus.emit('poll', {
512
+ action: 'opened',
513
+ payload: {
514
+ questionId,
515
+ questionType,
516
+ isAd: question?.attributes?.adUnit == AdUnit.UNSET,
517
+ questionOpenedFrom: question?.openedFrom === 'bet-pack' ? 'list' : question?.openedFrom,
518
+ hasBanner,
519
+ },
520
+ });
490
521
  if (!this.storage.isQuestionOpened(flags, questionId)) {
491
522
  eventBus.emit('poll', {
492
- action: 'opened',
523
+ action: 'viewed',
493
524
  payload: {
494
525
  questionId,
495
526
  questionType,
527
+ isAd: question?.attributes?.adUnit == AdUnit.UNSET,
496
528
  questionOpenedFrom: question?.openedFrom === 'bet-pack' ? 'list' : question?.openedFrom,
497
529
  },
498
530
  });
@@ -524,6 +556,12 @@ export class Gamification extends AbstractFeature {
524
556
  entity: questionId,
525
557
  })),
526
558
  });
559
+ eventBus.emit('poll', {
560
+ action: 'closed',
561
+ payload: {
562
+ questionId,
563
+ },
564
+ });
527
565
  }
528
566
  return this.background.closeQuestion(questionId);
529
567
  };
@@ -562,6 +600,13 @@ export class Gamification extends AbstractFeature {
562
600
  closeUser = () => {
563
601
  this.openedUser?.set(undefined);
564
602
  };
603
+ openOnboarding = () => {
604
+ this.openFeature();
605
+ eventBus.emit('poll', {
606
+ action: 'onboardingOpen',
607
+ payload: {},
608
+ });
609
+ };
565
610
  /**
566
611
  * Show in-app notification for active question
567
612
  * for interactive questions we show notification only if interactiveAllowed
@@ -570,13 +615,14 @@ export class Gamification extends AbstractFeature {
570
615
  */
571
616
  showInApp = (question) => {
572
617
  const onboardingStatus = this.onboardingStatus.$store.get();
573
- if (question && question.data && onboardingStatus && onboardingStatus !== OnboardingStatus.Unset) {
618
+ const isAdUnit = question?.data?.question?.adUnit === AdUnit.STANDART;
619
+ if (question && question.data && (isAdUnit || (onboardingStatus && onboardingStatus !== OnboardingStatus.Unset))) {
574
620
  if (question.data.question?.id !== undefined &&
575
621
  question.data.question?.bypassNotifications?.inAppSilence !== SilenceSetting.ON &&
576
622
  question.data.question.status === QuestionStatus.ACTIVE &&
577
623
  !question.data.question.marketClosed) {
578
624
  if (InteractiveQuestionTypes.has(question.data.question.type)) {
579
- if (this.isInteractiveAllowed && question.data.question.notification !== undefined) {
625
+ if ((this.isInteractiveAllowed || isAdUnit) && question.data.question.notification !== undefined) {
580
626
  this.notifications.add({
581
627
  type: NotificationType.QUESTION,
582
628
  action: () => this.openQuestion(question.data?.question?.id, question.data?.feedItem),
@@ -597,6 +643,8 @@ export class Gamification extends AbstractFeature {
597
643
  notification: question.data.question.notification,
598
644
  appearance: question.data.question.appearance,
599
645
  sponsorship: question.data.question.sponsorship,
646
+ adUnit: question.data.question?.adUnit,
647
+ sponsorLogo: question.data.question.promotion?.sponsor?.logo,
600
648
  },
601
649
  },
602
650
  });
@@ -604,8 +652,12 @@ export class Gamification extends AbstractFeature {
604
652
  }
605
653
  else if (question.data.question.type === QuestionType.FACTOID) {
606
654
  const optionsValue = question.data.question.options?.options.value;
607
- const heading = question.data.question.notification?.title || question.data.question.subject || '';
608
- const body = question.data.question.notification?.body || optionsValue.body;
655
+ const heading = question.data.question.notification?.useContentTexts === NotificationUseContentTexts.ENABLED
656
+ ? question.data.question.subject
657
+ : question.data.question.notification?.title || '';
658
+ const body = question.data.question.notification?.useContentTexts === NotificationUseContentTexts.ENABLED
659
+ ? optionsValue.body
660
+ : question.data.question.notification?.body;
609
661
  const instantView = {
610
662
  heading,
611
663
  body,
@@ -637,6 +689,9 @@ export class Gamification extends AbstractFeature {
637
689
  notification: question.data.question.notification,
638
690
  appearance: question.data.question.appearance,
639
691
  sponsorship: question.data.question.sponsorship,
692
+ adUnit: question.data.question?.adUnit,
693
+ sponsorLogo: question.data.question.promotion?.sponsor?.logo,
694
+ isVideo: optionsValue?.mode === FactoidMediaMode.VIDEO,
640
695
  },
641
696
  },
642
697
  });
package/lib/index.d.ts CHANGED
@@ -3,6 +3,6 @@ export { Gamification } from './gamification';
3
3
  export { Advertisement } from './advertisement';
4
4
  declare module '@streamlayer/sdk-web-interfaces' {
5
5
  interface StreamLayerContext {
6
- gamification: import('./background').GamificationBackground;
6
+ gamification: import('./gamification').Gamification;
7
7
  }
8
8
  }
package/lib/onboarding.js CHANGED
@@ -42,6 +42,18 @@ const showOnboardingInApp = (service, background, notifications, storage) => {
42
42
  organizationId: background.organizationId.get() || '',
43
43
  eventId: background.slStreamId.get() || '',
44
44
  }),
45
+ markIstantOpen: () => {
46
+ storage.setOnboardingInstantOpen({
47
+ userId: background.userId.get() || '',
48
+ organizationId: background.organizationId.get() || '',
49
+ eventId: background.slStreamId.get() || '',
50
+ });
51
+ notifications.update(notificationId, (notification) => {
52
+ if (notification?.data?.onboarding) {
53
+ notification.data.onboarding.instantOpen = true;
54
+ }
55
+ });
56
+ },
45
57
  },
46
58
  },
47
59
  });
@@ -1,5 +1,5 @@
1
1
  import type { Transport } from '@streamlayer/sdk-web-api';
2
- import { QuestionStatus, QuestionType } from '@streamlayer/sdk-web-types';
2
+ import { AdUnit, QuestionStatus, QuestionType } from '@streamlayer/sdk-web-types';
3
3
  import { ReadableAtom } from 'nanostores';
4
4
  import { FeedItem, QuestionSubscriptionRequest, QuestionSubscriptionResponse, SubscriptionRequest, SubscriptionResponse, VotingSubscriptionRequest, VotingSubscriptionResponse } from '@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb';
5
5
  import { InteractiveAllowed } from '../background';
@@ -91,6 +91,11 @@ export declare const feedSubscription: ($slStreamId: ReadableAtom<string | undef
91
91
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListRequestSchema;
92
92
  output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListResponseSchema;
93
93
  };
94
+ pauseAdList: {
95
+ methodKind: "unary";
96
+ input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListListRequestSchema;
97
+ output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListResponseSchema;
98
+ };
94
99
  item: {
95
100
  methodKind: "unary";
96
101
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedItemRequestSchema;
@@ -217,6 +222,11 @@ export declare const votingSubscription: (params: {
217
222
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListRequestSchema;
218
223
  output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListResponseSchema;
219
224
  };
225
+ pauseAdList: {
226
+ methodKind: "unary";
227
+ input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListListRequestSchema;
228
+ output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListResponseSchema;
229
+ };
220
230
  item: {
221
231
  methodKind: "unary";
222
232
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedItemRequestSchema;
@@ -340,6 +350,11 @@ export declare const questionSubscription: (questionId: string, transport: Trans
340
350
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListRequestSchema;
341
351
  output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedListResponseSchema;
342
352
  };
353
+ pauseAdList: {
354
+ methodKind: "unary";
355
+ input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListListRequestSchema;
356
+ output: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").PauseAdListResponseSchema;
357
+ };
343
358
  item: {
344
359
  methodKind: "unary";
345
360
  input: typeof import("@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb").FeedItemRequestSchema;
@@ -417,6 +432,11 @@ export declare const getPromotionDetail: (promoId: string, transport: Transport)
417
432
  activatedBy?: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").ActivatedBy;
418
433
  activatedByTriggerId?: string;
419
434
  activatedByTriggerName?: string;
435
+ templateId?: string;
436
+ adUnit: AdUnit;
437
+ moduleId?: string;
438
+ isModuleOverridden?: boolean;
439
+ format: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").CardFormat;
420
440
  };
421
441
  promotion: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionOptions_PromotionOptions | undefined;
422
442
  notification: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionNotification | undefined;
@@ -459,6 +479,11 @@ export declare const $activePromotionId: ($slStreamId: ReadableAtom<string | und
459
479
  activatedBy?: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").ActivatedBy;
460
480
  activatedByTriggerId?: string;
461
481
  activatedByTriggerName?: string;
482
+ templateId?: string;
483
+ adUnit: AdUnit;
484
+ moduleId?: string;
485
+ isModuleOverridden?: boolean;
486
+ format: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").CardFormat;
462
487
  };
463
488
  promotion: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionOptions_PromotionOptions | undefined;
464
489
  notification: import("@streamlayer/sl-eslib/interactive/interactive.common_pb").QuestionNotification | undefined;
@@ -1,4 +1,4 @@
1
- import { QuestionStatus, QuestionType } from '@streamlayer/sdk-web-types';
1
+ import { AdUnit, QuestionStatus, QuestionType } from '@streamlayer/sdk-web-types';
2
2
  import { eventBus } from '@streamlayer/sdk-web-interfaces';
3
3
  import { atom } from 'nanostores';
4
4
  import { Feed, } from '@streamlayer/sl-eslib/interactive/feed/interactive.feed_pb';
@@ -158,6 +158,7 @@ export const $feedList = ($slStreamId, $interactiveAllowed, $slUserId, $slOrgani
158
158
  eventBus.emit('poll', {
159
159
  action: 'received',
160
160
  payload: {
161
+ isAd: question.attributes?.adUnit == AdUnit.UNSET,
161
162
  questionId: question.id,
162
163
  questionType: question.attributes?.type,
163
164
  },
@@ -250,6 +251,7 @@ export const $betPack = ($slStreamId, $slUserId, $slOrganizationId, storage, tra
250
251
  eventBus.emit('poll', {
251
252
  action: 'received',
252
253
  payload: {
254
+ isAd: question?.adUnit == AdUnit.UNSET,
253
255
  questionId: question.id,
254
256
  questionType: question.type,
255
257
  },
package/package.json CHANGED
@@ -1,19 +1,19 @@
1
1
  {
2
2
  "name": "@streamlayer/feature-gamification",
3
- "version": "1.19.1",
3
+ "version": "1.20.1",
4
4
  "peerDependencies": {
5
5
  "@bufbuild/protobuf": "^2.2.2",
6
6
  "@fastify/deepmerge": "^2.0.0",
7
- "@streamlayer/sl-eslib": "^5.179.1",
7
+ "@streamlayer/sl-eslib": "^5.216.1",
8
8
  "uuid": "^11.1.0",
9
9
  "nanostores": "^0.11.4",
10
- "@streamlayer/sdk-web-api": "^1.11.1",
11
- "@streamlayer/sdk-web-core": "^1.14.1",
12
- "@streamlayer/sdk-web-interfaces": "^1.6.4",
13
- "@streamlayer/sdk-web-logger": "^1.0.66",
14
- "@streamlayer/sdk-web-notifications": "^1.3.28",
15
- "@streamlayer/sdk-web-storage": "^1.0.66",
16
- "@streamlayer/sdk-web-types": "^1.13.1"
10
+ "@streamlayer/sdk-web-api": "^1.12.1",
11
+ "@streamlayer/sdk-web-core": "^1.15.1",
12
+ "@streamlayer/sdk-web-interfaces": "^1.7.1",
13
+ "@streamlayer/sdk-web-logger": "^1.0.68",
14
+ "@streamlayer/sdk-web-notifications": "^1.3.30",
15
+ "@streamlayer/sdk-web-storage": "^1.0.68",
16
+ "@streamlayer/sdk-web-types": "^1.14.1"
17
17
  },
18
18
  "devDependencies": {
19
19
  "tslib": "^2.7.0"