@startinblox/components-ds4go 4.1.4 → 4.1.6

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@startinblox/components-ds4go",
3
- "version": "4.1.4",
3
+ "version": "4.1.6",
4
4
  "description": "Startin'blox DS4GO",
5
5
  "main": "dist/index.js",
6
6
  "type": "module",
@@ -2,7 +2,7 @@ import { formatDate, formatCase, OrbitComponent } from "@helpers";
2
2
  import { localized, msg } from "@lit/localize";
3
3
  import { Task } from "@lit/task";
4
4
  import { PropertiesPicker } from "@src/component";
5
- import type { Category, Fact } from "@src/ds4go";
5
+ import type { Category, Customer, Fact } from "@src/ds4go";
6
6
 
7
7
  import ModalStyle from "@styles/modal/ds4go-fact-modal.scss?inline";
8
8
  import { css, html, nothing, unsafeCSS } from "lit";
@@ -39,7 +39,10 @@ export class Ds4goFactModal extends OrbitComponent {
39
39
  ];
40
40
 
41
41
  @state()
42
- disableButton = false;
42
+ customer?: Customer;
43
+
44
+ @state()
45
+ alreadyGenerated = false;
43
46
 
44
47
  _generateVideo() {
45
48
  this.orbit?.Swal.fire({
@@ -61,25 +64,40 @@ export class Ds4goFactModal extends OrbitComponent {
61
64
  },
62
65
  }).then((result: any) => {
63
66
  if (result.isConfirmed) {
64
- this.orbit?.Swal.fire({
65
- title: msg("Generating..."),
66
- text: msg("Please wait while Tralalère generates your AI-Video..."),
67
- icon: "info",
68
- showConfirmButton: false,
69
- allowOutsideClick: false,
70
- allowEscapeKey: false,
71
- allowEnterKey: false,
72
- });
73
- setTimeout(() => {
67
+ if (this.customer) {
74
68
  this.orbit?.Swal.fire({
75
- title: msg("AI-Video generated!"),
76
- text: msg(
77
- "Your AI-Generated video has been generated and is available in your Tralalère space.",
78
- ),
79
- icon: "success",
69
+ title: msg("Generating..."),
70
+ text: msg("Please wait while Tralalère generates your AI-Video..."),
71
+ icon: "info",
72
+ showConfirmButton: false,
73
+ allowOutsideClick: false,
74
+ allowEscapeKey: false,
75
+ allowEnterKey: false,
80
76
  });
81
- this.disableButton = true;
82
- }, 2500);
77
+ window.sib.store.ldp
78
+ .patch(
79
+ {
80
+ "@context": this.customer._originalResource?.serverContext,
81
+ balance: (this.customer.balance || 0) - 5,
82
+ },
83
+ this.customer["@id"],
84
+ )
85
+ .then(async () => {
86
+ if (this.customer) {
87
+ await window.sib.store.ldp.clearCache(this.customer["@id"]);
88
+ await window.sib.store.ldp.getData(this.customer["@id"], {});
89
+ }
90
+ setTimeout(() => {
91
+ this.parent.notifyVideoGeneration(this.object["@id"]);
92
+ }, 2500);
93
+ });
94
+ } else {
95
+ this.orbit?.Swal.fire({
96
+ title: msg("Error"),
97
+ text: msg("Customer not found."),
98
+ icon: "error",
99
+ });
100
+ }
83
101
  }
84
102
  });
85
103
  }
@@ -124,13 +142,19 @@ export class Ds4goFactModal extends OrbitComponent {
124
142
  type="outline-gray"
125
143
  .iconLeft=${html`<icon-material-symbols-close-rounded></icon-material-symbols-close-rounded>`}
126
144
  ></tems-button>
127
- <tems-button
128
- @click=${this._generateVideo}
129
- disabled=${this.disableButton || nothing}
130
- >${this.disableButton
131
- ? msg("Video already generated")
132
- : msg("Generate an AI-Video with Tralalère (5€)")}</tems-button
133
- >
145
+ ${this.customer
146
+ ? html`<tems-button
147
+ @click=${this._generateVideo}
148
+ disabled=${this.alreadyGenerated || nothing}
149
+ >${(this.customer?.balance || 0) < 5
150
+ ? msg("Insufficient balance")
151
+ : this.alreadyGenerated
152
+ ? msg("Video already generated")
153
+ : msg(
154
+ "Generate an AI-Video with Tralalère (5€)",
155
+ )}</tems-button
156
+ >`
157
+ : nothing}
134
158
  </div>
135
159
  <div class="modal-content-wrapper">
136
160
  <div class="modal-box">
@@ -14,6 +14,7 @@ import type {
14
14
  PolicyDefinition,
15
15
  PolicyTemplate,
16
16
  PropertiesPicker,
17
+ Resource,
17
18
  } from "@src/component";
18
19
  import type { Category, Fact } from "@src/ds4go";
19
20
  import ComponentStyles from "@styles/fact-bundle-creation.scss?inline";
@@ -86,17 +87,29 @@ export class SolidFactBundle extends OrbitComponent {
86
87
  }
87
88
 
88
89
  cherryPickedProperties: PropertiesPicker[] = [
89
- { key: "created_at", value: "created_at", cast: formatDate },
90
+ { key: "created_at", value: "created_at" },
90
91
  { key: "updated_at", value: "updated_at", cast: formatDate },
91
92
  { key: "name", value: "name" },
92
93
  { key: "description", value: "description" },
93
94
  { key: "author", value: "author" },
95
+ { key: "link", value: "link" },
96
+ { key: "enclosure", value: "enclosure" },
94
97
  {
95
98
  key: "categories",
96
99
  value: "categories",
97
100
  expand: true,
98
- cast: (c: Category[]) => sort(c, "name"),
101
+ cast: (categories: Resource[]) =>
102
+ (categories || []).map((category: Resource) => ({
103
+ "@id": category["@id"],
104
+ name: formatCase(category["name"] || ""),
105
+ })),
99
106
  },
107
+ { key: "medias", value: "medias", expand: true },
108
+ { key: "url", value: "url" },
109
+ { key: "file_size", value: "file_size" },
110
+ { key: "file_type", value: "file_type" },
111
+ { key: "width", value: "width" },
112
+ { key: "height", value: "height" },
100
113
  ];
101
114
 
102
115
  _getResource = new Task(this, {
@@ -479,7 +492,10 @@ export class SolidFactBundle extends OrbitComponent {
479
492
  !!this.bundleContractPolicy;
480
493
 
481
494
  return html`<tems-viewport>
482
- <tems-header slot="header" heading=${this.header}>
495
+ <tems-header
496
+ slot="header"
497
+ heading=${`${this.header} - ${this.step === 0 ? msg("Fact checks selection") : msg("Bundle information")}`}
498
+ >
483
499
  <div slot="cta">
484
500
  ${this.step === 0
485
501
  ? html`<tems-button
@@ -497,7 +513,9 @@ export class SolidFactBundle extends OrbitComponent {
497
513
  ><tems-button
498
514
  type="primary"
499
515
  disabled=${!allowCreation || nothing}
500
- label=${msg("Create bundle")}
516
+ label=${msg(
517
+ str`Create bundle with ${selectedFactsCount} fact${selectedFactsCount > 1 ? "s" : ""}`,
518
+ )}
501
519
  @click=${this._createFactBundle}
502
520
  ></tems-button>
503
521
  </div>`}
@@ -516,10 +534,12 @@ export class SolidFactBundle extends OrbitComponent {
516
534
  >
517
535
  <div class="card-grid card-grid-vertical">
518
536
  ${this.selectedFacts.map((fact: Fact) => {
519
- const tags = (fact.categories || []).map((c: Category) => ({
520
- name: c.name,
521
- type: "information",
522
- }));
537
+ const tags = (fact.categories || []).map(
538
+ (c: Category) => ({
539
+ name: c.name,
540
+ type: "information",
541
+ }),
542
+ );
523
543
  if (tags.length > 3) {
524
544
  const overflowTags = tags.length - 3;
525
545
  tags.splice(3, overflowTags);
@@ -529,7 +549,7 @@ export class SolidFactBundle extends OrbitComponent {
529
549
  });
530
550
  }
531
551
  return html`<ds4go-card-catalog
532
- .object=${import.meta.env.DEV ? fact : nothing}
552
+ .object=${fact}
533
553
  .header=${fact.name || nothing}
534
554
  date=${fact.updated_at || nothing}
535
555
  @click=${this._toggleFactSelection.bind(
@@ -575,10 +595,8 @@ export class SolidFactBundle extends OrbitComponent {
575
595
  });
576
596
  }
577
597
 
578
- return html`<ds4go-card-catalog
579
- .object=${import.meta.env.DEV
580
- ? fact
581
- : nothing}
598
+ return html`<ds4go-card-fact
599
+ .object=${fact}
582
600
  .tags=${tags}
583
601
  .header=${fact.name || nothing}
584
602
  .content=${fact.description || nothing}
@@ -587,7 +605,7 @@ export class SolidFactBundle extends OrbitComponent {
587
605
  this,
588
606
  fact,
589
607
  )}
590
- ></ds4go-card-catalog>`;
608
+ ></ds4go-card-fact>`;
591
609
  })}
592
610
  </div>
593
611
  ${splicedDatas.length < datas.length
@@ -657,8 +675,9 @@ export class SolidFactBundle extends OrbitComponent {
657
675
  ${Array.from(
658
676
  new Set(
659
677
  this.selectedFacts.flatMap((fact: Fact) =>
660
- (fact.categories || []).map((category: Category) =>
661
- formatCase(category.name || ""),
678
+ (fact.categories || []).map(
679
+ (category: Category) =>
680
+ formatCase(category.name || ""),
662
681
  ),
663
682
  ),
664
683
  ),
@@ -6,6 +6,7 @@ import {
6
6
  setupCacheInvalidation,
7
7
  sort,
8
8
  } from "@helpers";
9
+ import { msg } from "@lit/localize";
9
10
  import { Task } from "@lit/task";
10
11
  import type {
11
12
  Asset,
@@ -16,7 +17,7 @@ import type {
16
17
  Resource,
17
18
  SearchObject,
18
19
  } from "@src/component";
19
- import type { Category, Fact } from "@src/ds4go";
20
+ import type { Customer, Fact } from "@src/ds4go";
20
21
  import { css, html, nothing } from "lit";
21
22
  import { customElement, property, state } from "lit/decorators.js";
22
23
 
@@ -55,6 +56,15 @@ export class SolidFactList extends OrbitComponent {
55
56
  @state()
56
57
  consumerAgreements: ContractAgreement[] = [];
57
58
 
59
+ @property({ attribute: "customers-src", type: String })
60
+ customersSrc?: string;
61
+
62
+ @state()
63
+ customer?: Customer;
64
+
65
+ @state()
66
+ alreadyGeneratedVideos: string[] = [];
67
+
58
68
  cherryPickedProperties: PropertiesPicker[] = [
59
69
  { key: "created_at", value: "created_at", cast: formatDate },
60
70
  { key: "updated_at", value: "updated_at", cast: formatDate },
@@ -63,7 +73,7 @@ export class SolidFactList extends OrbitComponent {
63
73
 
64
74
  async _afterAttach() {
65
75
  setupCacheInvalidation(this, {
66
- keywords: ["fact"],
76
+ keywords: ["customers", "fact"],
67
77
  });
68
78
 
69
79
  // use this.dspConnector.instance to reach the connector
@@ -75,7 +85,7 @@ export class SolidFactList extends OrbitComponent {
75
85
  }
76
86
 
77
87
  _getResource = new Task(this, {
78
- task: async ([objSrc]) => {
88
+ task: async ([objSrc, customersSrc]) => {
79
89
  if (
80
90
  !this.orbit ||
81
91
  (!this.noRouter &&
@@ -85,6 +95,14 @@ export class SolidFactList extends OrbitComponent {
85
95
  )
86
96
  return;
87
97
 
98
+ const customers: Customer[] = customersSrc
99
+ ? ((await this._getProxyValue(customersSrc, true, [
100
+ { key: "name", value: "name" },
101
+ { key: "participant_id", value: "participant_id" },
102
+ { key: "balance", value: "balance" },
103
+ ])) as Customer[]) || []
104
+ : [];
105
+
88
106
  if (this.dspConnector?.instance) {
89
107
  // Get all data from DSP connector
90
108
  await this.dspConnector.instance.loadAll();
@@ -93,6 +111,10 @@ export class SolidFactList extends OrbitComponent {
93
111
  "participant-id"
94
112
  ];
95
113
  if (participantId) {
114
+ this.customer = customers.find(
115
+ (c) => c.participant_id === participantId,
116
+ );
117
+
96
118
  // Load agreements for all negotiations to find consumer/provider relationships
97
119
  const allNegotiations = this.dspConnector.instance.negotiations || [];
98
120
 
@@ -163,15 +185,11 @@ export class SolidFactList extends OrbitComponent {
163
185
  key: "categories",
164
186
  value: "categories",
165
187
  expand: true,
166
- cast: async (c: Resource) =>
167
- await Promise.all(
168
- (await c._originalResource?.["ldp:contains"]).map(
169
- async (c: Category) => ({
170
- "@id": c["@id"],
171
- name: formatCase((await c["name"]) || ""),
172
- }),
173
- ),
174
- ),
188
+ cast: (categories: Resource[]) =>
189
+ (categories || []).map((category: Resource) => ({
190
+ "@id": category["@id"],
191
+ name: formatCase(category["name"] || ""),
192
+ })),
175
193
  },
176
194
  { key: "medias", value: "medias", expand: true },
177
195
  { key: "url", value: "url" },
@@ -211,7 +229,12 @@ export class SolidFactList extends OrbitComponent {
211
229
 
212
230
  return [];
213
231
  },
214
- args: () => [this.dataSrc, this.caching, this.currentRoute],
232
+ args: () => [
233
+ this.dataSrc,
234
+ this.customersSrc,
235
+ this.caching,
236
+ this.currentRoute,
237
+ ],
215
238
  });
216
239
 
217
240
  _search(e: Event) {
@@ -260,6 +283,27 @@ export class SolidFactList extends OrbitComponent {
260
283
  }
261
284
  }
262
285
 
286
+ notifyVideoGeneration(id: string) {
287
+ this.alreadyGeneratedVideos.push(id);
288
+ if (this.customer) {
289
+ document.dispatchEvent(
290
+ new CustomEvent("save", {
291
+ detail: {
292
+ resource: { "@id": this.customer["@id"] },
293
+ },
294
+ bubbles: true,
295
+ }),
296
+ );
297
+ }
298
+ this.orbit?.Swal.fire({
299
+ title: msg("AI-Video generated!"),
300
+ text: msg(
301
+ "Your AI-Generated video has been generated and is available in your Tralalère space.",
302
+ ),
303
+ icon: "success",
304
+ });
305
+ }
306
+
263
307
  _resultCountUpdate(e: Event) {
264
308
  this.resultCount = e.detail ?? 0;
265
309
  }
@@ -283,7 +327,17 @@ export class SolidFactList extends OrbitComponent {
283
327
  },
284
328
  complete: (datas) => {
285
329
  return html`<tems-viewport>
286
- <tems-header slot="header" heading=${this.header}></tems-header>
330
+ <tems-header slot="header" heading=${this.header}>
331
+ <div slot="cta">
332
+ <tems-badge type="brand"
333
+ >Balance:
334
+ ${new Intl.NumberFormat(undefined, {
335
+ style: "currency",
336
+ currency: "EUR",
337
+ }).format(Number(this.customer?.balance || 0))}</tems-badge
338
+ >
339
+ </div>
340
+ </tems-header>
287
341
  <div slot="content">
288
342
  <ds4go-catalog-filter-holder
289
343
  .displayFiltering=${this.displayFiltering}
@@ -305,7 +359,12 @@ export class SolidFactList extends OrbitComponent {
305
359
  @click=${this._closeModalFromBackground}
306
360
  >
307
361
  <ds4go-fact-modal
362
+ .parent=${this}
363
+ .customer=${this.customer}
308
364
  .object=${this.object}
365
+ .alreadyGenerated=${this.alreadyGeneratedVideos.includes(
366
+ this.object["@id"],
367
+ )}
309
368
  @close=${this._closeModal}
310
369
  ></ds4go-fact-modal>
311
370
  </div>`
@@ -215,10 +215,13 @@ export default class extends ComponentObjectsHandler {
215
215
  return await this._responseAdaptator(response);
216
216
  }
217
217
 
218
- async _hasCherryPickedProperties(resource: Resource) {
218
+ async _hasCherryPickedProperties(
219
+ resource: Resource,
220
+ targetProperties = this.cherryPickedProperties,
221
+ ) {
219
222
  const properties = await resource.properties;
220
223
 
221
- for (const prop of this.cherryPickedProperties) {
224
+ for (const prop of targetProperties) {
222
225
  if (properties?.includes(prop.key)) {
223
226
  return true;
224
227
  }
@@ -251,7 +254,7 @@ export default class extends ComponentObjectsHandler {
251
254
  if (typeof target !== "object" || target === null) return;
252
255
 
253
256
  if (target.isContainer?.() && target["ldp:contains"]) {
254
- if (await this._hasCherryPickedProperties(target)) {
257
+ if (await this._hasCherryPickedProperties(target, targetProperties)) {
255
258
  return await this._getProperties(target, recursive, targetProperties);
256
259
  }
257
260
 
@@ -37,7 +37,7 @@ section {
37
37
  .card-grid-vertical {
38
38
  justify-content: stretch;
39
39
 
40
- ds4go-card-catalog {
40
+ ds4go-card-catalog, ds4go-card-fact {
41
41
  width: 354px;
42
42
  height: fit-content;
43
43
  }