@websolutespa/bom-mixer-store 1.7.7 → 1.7.9
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/CHANGELOG.md +16 -0
- package/dist/index.js +152 -113
- package/dist/index.mjs +95 -50
- package/package.json +2 -2
- package/src/decorators/category.ts +3 -8
- package/src/decorators/menu.ts +187 -28
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,21 @@
|
|
|
1
1
|
# @websolutespa/bom-mixer-store
|
|
2
2
|
|
|
3
|
+
## 1.7.9
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- Added: MenuCategory strategy
|
|
8
|
+
- Updated dependencies
|
|
9
|
+
- @websolutespa/bom-core@1.7.16
|
|
10
|
+
|
|
11
|
+
## 1.7.8
|
|
12
|
+
|
|
13
|
+
### Patch Changes
|
|
14
|
+
|
|
15
|
+
- Modified: RouteService, MenuService to handle isHidden Category segments
|
|
16
|
+
- Updated dependencies
|
|
17
|
+
- @websolutespa/bom-core@1.7.12
|
|
18
|
+
|
|
3
19
|
## 1.7.7
|
|
4
20
|
|
|
5
21
|
### Patch Changes
|
package/dist/index.js
CHANGED
|
@@ -184,6 +184,7 @@ async function fromCache(callback, key) {
|
|
|
184
184
|
}
|
|
185
185
|
|
|
186
186
|
// src/decorators/category.ts
|
|
187
|
+
var import_bom_core = require("@websolutespa/bom-core");
|
|
187
188
|
async function decorateCategory_(store, item, params = {}) {
|
|
188
189
|
if (typeof item.category === "string") {
|
|
189
190
|
const categories = await store.category.findMany({
|
|
@@ -196,9 +197,7 @@ async function decorateCategory_(store, item, params = {}) {
|
|
|
196
197
|
if (categories.length > 0) {
|
|
197
198
|
const category = categories[0];
|
|
198
199
|
const routes = await store.route.findMany();
|
|
199
|
-
const route = routes.
|
|
200
|
-
(x) => x.market === params.market && x.locale === params.locale && x.isDefault && x.category === category.id
|
|
201
|
-
);
|
|
200
|
+
const route = (0, import_bom_core.findRouteOfCategory)(routes, category.id, params.market, params.locale);
|
|
202
201
|
if (route) {
|
|
203
202
|
category.href = route.id;
|
|
204
203
|
}
|
|
@@ -216,7 +215,7 @@ async function decorateCategories_(store, items, params = {}) {
|
|
|
216
215
|
return items.map((item) => {
|
|
217
216
|
const category = categories.find((x) => x.id === item.category);
|
|
218
217
|
if (category) {
|
|
219
|
-
const route =
|
|
218
|
+
const route = (0, import_bom_core.findRouteOfCategory)(routes, category.id);
|
|
220
219
|
if (route) {
|
|
221
220
|
category.href = route.id;
|
|
222
221
|
}
|
|
@@ -278,25 +277,25 @@ async function decorateHrefs_(store, items, params = {}) {
|
|
|
278
277
|
}
|
|
279
278
|
|
|
280
279
|
// src/decorators/localizable.ts
|
|
281
|
-
var
|
|
280
|
+
var import_bom_core2 = require("@websolutespa/bom-core");
|
|
282
281
|
async function decorateLocalizable_(item, params = {}) {
|
|
283
282
|
if (params.locale) {
|
|
284
|
-
return (0,
|
|
283
|
+
return (0, import_bom_core2.localizeItem)(item, params.locale);
|
|
285
284
|
} else {
|
|
286
|
-
return (0,
|
|
285
|
+
return (0, import_bom_core2.cloneItem)(item);
|
|
287
286
|
}
|
|
288
287
|
}
|
|
289
288
|
async function decorateLocalizables_(items, params = {}) {
|
|
290
289
|
const decoratedItems = [];
|
|
291
290
|
for (const item of items) {
|
|
292
|
-
const decoratedItem = params.locale ? (0,
|
|
291
|
+
const decoratedItem = params.locale ? (0, import_bom_core2.localizeItem)(item, params.locale) : (0, import_bom_core2.cloneItem)(item);
|
|
293
292
|
decoratedItems.push(decoratedItem);
|
|
294
293
|
}
|
|
295
294
|
return decoratedItems;
|
|
296
295
|
}
|
|
297
296
|
|
|
298
297
|
// src/decorators/menu.ts
|
|
299
|
-
var
|
|
298
|
+
var import_bom_core3 = require("@websolutespa/bom-core");
|
|
300
299
|
async function decorateMenu_(store, item, params) {
|
|
301
300
|
const { market, locale } = params;
|
|
302
301
|
const items = itemsFilteredByMarket_(item.items || [], market);
|
|
@@ -350,7 +349,7 @@ function itemHasMarket_(item, market) {
|
|
|
350
349
|
}
|
|
351
350
|
function collectUndecoratedCategories(items, undecoratedCategories = []) {
|
|
352
351
|
items.forEach((item) => {
|
|
353
|
-
if ((0,
|
|
352
|
+
if ((0, import_bom_core3.isUndecoratedMenuCategory)(item)) {
|
|
354
353
|
undecoratedCategories.push(item);
|
|
355
354
|
}
|
|
356
355
|
if (item.items) {
|
|
@@ -361,7 +360,7 @@ function collectUndecoratedCategories(items, undecoratedCategories = []) {
|
|
|
361
360
|
}
|
|
362
361
|
function collectUndecoratedPages(items, undecoratedPages = []) {
|
|
363
362
|
items.forEach((item) => {
|
|
364
|
-
if ((0,
|
|
363
|
+
if ((0, import_bom_core3.isUndecoratedMenuPage)(item)) {
|
|
365
364
|
undecoratedPages.push(item);
|
|
366
365
|
}
|
|
367
366
|
if (item.items) {
|
|
@@ -371,26 +370,44 @@ function collectUndecoratedPages(items, undecoratedPages = []) {
|
|
|
371
370
|
return undecoratedPages;
|
|
372
371
|
}
|
|
373
372
|
var MAX_INT = 1e12;
|
|
374
|
-
function
|
|
375
|
-
const
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
373
|
+
function makeCategoryMenuItem_(item, category) {
|
|
374
|
+
const id = item.id || (0, import_bom_core3.uuidv4)();
|
|
375
|
+
const title = item.title || category.title || "";
|
|
376
|
+
const abstract = item.abstract || void 0;
|
|
377
|
+
const customClass = item.customClass || void 0;
|
|
378
|
+
const media = item.media || category.media;
|
|
379
|
+
const items = [];
|
|
380
|
+
return category.isHidden ? {
|
|
381
|
+
type: "group",
|
|
382
|
+
id,
|
|
383
|
+
title,
|
|
384
|
+
abstract,
|
|
385
|
+
media,
|
|
386
|
+
customClass,
|
|
387
|
+
items
|
|
388
|
+
} : {
|
|
389
|
+
type: "category",
|
|
390
|
+
category: category.id,
|
|
391
|
+
id,
|
|
379
392
|
href: "",
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
393
|
+
title,
|
|
394
|
+
abstract,
|
|
395
|
+
media,
|
|
396
|
+
customClass,
|
|
397
|
+
items
|
|
384
398
|
};
|
|
385
|
-
|
|
399
|
+
}
|
|
400
|
+
function decorateMenuCategory_(item, categories, routes, market, depth = 0) {
|
|
401
|
+
const strategy = item.strategy || import_bom_core3.MenuCategoryStrategy.Default;
|
|
402
|
+
const categoryId = (0, import_bom_core3.asCategoryId)(item.category);
|
|
403
|
+
const category = categoryId ? categories.find((x) => x.id === categoryId) : void 0;
|
|
386
404
|
if (category) {
|
|
387
|
-
decoratedItem
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
} else {
|
|
405
|
+
const decoratedItem = makeCategoryMenuItem_(item, category);
|
|
406
|
+
if (!category.isHidden) {
|
|
407
|
+
const route = routes.find((route2) => route2.isDefault && route2.resolvedCategory === category.id);
|
|
408
|
+
if (route) {
|
|
409
|
+
decoratedItem.href = route.id;
|
|
410
|
+
}
|
|
394
411
|
}
|
|
395
412
|
let maxDepth = item.maxDepth;
|
|
396
413
|
if (typeof maxDepth === "number") {
|
|
@@ -399,31 +416,55 @@ function decorateMenuCategory_(item, categories, routes, market, depth = 0) {
|
|
|
399
416
|
}
|
|
400
417
|
maxDepth--;
|
|
401
418
|
}
|
|
402
|
-
const childCategories = categories.filter((x) =>
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
419
|
+
const childCategories = (category.id ? categories.filter((x) => (0, import_bom_core3.asCategoryId)(x.category) === category.id) : []).filter((x) => {
|
|
420
|
+
switch (strategy) {
|
|
421
|
+
case import_bom_core3.MenuCategoryStrategy.ExcludeHidden:
|
|
422
|
+
return Boolean(x.isHidden) === false;
|
|
423
|
+
case import_bom_core3.MenuCategoryStrategy.Default:
|
|
424
|
+
return true;
|
|
425
|
+
}
|
|
426
|
+
});
|
|
427
|
+
childCategories.sort((a, b) => {
|
|
428
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
429
|
+
});
|
|
430
|
+
const subStrategy = strategy;
|
|
431
|
+
const childCategoryItems = childCategories.map((c) => decorateMenuCategory_({
|
|
432
|
+
id: c.id,
|
|
433
|
+
type: "category",
|
|
434
|
+
category: c.id,
|
|
435
|
+
maxDepth,
|
|
436
|
+
strategy: subStrategy,
|
|
437
|
+
// dispatch sub strategy
|
|
438
|
+
items: []
|
|
439
|
+
}, categories, routes, market, depth + 1));
|
|
440
|
+
const childRoutes = routes.filter((route) => {
|
|
441
|
+
switch (strategy) {
|
|
442
|
+
case import_bom_core3.MenuCategoryStrategy.ExcludeHidden:
|
|
443
|
+
return route.resolvedCategory === category.id && Boolean(route.isDefault) === false;
|
|
444
|
+
case import_bom_core3.MenuCategoryStrategy.Default:
|
|
445
|
+
return route.category === category.id && (category.isHidden || Boolean(route.isDefault) === false);
|
|
446
|
+
}
|
|
447
|
+
});
|
|
448
|
+
childRoutes.sort((a, b) => {
|
|
449
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
450
|
+
});
|
|
451
|
+
const childRouteItems = childRoutes.map((x) => decorateMenuRoute_(x));
|
|
452
|
+
decoratedItem.items = [
|
|
453
|
+
...childCategoryItems,
|
|
454
|
+
...childRouteItems
|
|
455
|
+
].filter((x) => Boolean(x));
|
|
456
|
+
return decoratedItem;
|
|
421
457
|
}
|
|
422
|
-
return
|
|
458
|
+
return {
|
|
459
|
+
id: item.id || (0, import_bom_core3.uuidv4)(),
|
|
460
|
+
type: "group",
|
|
461
|
+
title: item.title || "",
|
|
462
|
+
items: []
|
|
463
|
+
};
|
|
423
464
|
}
|
|
424
465
|
function decorateMenuRoute_(item) {
|
|
425
466
|
const decoratedItem = {
|
|
426
|
-
id:
|
|
467
|
+
id: (0, import_bom_core3.uuidv4)(),
|
|
427
468
|
type: "route",
|
|
428
469
|
title: item.title,
|
|
429
470
|
href: item.id,
|
|
@@ -435,13 +476,13 @@ function decorateMenuRoute_(item) {
|
|
|
435
476
|
return decoratedItem;
|
|
436
477
|
}
|
|
437
478
|
async function decorateMenuPage_(item, routes, store, params = {}) {
|
|
438
|
-
const id = (0,
|
|
479
|
+
const id = (0, import_bom_core3.isEquatable)(item.page.value) ? item.page.value : item.page.value.id;
|
|
439
480
|
const route = routes.find(
|
|
440
481
|
(x) => x.schema === item.page.relationTo && x.page === id
|
|
441
482
|
);
|
|
442
483
|
const page = await store[item.page.relationTo].findOne(id, { ...params });
|
|
443
484
|
const decoratedItem = {
|
|
444
|
-
id: item.id ||
|
|
485
|
+
id: item.id || (0, import_bom_core3.uuidv4)(),
|
|
445
486
|
type: item.type,
|
|
446
487
|
title: item.title || page?.title || "",
|
|
447
488
|
abstract: item.abstract || page?.abstract || "",
|
|
@@ -456,7 +497,7 @@ async function decorateMenuPage_(item, routes, store, params = {}) {
|
|
|
456
497
|
}
|
|
457
498
|
|
|
458
499
|
// src/decorators/nav.ts
|
|
459
|
-
var
|
|
500
|
+
var import_bom_core4 = require("@websolutespa/bom-core");
|
|
460
501
|
async function decorateNav_(store, item, params = {}, routes) {
|
|
461
502
|
if (!routes) {
|
|
462
503
|
routes = await store.route.findMany({
|
|
@@ -486,12 +527,12 @@ async function decorateNavs_(store, items, params = {}) {
|
|
|
486
527
|
return items;
|
|
487
528
|
}
|
|
488
529
|
function collectNavs_(item, navs = []) {
|
|
489
|
-
if ((0,
|
|
530
|
+
if ((0, import_bom_core4.isUndecoratedNav)(item)) {
|
|
490
531
|
navs.push(item);
|
|
491
532
|
}
|
|
492
|
-
if ((0,
|
|
533
|
+
if ((0, import_bom_core4.isArray)(item)) {
|
|
493
534
|
item.forEach((x) => collectNavs_(x, navs));
|
|
494
|
-
} else if ((0,
|
|
535
|
+
} else if ((0, import_bom_core4.isObject)(item)) {
|
|
495
536
|
Object.values(item).forEach((value) => {
|
|
496
537
|
collectNavs_(value, navs);
|
|
497
538
|
});
|
|
@@ -521,7 +562,7 @@ function decorateNav__(item, routes) {
|
|
|
521
562
|
}
|
|
522
563
|
|
|
523
564
|
// src/decorators/optimize.ts
|
|
524
|
-
var
|
|
565
|
+
var import_bom_core5 = require("@websolutespa/bom-core");
|
|
525
566
|
async function optimizeOne_(item) {
|
|
526
567
|
const validEntries = Object.entries(item).filter(([key, value]) => {
|
|
527
568
|
switch (key) {
|
|
@@ -529,7 +570,7 @@ async function optimizeOne_(item) {
|
|
|
529
570
|
case "meta":
|
|
530
571
|
return false;
|
|
531
572
|
default:
|
|
532
|
-
if ((0,
|
|
573
|
+
if ((0, import_bom_core5.isUnresolvedRelation)(value) || Array.isArray(value) && value.reduce((p, c) => p && (0, import_bom_core5.isUnresolvedRelation)(c), true)) {
|
|
533
574
|
return false;
|
|
534
575
|
}
|
|
535
576
|
}
|
|
@@ -547,7 +588,7 @@ async function optimizeMany_(items) {
|
|
|
547
588
|
}
|
|
548
589
|
|
|
549
590
|
// src/decorators/relation.ts
|
|
550
|
-
var
|
|
591
|
+
var import_bom_core6 = require("@websolutespa/bom-core");
|
|
551
592
|
var SERVICE_DEFAULT_DEPTH = 3;
|
|
552
593
|
async function decorateRelation_(store, item, params = {}) {
|
|
553
594
|
const depth = params.depth != null ? params.depth : SERVICE_DEFAULT_DEPTH;
|
|
@@ -564,7 +605,7 @@ async function decorateRelations_(store, items, params = {}) {
|
|
|
564
605
|
return items;
|
|
565
606
|
}
|
|
566
607
|
async function collectRelations_(context, item, relations = []) {
|
|
567
|
-
if ((0,
|
|
608
|
+
if ((0, import_bom_core6.isUnresolvedRelation)(item)) {
|
|
568
609
|
const index = relations.findIndex(
|
|
569
610
|
(x) => x.relationTo === item.relationTo && x.value === item.value
|
|
570
611
|
);
|
|
@@ -593,13 +634,13 @@ async function collectRelations_(context, item, relations = []) {
|
|
|
593
634
|
} else {
|
|
594
635
|
return relations[index].resolvedValue;
|
|
595
636
|
}
|
|
596
|
-
} else if ((0,
|
|
637
|
+
} else if ((0, import_bom_core6.isArray)(item)) {
|
|
597
638
|
const items = [];
|
|
598
639
|
for (let i = 0; i < item.length; i++) {
|
|
599
640
|
items[i] = await collectRelations_(context, item[i], relations);
|
|
600
641
|
}
|
|
601
642
|
return items;
|
|
602
|
-
} else if ((0,
|
|
643
|
+
} else if ((0, import_bom_core6.isObject)(item)) {
|
|
603
644
|
for (const [key, value] of Object.entries(item)) {
|
|
604
645
|
item[key] = await collectRelations_(context, value, relations);
|
|
605
646
|
}
|
|
@@ -618,12 +659,12 @@ async function decorateSchemas_(store, items, schema) {
|
|
|
618
659
|
}
|
|
619
660
|
|
|
620
661
|
// src/local/local.api.ts
|
|
621
|
-
var
|
|
662
|
+
var import_bom_core7 = require("@websolutespa/bom-core");
|
|
622
663
|
var API_URL = process.env.NEXT_PUBLIC_URL === "https://" ? process.env.NEXT_PUBLIC_MOCK_FALLBACK_URL : process.env.NEXT_PUBLIC_URL;
|
|
623
664
|
var API_BASE = process.env.NEXT_PUBLIC_API || "/api";
|
|
624
665
|
function getLocalApiUrl(pathname) {
|
|
625
|
-
let url = `${
|
|
626
|
-
url =
|
|
666
|
+
let url = `${import_bom_core7.isBrowser ? window.location.origin : API_URL}${API_BASE}${pathname}`;
|
|
667
|
+
url = import_bom_core7.isBrowser ? url : url.replace("://localhost", "://127.0.0.1");
|
|
627
668
|
return url;
|
|
628
669
|
}
|
|
629
670
|
async function localApiFetch(pathname, options = {}, serviceOptions) {
|
|
@@ -632,9 +673,9 @@ async function localApiFetch(pathname, options = {}, serviceOptions) {
|
|
|
632
673
|
url.searchParams.append("locale", serviceOptions.locale);
|
|
633
674
|
url.searchParams.append("market", serviceOptions.market);
|
|
634
675
|
}
|
|
635
|
-
const apiOptions = (0,
|
|
676
|
+
const apiOptions = (0, import_bom_core7.merge)({ ...getLocalApiRequestOptions() }, options);
|
|
636
677
|
console.log("localApiFetch", apiOptions.method, url.href);
|
|
637
|
-
const apiResponse = await (0,
|
|
678
|
+
const apiResponse = await (0, import_bom_core7.httpFetch)(url.href, apiOptions);
|
|
638
679
|
return apiResponse;
|
|
639
680
|
}
|
|
640
681
|
async function localApiGet(url, options = {}, serviceOptions) {
|
|
@@ -673,8 +714,8 @@ function isApiRequest(request) {
|
|
|
673
714
|
}
|
|
674
715
|
|
|
675
716
|
// src/mock/mock.service.ts
|
|
676
|
-
var
|
|
677
|
-
var MockService = class extends
|
|
717
|
+
var import_bom_core8 = require("@websolutespa/bom-core");
|
|
718
|
+
var MockService = class extends import_bom_core8.JsonService {
|
|
678
719
|
constructor(items, store) {
|
|
679
720
|
super(items);
|
|
680
721
|
this.store = store;
|
|
@@ -759,19 +800,19 @@ var MockPageService = class extends MockService {
|
|
|
759
800
|
};
|
|
760
801
|
|
|
761
802
|
// src/mock/mock.api.ts
|
|
762
|
-
var
|
|
803
|
+
var import_bom_core9 = require("@websolutespa/bom-core");
|
|
763
804
|
var API_URL2 = process.env.NEXT_PUBLIC_URL;
|
|
764
805
|
var API_BASE3 = process.env.NEXT_PUBLIC_API || "/api";
|
|
765
806
|
function getMockApiUrl(pathname) {
|
|
766
807
|
let url = `${API_URL2}${API_BASE3}/_mock${pathname}`;
|
|
767
|
-
url =
|
|
808
|
+
url = import_bom_core9.isBrowser ? url : url.replace("://localhost", "://127.0.0.1");
|
|
768
809
|
return url;
|
|
769
810
|
}
|
|
770
811
|
async function mockApiFetch(pathname, options = {}) {
|
|
771
812
|
const url = getMockApiUrl(pathname);
|
|
772
|
-
const apiOptions = (0,
|
|
813
|
+
const apiOptions = (0, import_bom_core9.merge)({ ...getLocalApiRequestOptions() }, options);
|
|
773
814
|
console.log("mockApiFetch", apiOptions.method, url);
|
|
774
|
-
const apiResponse = await (0,
|
|
815
|
+
const apiResponse = await (0, import_bom_core9.httpFetch)(url, apiOptions);
|
|
775
816
|
return apiResponse;
|
|
776
817
|
}
|
|
777
818
|
async function mockApiGet(url, options = {}) {
|
|
@@ -791,7 +832,7 @@ async function mockApiDelete(url, options = {}) {
|
|
|
791
832
|
}
|
|
792
833
|
|
|
793
834
|
// src/store/store.handler.ts
|
|
794
|
-
var
|
|
835
|
+
var import_bom_core15 = require("@websolutespa/bom-core");
|
|
795
836
|
|
|
796
837
|
// src/static/static.ts
|
|
797
838
|
var staticCollections = [{
|
|
@@ -1066,7 +1107,7 @@ var KNOWN_COLLECTIONS = [
|
|
|
1066
1107
|
var COLLECTIONS = [...ENV_COLLECTIONS, ...KNOWN_COLLECTIONS];
|
|
1067
1108
|
|
|
1068
1109
|
// src/mock/mock.store.ts
|
|
1069
|
-
var
|
|
1110
|
+
var import_bom_core11 = require("@websolutespa/bom-core");
|
|
1070
1111
|
|
|
1071
1112
|
// src/fs/fs.service.ts
|
|
1072
1113
|
var fs = __toESM(require("fs"));
|
|
@@ -1094,8 +1135,8 @@ async function fsReadJson(pathname) {
|
|
|
1094
1135
|
}
|
|
1095
1136
|
|
|
1096
1137
|
// src/static/static.service.ts
|
|
1097
|
-
var
|
|
1098
|
-
var StaticService = class extends
|
|
1138
|
+
var import_bom_core10 = require("@websolutespa/bom-core");
|
|
1139
|
+
var StaticService = class extends import_bom_core10.JsonService {
|
|
1099
1140
|
constructor(config, store) {
|
|
1100
1141
|
super([]);
|
|
1101
1142
|
this.loaded = false;
|
|
@@ -1123,7 +1164,7 @@ var StaticService = class extends import_bom_core9.JsonService {
|
|
|
1123
1164
|
const config = this.config;
|
|
1124
1165
|
const src = config.src;
|
|
1125
1166
|
if (typeof src === "string") {
|
|
1126
|
-
const response = await (0,
|
|
1167
|
+
const response = await (0, import_bom_core10.httpGet)(src, {});
|
|
1127
1168
|
items = response.items;
|
|
1128
1169
|
} else if (typeof src === "function") {
|
|
1129
1170
|
if (src instanceof Promise) {
|
|
@@ -1239,7 +1280,7 @@ function getMockStoreFromData_(data) {
|
|
|
1239
1280
|
return store;
|
|
1240
1281
|
}
|
|
1241
1282
|
async function getStoreData_() {
|
|
1242
|
-
if (
|
|
1283
|
+
if (import_bom_core11.isDevelopment) {
|
|
1243
1284
|
const path = require("path");
|
|
1244
1285
|
const pathname = path.join(process.cwd(), ".mixer", "store.json");
|
|
1245
1286
|
return await fsReadJson(pathname) || {};
|
|
@@ -1255,17 +1296,17 @@ async function getMockStore_() {
|
|
|
1255
1296
|
}
|
|
1256
1297
|
async function getMockStore() {
|
|
1257
1298
|
return fromCache(async () => {
|
|
1258
|
-
if (!
|
|
1299
|
+
if (!import_bom_core11.isDevelopment) {
|
|
1259
1300
|
console.warn("getMockStore");
|
|
1260
1301
|
}
|
|
1261
1302
|
const store = await getMockStore_();
|
|
1262
1303
|
return store;
|
|
1263
|
-
},
|
|
1304
|
+
}, import_bom_core11.isDevelopment ? void 0 : "STORE_MOCK_");
|
|
1264
1305
|
}
|
|
1265
1306
|
|
|
1266
1307
|
// src/cached/cached.service.ts
|
|
1267
|
-
var
|
|
1268
|
-
var CachedService = class extends
|
|
1308
|
+
var import_bom_core12 = require("@websolutespa/bom-core");
|
|
1309
|
+
var CachedService = class extends import_bom_core12.JsonService {
|
|
1269
1310
|
constructor(service, options = {}) {
|
|
1270
1311
|
super([]);
|
|
1271
1312
|
this.cache_ = /* @__PURE__ */ new Map();
|
|
@@ -1304,7 +1345,7 @@ var CachedService = class extends import_bom_core11.JsonService {
|
|
|
1304
1345
|
});
|
|
1305
1346
|
}
|
|
1306
1347
|
async findOne(id, params = {}) {
|
|
1307
|
-
const serializedParams = (0,
|
|
1348
|
+
const serializedParams = (0, import_bom_core12.qsSerialize)(params);
|
|
1308
1349
|
const key = `findOne[${id}]?${serializedParams}`;
|
|
1309
1350
|
return await this.fromCache_(async () => {
|
|
1310
1351
|
return await this.service_.findOne(id, params);
|
|
@@ -1313,7 +1354,7 @@ var CachedService = class extends import_bom_core11.JsonService {
|
|
|
1313
1354
|
async findMany(params = {}) {
|
|
1314
1355
|
if (storeStrategy === "decoratedApi" /* DecoratedApi */) {
|
|
1315
1356
|
const { market, locale, ...otherParams } = params;
|
|
1316
|
-
const serializedParams = (0,
|
|
1357
|
+
const serializedParams = (0, import_bom_core12.qsSerialize)({ market, locale });
|
|
1317
1358
|
const key = `findMany?${serializedParams}`;
|
|
1318
1359
|
let items = await this.fromCache_(async () => {
|
|
1319
1360
|
return await this.service_.findMany({ market, locale });
|
|
@@ -1326,7 +1367,7 @@ var CachedService = class extends import_bom_core11.JsonService {
|
|
|
1326
1367
|
}
|
|
1327
1368
|
return items;
|
|
1328
1369
|
} else {
|
|
1329
|
-
const serializedParams = (0,
|
|
1370
|
+
const serializedParams = (0, import_bom_core12.qsSerialize)(params);
|
|
1330
1371
|
const key = `findMany?${serializedParams}`;
|
|
1331
1372
|
return await this.fromCache_(async () => {
|
|
1332
1373
|
return await this.service_.findMany(params);
|
|
@@ -1334,7 +1375,7 @@ var CachedService = class extends import_bom_core11.JsonService {
|
|
|
1334
1375
|
}
|
|
1335
1376
|
}
|
|
1336
1377
|
async findPaged(params = {}) {
|
|
1337
|
-
const serializedParams = (0,
|
|
1378
|
+
const serializedParams = (0, import_bom_core12.qsSerialize)(params);
|
|
1338
1379
|
const key = `findPaged?${serializedParams}`;
|
|
1339
1380
|
return await this.fromCache_(async () => {
|
|
1340
1381
|
return await this.service_.findPaged(params);
|
|
@@ -1352,22 +1393,22 @@ var CachedService = class extends import_bom_core11.JsonService {
|
|
|
1352
1393
|
};
|
|
1353
1394
|
|
|
1354
1395
|
// src/remote/remote.service.ts
|
|
1355
|
-
var
|
|
1396
|
+
var import_bom_core14 = require("@websolutespa/bom-core");
|
|
1356
1397
|
|
|
1357
1398
|
// src/remote/remote.api.ts
|
|
1358
|
-
var
|
|
1399
|
+
var import_bom_core13 = require("@websolutespa/bom-core");
|
|
1359
1400
|
var API_URL3 = process.env.STORE_URL;
|
|
1360
1401
|
var API_BASE4 = process.env.STORE_API || "/api";
|
|
1361
1402
|
function getRemoteApiUrl(pathname) {
|
|
1362
1403
|
let url = `${API_URL3}${API_BASE4}${pathname}`;
|
|
1363
|
-
url =
|
|
1404
|
+
url = import_bom_core13.isBrowser ? url : url.replace("://localhost", "://127.0.0.1");
|
|
1364
1405
|
return url;
|
|
1365
1406
|
}
|
|
1366
1407
|
async function remoteApiFetch(pathname, options = {}) {
|
|
1367
1408
|
const url = getRemoteApiUrl(pathname);
|
|
1368
|
-
const apiOptions = (0,
|
|
1409
|
+
const apiOptions = (0, import_bom_core13.merge)({ ...getRemoteApiRequestOptions() }, options);
|
|
1369
1410
|
console.log("remoteApiFetch", apiOptions.method, url);
|
|
1370
|
-
const apiResponse = await (0,
|
|
1411
|
+
const apiResponse = await (0, import_bom_core13.httpFetch)(url, apiOptions);
|
|
1371
1412
|
return apiResponse;
|
|
1372
1413
|
}
|
|
1373
1414
|
async function remoteApiGet(url, options = {}) {
|
|
@@ -1404,7 +1445,7 @@ var RemoteService = class {
|
|
|
1404
1445
|
async findOne(id, params = {}) {
|
|
1405
1446
|
params.richText = String(params.richText) === "true" ? true : false;
|
|
1406
1447
|
params.draft = RemoteServiceStrategy.draft;
|
|
1407
|
-
const query = (0,
|
|
1448
|
+
const query = (0, import_bom_core14.qsSerialize)(params);
|
|
1408
1449
|
const search = query ? `?${query}` : "";
|
|
1409
1450
|
const url = `/${this.key}/${encodeURIComponent(id)}${search}`;
|
|
1410
1451
|
const item = await remoteApiGet(url);
|
|
@@ -1417,7 +1458,7 @@ var RemoteService = class {
|
|
|
1417
1458
|
params.richText = String(params.richText) === "true" ? true : false;
|
|
1418
1459
|
params.draft = RemoteServiceStrategy.draft;
|
|
1419
1460
|
params.pagination = false;
|
|
1420
|
-
const query = (0,
|
|
1461
|
+
const query = (0, import_bom_core14.qsSerialize)(params);
|
|
1421
1462
|
const search = query ? `?${query}` : "";
|
|
1422
1463
|
const url = `/${this.key}${search}`;
|
|
1423
1464
|
const response = await remoteApiGet(url);
|
|
@@ -1428,7 +1469,7 @@ var RemoteService = class {
|
|
|
1428
1469
|
params.richText = String(params.richText) === "true" ? true : false;
|
|
1429
1470
|
params.draft = RemoteServiceStrategy.draft;
|
|
1430
1471
|
params.pagination = true;
|
|
1431
|
-
const query = (0,
|
|
1472
|
+
const query = (0, import_bom_core14.qsSerialize)(params);
|
|
1432
1473
|
const search = query ? `?${query}` : "";
|
|
1433
1474
|
const url = `/${this.key}${search}`;
|
|
1434
1475
|
const response = await remoteApiGet(url);
|
|
@@ -1457,7 +1498,7 @@ var RemoteService = class {
|
|
|
1457
1498
|
}
|
|
1458
1499
|
}
|
|
1459
1500
|
};
|
|
1460
|
-
const query = (0,
|
|
1501
|
+
const query = (0, import_bom_core14.qsSerialize)(params);
|
|
1461
1502
|
const search = query ? `?${query}` : "";
|
|
1462
1503
|
const url = `/${this.key}${search}`;
|
|
1463
1504
|
const item = await remoteApiDelete(url);
|
|
@@ -1637,7 +1678,7 @@ function collectionGet(storePromise) {
|
|
|
1637
1678
|
const collection = collections[0];
|
|
1638
1679
|
const id = collections[1];
|
|
1639
1680
|
const qs = Object.entries(query).map((kv) => kv.join("=")).join("&");
|
|
1640
|
-
const params = (0,
|
|
1681
|
+
const params = (0, import_bom_core15.qsDeserialize)(qs);
|
|
1641
1682
|
if (!COLLECTIONS.includes(collection)) {
|
|
1642
1683
|
console.error("storeHandler.collectionGet", "method not allowed", collection);
|
|
1643
1684
|
return response.status(405).send("method not allowed");
|
|
@@ -1649,7 +1690,7 @@ function collectionGet(storePromise) {
|
|
|
1649
1690
|
return response.status(405).send("method not allowed");
|
|
1650
1691
|
}
|
|
1651
1692
|
if (id) {
|
|
1652
|
-
const item = await service.findOne((0,
|
|
1693
|
+
const item = await service.findOne((0, import_bom_core15.asEquatable)(id), params);
|
|
1653
1694
|
if (item) {
|
|
1654
1695
|
return response.status(200).json(item);
|
|
1655
1696
|
} else {
|
|
@@ -1769,8 +1810,8 @@ function storeIndexHandler() {
|
|
|
1769
1810
|
return apiHandler({
|
|
1770
1811
|
get: async (request, response) => {
|
|
1771
1812
|
try {
|
|
1772
|
-
const market =
|
|
1773
|
-
const locale =
|
|
1813
|
+
const market = import_bom_core15.defaultMarket;
|
|
1814
|
+
const locale = import_bom_core15.defaultLocale;
|
|
1774
1815
|
if (!Array.isArray(COLLECTIONS) || COLLECTIONS?.length === 0) {
|
|
1775
1816
|
console.error("apiHome.collectionGet", "collections not found", COLLECTIONS);
|
|
1776
1817
|
return response.status(405).send("method not allowed");
|
|
@@ -2037,10 +2078,10 @@ async function storeApiDelete(url, options = {}) {
|
|
|
2037
2078
|
}
|
|
2038
2079
|
|
|
2039
2080
|
// src/vars/vars.handler.ts
|
|
2040
|
-
var
|
|
2081
|
+
var import_bom_core17 = require("@websolutespa/bom-core");
|
|
2041
2082
|
|
|
2042
2083
|
// ../models/src/route/route.service.ts
|
|
2043
|
-
var
|
|
2084
|
+
var import_bom_core16 = require("@websolutespa/bom-core");
|
|
2044
2085
|
async function getRouteLinkTree(market, locale) {
|
|
2045
2086
|
const store = await getStore();
|
|
2046
2087
|
const routes = await store.route.findMany({
|
|
@@ -2053,8 +2094,8 @@ async function getRouteLinkTree(market, locale) {
|
|
|
2053
2094
|
}
|
|
2054
2095
|
}
|
|
2055
2096
|
});
|
|
2056
|
-
const categories = await store.category.findMany();
|
|
2057
|
-
const rootCategory = (0,
|
|
2097
|
+
const categories = await store.category.findMany({ market, locale });
|
|
2098
|
+
const rootCategory = (0, import_bom_core16.getRootCategory)(categories);
|
|
2058
2099
|
if (rootCategory) {
|
|
2059
2100
|
const root = categoryToRouteLink(routes, categories, rootCategory, locale);
|
|
2060
2101
|
return root;
|
|
@@ -2062,15 +2103,13 @@ async function getRouteLinkTree(market, locale) {
|
|
|
2062
2103
|
return void 0;
|
|
2063
2104
|
}
|
|
2064
2105
|
function categoryToRouteLink(routes, categories, category, locale) {
|
|
2065
|
-
const route = routes.
|
|
2066
|
-
(r) => r.category === category.id && r.isDefault
|
|
2067
|
-
);
|
|
2106
|
+
const route = (0, import_bom_core16.findRouteOfCategory)(routes, category.id);
|
|
2068
2107
|
if (!route) {
|
|
2069
2108
|
return void 0;
|
|
2070
2109
|
}
|
|
2071
|
-
const rootCategory = (0,
|
|
2110
|
+
const rootCategory = (0, import_bom_core16.getRootCategory)(categories);
|
|
2072
2111
|
const childCategories = categories.filter((x) => {
|
|
2073
|
-
const parentId =
|
|
2112
|
+
const parentId = (0, import_bom_core16.asCategoryId)(x.category);
|
|
2074
2113
|
return rootCategory && rootCategory.id === category.id ? x.id !== rootCategory.id && (parentId === category.id || !parentId) : parentId === category.id;
|
|
2075
2114
|
});
|
|
2076
2115
|
const routeLink = newRouteLink(category, route, locale);
|
|
@@ -2082,7 +2121,7 @@ function newRouteLink(category, route, locale) {
|
|
|
2082
2121
|
const id = route?.page || category.id;
|
|
2083
2122
|
const media = category.media || route?.media;
|
|
2084
2123
|
const schema = route?.schema || category?.schema || "unknown";
|
|
2085
|
-
const title = (0,
|
|
2124
|
+
const title = (0, import_bom_core16.localize)(category.title || route?.title || "untitled", locale);
|
|
2086
2125
|
const routeLink = {
|
|
2087
2126
|
category: category.id,
|
|
2088
2127
|
href,
|
|
@@ -2185,10 +2224,10 @@ function varsHandler() {
|
|
|
2185
2224
|
const { locale = defaultLocale3, market = defaultMaket } = request.query || {};
|
|
2186
2225
|
const layout = typeof locale === "string" && typeof market === "string" ? await getLayout(market, locale) : void 0;
|
|
2187
2226
|
const info = {
|
|
2188
|
-
production:
|
|
2189
|
-
development:
|
|
2190
|
-
origin: (0,
|
|
2191
|
-
host: (0,
|
|
2227
|
+
production: import_bom_core17.isProduction,
|
|
2228
|
+
development: import_bom_core17.isDevelopment,
|
|
2229
|
+
origin: (0, import_bom_core17.getOrigin)(request.headers),
|
|
2230
|
+
host: (0, import_bom_core17.getHost)(request.headers),
|
|
2192
2231
|
headers: { ...sortKeys(request.headers) },
|
|
2193
2232
|
env: { ...getFilteredEnv(process.env) },
|
|
2194
2233
|
layout: { ...sortKeys(layout) }
|
package/dist/index.mjs
CHANGED
|
@@ -70,6 +70,7 @@ async function fromCache(callback, key) {
|
|
|
70
70
|
}
|
|
71
71
|
|
|
72
72
|
// src/decorators/category.ts
|
|
73
|
+
import { findRouteOfCategory } from "@websolutespa/bom-core";
|
|
73
74
|
async function decorateCategory_(store, item, params = {}) {
|
|
74
75
|
if (typeof item.category === "string") {
|
|
75
76
|
const categories = await store.category.findMany({
|
|
@@ -82,9 +83,7 @@ async function decorateCategory_(store, item, params = {}) {
|
|
|
82
83
|
if (categories.length > 0) {
|
|
83
84
|
const category = categories[0];
|
|
84
85
|
const routes = await store.route.findMany();
|
|
85
|
-
const route = routes.
|
|
86
|
-
(x) => x.market === params.market && x.locale === params.locale && x.isDefault && x.category === category.id
|
|
87
|
-
);
|
|
86
|
+
const route = findRouteOfCategory(routes, category.id, params.market, params.locale);
|
|
88
87
|
if (route) {
|
|
89
88
|
category.href = route.id;
|
|
90
89
|
}
|
|
@@ -102,7 +101,7 @@ async function decorateCategories_(store, items, params = {}) {
|
|
|
102
101
|
return items.map((item) => {
|
|
103
102
|
const category = categories.find((x) => x.id === item.category);
|
|
104
103
|
if (category) {
|
|
105
|
-
const route = routes
|
|
104
|
+
const route = findRouteOfCategory(routes, category.id);
|
|
106
105
|
if (route) {
|
|
107
106
|
category.href = route.id;
|
|
108
107
|
}
|
|
@@ -183,9 +182,15 @@ async function decorateLocalizables_(items, params = {}) {
|
|
|
183
182
|
|
|
184
183
|
// src/decorators/menu.ts
|
|
185
184
|
import {
|
|
185
|
+
MenuCategoryStrategy,
|
|
186
|
+
asCategoryId,
|
|
187
|
+
findCategoryInCategories,
|
|
188
|
+
findChildCategories,
|
|
189
|
+
findRouteOfCategory as findRouteOfCategory2,
|
|
186
190
|
isEquatable,
|
|
187
191
|
isUndecoratedMenuCategory,
|
|
188
|
-
isUndecoratedMenuPage
|
|
192
|
+
isUndecoratedMenuPage,
|
|
193
|
+
uuidv4
|
|
189
194
|
} from "@websolutespa/bom-core";
|
|
190
195
|
async function decorateMenu_(store, item, params) {
|
|
191
196
|
const { market, locale } = params;
|
|
@@ -261,26 +266,44 @@ function collectUndecoratedPages(items, undecoratedPages = []) {
|
|
|
261
266
|
return undecoratedPages;
|
|
262
267
|
}
|
|
263
268
|
var MAX_INT = 1e12;
|
|
264
|
-
function
|
|
265
|
-
const
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
+
function makeCategoryMenuItem_(item, category) {
|
|
270
|
+
const id = item.id || uuidv4();
|
|
271
|
+
const title = item.title || category.title || "";
|
|
272
|
+
const abstract = item.abstract || void 0;
|
|
273
|
+
const customClass = item.customClass || void 0;
|
|
274
|
+
const media = item.media || category.media;
|
|
275
|
+
const items = [];
|
|
276
|
+
return category.isHidden ? {
|
|
277
|
+
type: "group",
|
|
278
|
+
id,
|
|
279
|
+
title,
|
|
280
|
+
abstract,
|
|
281
|
+
media,
|
|
282
|
+
customClass,
|
|
283
|
+
items
|
|
284
|
+
} : {
|
|
285
|
+
type: "category",
|
|
286
|
+
category: category.id,
|
|
287
|
+
id,
|
|
269
288
|
href: "",
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
289
|
+
title,
|
|
290
|
+
abstract,
|
|
291
|
+
media,
|
|
292
|
+
customClass,
|
|
293
|
+
items
|
|
274
294
|
};
|
|
275
|
-
|
|
295
|
+
}
|
|
296
|
+
function decorateMenuCategory_(item, categories, routes, market, depth = 0) {
|
|
297
|
+
const strategy = item.strategy || MenuCategoryStrategy.Default;
|
|
298
|
+
const categoryId = asCategoryId(item.category);
|
|
299
|
+
const category = categoryId ? categories.find((x) => x.id === categoryId) : void 0;
|
|
276
300
|
if (category) {
|
|
277
|
-
decoratedItem
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
} else {
|
|
301
|
+
const decoratedItem = makeCategoryMenuItem_(item, category);
|
|
302
|
+
if (!category.isHidden) {
|
|
303
|
+
const route = routes.find((route2) => route2.isDefault && route2.resolvedCategory === category.id);
|
|
304
|
+
if (route) {
|
|
305
|
+
decoratedItem.href = route.id;
|
|
306
|
+
}
|
|
284
307
|
}
|
|
285
308
|
let maxDepth = item.maxDepth;
|
|
286
309
|
if (typeof maxDepth === "number") {
|
|
@@ -289,31 +312,55 @@ function decorateMenuCategory_(item, categories, routes, market, depth = 0) {
|
|
|
289
312
|
}
|
|
290
313
|
maxDepth--;
|
|
291
314
|
}
|
|
292
|
-
const childCategories = categories.filter((x) =>
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
315
|
+
const childCategories = (category.id ? categories.filter((x) => asCategoryId(x.category) === category.id) : []).filter((x) => {
|
|
316
|
+
switch (strategy) {
|
|
317
|
+
case MenuCategoryStrategy.ExcludeHidden:
|
|
318
|
+
return Boolean(x.isHidden) === false;
|
|
319
|
+
case MenuCategoryStrategy.Default:
|
|
320
|
+
return true;
|
|
321
|
+
}
|
|
322
|
+
});
|
|
323
|
+
childCategories.sort((a, b) => {
|
|
324
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
325
|
+
});
|
|
326
|
+
const subStrategy = strategy;
|
|
327
|
+
const childCategoryItems = childCategories.map((c) => decorateMenuCategory_({
|
|
328
|
+
id: c.id,
|
|
329
|
+
type: "category",
|
|
330
|
+
category: c.id,
|
|
331
|
+
maxDepth,
|
|
332
|
+
strategy: subStrategy,
|
|
333
|
+
// dispatch sub strategy
|
|
334
|
+
items: []
|
|
335
|
+
}, categories, routes, market, depth + 1));
|
|
336
|
+
const childRoutes = routes.filter((route) => {
|
|
337
|
+
switch (strategy) {
|
|
338
|
+
case MenuCategoryStrategy.ExcludeHidden:
|
|
339
|
+
return route.resolvedCategory === category.id && Boolean(route.isDefault) === false;
|
|
340
|
+
case MenuCategoryStrategy.Default:
|
|
341
|
+
return route.category === category.id && (category.isHidden || Boolean(route.isDefault) === false);
|
|
342
|
+
}
|
|
343
|
+
});
|
|
344
|
+
childRoutes.sort((a, b) => {
|
|
345
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
346
|
+
});
|
|
347
|
+
const childRouteItems = childRoutes.map((x) => decorateMenuRoute_(x));
|
|
348
|
+
decoratedItem.items = [
|
|
349
|
+
...childCategoryItems,
|
|
350
|
+
...childRouteItems
|
|
351
|
+
].filter((x) => Boolean(x));
|
|
352
|
+
return decoratedItem;
|
|
311
353
|
}
|
|
312
|
-
return
|
|
354
|
+
return {
|
|
355
|
+
id: item.id || uuidv4(),
|
|
356
|
+
type: "group",
|
|
357
|
+
title: item.title || "",
|
|
358
|
+
items: []
|
|
359
|
+
};
|
|
313
360
|
}
|
|
314
361
|
function decorateMenuRoute_(item) {
|
|
315
362
|
const decoratedItem = {
|
|
316
|
-
id:
|
|
363
|
+
id: uuidv4(),
|
|
317
364
|
type: "route",
|
|
318
365
|
title: item.title,
|
|
319
366
|
href: item.id,
|
|
@@ -331,7 +378,7 @@ async function decorateMenuPage_(item, routes, store, params = {}) {
|
|
|
331
378
|
);
|
|
332
379
|
const page = await store[item.page.relationTo].findOne(id, { ...params });
|
|
333
380
|
const decoratedItem = {
|
|
334
|
-
id: item.id ||
|
|
381
|
+
id: item.id || uuidv4(),
|
|
335
382
|
type: item.type,
|
|
336
383
|
title: item.title || page?.title || "",
|
|
337
384
|
abstract: item.abstract || page?.abstract || "",
|
|
@@ -1930,7 +1977,7 @@ async function storeApiDelete(url, options = {}) {
|
|
|
1930
1977
|
import { getHost, getOrigin, isDevelopment as isDevelopment2, isProduction } from "@websolutespa/bom-core";
|
|
1931
1978
|
|
|
1932
1979
|
// ../models/src/route/route.service.ts
|
|
1933
|
-
import { asCategoryId, defaultLocale as defaultLocale2, defaultMarket as defaultMarket2, getRootCategory, localize } from "@websolutespa/bom-core";
|
|
1980
|
+
import { asCategoryId as asCategoryId2, defaultLocale as defaultLocale2, defaultMarket as defaultMarket2, findRouteOfCategory as findRouteOfCategory3, getRootCategory, localize } from "@websolutespa/bom-core";
|
|
1934
1981
|
async function getRouteLinkTree(market, locale) {
|
|
1935
1982
|
const store = await getStore();
|
|
1936
1983
|
const routes = await store.route.findMany({
|
|
@@ -1943,7 +1990,7 @@ async function getRouteLinkTree(market, locale) {
|
|
|
1943
1990
|
}
|
|
1944
1991
|
}
|
|
1945
1992
|
});
|
|
1946
|
-
const categories = await store.category.findMany();
|
|
1993
|
+
const categories = await store.category.findMany({ market, locale });
|
|
1947
1994
|
const rootCategory = getRootCategory(categories);
|
|
1948
1995
|
if (rootCategory) {
|
|
1949
1996
|
const root = categoryToRouteLink(routes, categories, rootCategory, locale);
|
|
@@ -1952,15 +1999,13 @@ async function getRouteLinkTree(market, locale) {
|
|
|
1952
1999
|
return void 0;
|
|
1953
2000
|
}
|
|
1954
2001
|
function categoryToRouteLink(routes, categories, category, locale) {
|
|
1955
|
-
const route = routes.
|
|
1956
|
-
(r) => r.category === category.id && r.isDefault
|
|
1957
|
-
);
|
|
2002
|
+
const route = findRouteOfCategory3(routes, category.id);
|
|
1958
2003
|
if (!route) {
|
|
1959
2004
|
return void 0;
|
|
1960
2005
|
}
|
|
1961
2006
|
const rootCategory = getRootCategory(categories);
|
|
1962
2007
|
const childCategories = categories.filter((x) => {
|
|
1963
|
-
const parentId =
|
|
2008
|
+
const parentId = asCategoryId2(x.category);
|
|
1964
2009
|
return rootCategory && rootCategory.id === category.id ? x.id !== rootCategory.id && (parentId === category.id || !parentId) : parentId === category.id;
|
|
1965
2010
|
});
|
|
1966
2011
|
const routeLink = newRouteLink(category, route, locale);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@websolutespa/bom-mixer-store",
|
|
3
|
-
"version": "1.7.
|
|
3
|
+
"version": "1.7.9",
|
|
4
4
|
"description": "Mixer Store module of the BOM Repository",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"bom",
|
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
"scripts": {
|
|
16
16
|
"lint": "eslint *.ts*",
|
|
17
17
|
"test": "jest",
|
|
18
|
-
"test-watch": "npm test -- --watch",
|
|
18
|
+
"test-watch": "npm test -- --watch --silent=false",
|
|
19
19
|
"coverage:integration": "npm run test -- --coverage",
|
|
20
20
|
"coverage": "run-s -c --silent coverage:*",
|
|
21
21
|
"compile": "tsup ./src/index.ts --format esm,cjs --dts",
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ICategorized, ICategory, IRoute, IStore, QueryParams } from '@websolutespa/bom-core';
|
|
1
|
+
import { ICategorized, ICategory, IRoute, IStore, QueryParams, findRouteOfCategory } from '@websolutespa/bom-core';
|
|
2
2
|
|
|
3
3
|
export async function decorateCategory_<T extends ICategorized = ICategorized>(store: IStore, item: T, params: QueryParams = {}): Promise<T | (T & { category: ICategory })> {
|
|
4
4
|
if (typeof item.category === 'string') {
|
|
@@ -12,12 +12,7 @@ export async function decorateCategory_<T extends ICategorized = ICategorized>(s
|
|
|
12
12
|
if (categories.length > 0) {
|
|
13
13
|
const category = categories[0];
|
|
14
14
|
const routes = await store.route.findMany<IRoute>();
|
|
15
|
-
const route = routes.
|
|
16
|
-
x.market === params.market &&
|
|
17
|
-
x.locale === params.locale &&
|
|
18
|
-
x.isDefault &&
|
|
19
|
-
x.category === category.id
|
|
20
|
-
);
|
|
15
|
+
const route = findRouteOfCategory(routes, category.id, params.market, params.locale);
|
|
21
16
|
if (route) {
|
|
22
17
|
category.href = route.id;
|
|
23
18
|
}
|
|
@@ -36,7 +31,7 @@ export async function decorateCategories_<T extends ICategorized = ICategorized>
|
|
|
36
31
|
return items.map(item => {
|
|
37
32
|
const category = categories.find(x => x.id === item.category);
|
|
38
33
|
if (category) {
|
|
39
|
-
const route = routes
|
|
34
|
+
const route = findRouteOfCategory(routes, category.id);
|
|
40
35
|
if (route) {
|
|
41
36
|
category.href = route.id;
|
|
42
37
|
}
|
package/src/decorators/menu.ts
CHANGED
|
@@ -1,7 +1,12 @@
|
|
|
1
1
|
import {
|
|
2
|
-
ICategorized, ICategory, IMenu, IMenuCategory, IMenuItem, IMenuPage, IMenuRoute, IRoute,
|
|
3
|
-
|
|
4
|
-
|
|
2
|
+
ICategorized, ICategory, IMenu, IMenuCategory, IMenuGroup, IMenuItem, IMenuPage, IMenuRoute, IRoute, IStore,
|
|
3
|
+
IUndecoratedMenu, IUndecoratedMenuCategory, IUndecoratedMenuItem, IUndecoratedMenuPage, MenuCategoryStrategy, QueryParams,
|
|
4
|
+
asCategoryId,
|
|
5
|
+
findCategoryInCategories,
|
|
6
|
+
findChildCategories,
|
|
7
|
+
findRouteOfCategory,
|
|
8
|
+
isEquatable, isUndecoratedMenuCategory, isUndecoratedMenuPage,
|
|
9
|
+
uuidv4
|
|
5
10
|
} from '@websolutespa/bom-core';
|
|
6
11
|
|
|
7
12
|
export async function decorateMenu_(store: IStore, item: IUndecoratedMenu, params: { market: string, locale: string }): Promise<IMenu> {
|
|
@@ -88,33 +93,150 @@ function collectUndecoratedPages(items: IUndecoratedMenuItem[], undecoratedPages
|
|
|
88
93
|
|
|
89
94
|
export const MAX_INT = 1000000000000; // 9007199254740991
|
|
90
95
|
|
|
96
|
+
function makeCategoryMenuItem_(item: IUndecoratedMenuCategory, category: ICategory): IMenuCategory | IMenuGroup {
|
|
97
|
+
const id = item.id || uuidv4();
|
|
98
|
+
const title = item.title || category.title || '';
|
|
99
|
+
const abstract = item.abstract || undefined;
|
|
100
|
+
const customClass = item.customClass || undefined;
|
|
101
|
+
const media = item.media || category.media;
|
|
102
|
+
const items: IMenuItem[] = [];
|
|
103
|
+
return category.isHidden ?
|
|
104
|
+
{
|
|
105
|
+
type: 'group',
|
|
106
|
+
id,
|
|
107
|
+
title,
|
|
108
|
+
abstract,
|
|
109
|
+
media,
|
|
110
|
+
customClass,
|
|
111
|
+
items,
|
|
112
|
+
} : {
|
|
113
|
+
type: 'category',
|
|
114
|
+
category: category.id,
|
|
115
|
+
id,
|
|
116
|
+
href: '',
|
|
117
|
+
title,
|
|
118
|
+
abstract,
|
|
119
|
+
media,
|
|
120
|
+
customClass,
|
|
121
|
+
items,
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
|
|
91
125
|
function decorateMenuCategory_(
|
|
92
126
|
item: IUndecoratedMenuCategory,
|
|
93
127
|
categories: ICategory[],
|
|
94
128
|
routes: IRoute[],
|
|
95
129
|
market: string,
|
|
96
130
|
depth: number = 0
|
|
131
|
+
): IMenuItem | undefined {
|
|
132
|
+
const strategy = item.strategy || MenuCategoryStrategy.Default;
|
|
133
|
+
const categoryId = asCategoryId(item.category);
|
|
134
|
+
// find category
|
|
135
|
+
const category = categoryId ? categories.find(x => x.id === categoryId) : undefined;
|
|
136
|
+
if (category) {
|
|
137
|
+
const decoratedItem = makeCategoryMenuItem_(item, category);
|
|
138
|
+
if (!category.isHidden) {
|
|
139
|
+
const route = routes.find((route: IRoute) => route.isDefault && route.resolvedCategory === category.id);
|
|
140
|
+
if (route) {
|
|
141
|
+
(decoratedItem as IMenuCategory).href = route.id;
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
// checking for max depth recursion
|
|
145
|
+
let maxDepth = item.maxDepth;
|
|
146
|
+
if (typeof maxDepth === 'number') {
|
|
147
|
+
if (depth > maxDepth) {
|
|
148
|
+
return decoratedItem;
|
|
149
|
+
}
|
|
150
|
+
maxDepth--;
|
|
151
|
+
}
|
|
152
|
+
// search child categories
|
|
153
|
+
const childCategories = (category.id ?
|
|
154
|
+
categories.filter(x => asCategoryId(x.category) === category.id) : []
|
|
155
|
+
).filter(x => {
|
|
156
|
+
switch (strategy) {
|
|
157
|
+
case MenuCategoryStrategy.ExcludeHidden:
|
|
158
|
+
return Boolean(x.isHidden) === false;
|
|
159
|
+
case MenuCategoryStrategy.Default:
|
|
160
|
+
return true;
|
|
161
|
+
}
|
|
162
|
+
});
|
|
163
|
+
// sort child categories
|
|
164
|
+
childCategories.sort((a, b) => {
|
|
165
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
166
|
+
});
|
|
167
|
+
// define sub strategy (!!! todo)
|
|
168
|
+
const subStrategy = strategy;
|
|
169
|
+
// decorate child categories
|
|
170
|
+
const childCategoryItems = childCategories.map(c => decorateMenuCategory_({
|
|
171
|
+
id: c.id,
|
|
172
|
+
type: 'category',
|
|
173
|
+
category: c.id,
|
|
174
|
+
maxDepth,
|
|
175
|
+
strategy: subStrategy, // dispatch sub strategy
|
|
176
|
+
items: [],
|
|
177
|
+
} as IUndecoratedMenuCategory, categories, routes, market, depth + 1));
|
|
178
|
+
// find child routes
|
|
179
|
+
const childRoutes = routes.filter((route: IRoute) => {
|
|
180
|
+
switch (strategy) {
|
|
181
|
+
case MenuCategoryStrategy.ExcludeHidden:
|
|
182
|
+
return route.resolvedCategory === category.id && Boolean(route.isDefault) === false;
|
|
183
|
+
case MenuCategoryStrategy.Default:
|
|
184
|
+
return route.category === category.id && (category.isHidden || Boolean(route.isDefault) === false);
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
// sort child routes
|
|
188
|
+
childRoutes.sort((a, b) => {
|
|
189
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
190
|
+
});
|
|
191
|
+
// decorate child routes
|
|
192
|
+
const childRouteItems: IMenuItem[] = childRoutes.map(x => decorateMenuRoute_(x));
|
|
193
|
+
// filter items
|
|
194
|
+
decoratedItem.items = [
|
|
195
|
+
...childCategoryItems,
|
|
196
|
+
...childRouteItems,
|
|
197
|
+
].filter(x => Boolean(x)) as IMenuItem[];
|
|
198
|
+
return decoratedItem;
|
|
199
|
+
}
|
|
200
|
+
// return unresolved category as group
|
|
201
|
+
return {
|
|
202
|
+
id: item.id || uuidv4(),
|
|
203
|
+
type: 'group',
|
|
204
|
+
title: item.title || '',
|
|
205
|
+
items: [],
|
|
206
|
+
};
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
function decorateMenuCategoryWithHiddenSubCategories_(
|
|
210
|
+
item: IUndecoratedMenuCategory,
|
|
211
|
+
categories: ICategory[],
|
|
212
|
+
routes: IRoute[],
|
|
213
|
+
market: string,
|
|
214
|
+
depth: number = 0
|
|
97
215
|
): IMenuItem {
|
|
98
216
|
const decoratedItem: IMenuCategory = {
|
|
99
217
|
abstract: item.abstract,
|
|
100
218
|
category: '',
|
|
101
219
|
customClass: item.customClass,
|
|
102
220
|
href: '',
|
|
103
|
-
id: item.id ||
|
|
221
|
+
id: item.id || uuidv4(),
|
|
104
222
|
items: [],
|
|
105
223
|
title: '',
|
|
106
224
|
type: item.type,
|
|
107
225
|
};
|
|
108
|
-
|
|
226
|
+
/*
|
|
227
|
+
const categoryId = asCategoryId(item.category);
|
|
228
|
+
const category = categoryId ? categories.find(x => x.id === categoryId) : undefined;
|
|
229
|
+
*/
|
|
230
|
+
const category = findCategoryInCategories(categories, item.category);
|
|
109
231
|
if (category) {
|
|
110
232
|
// assigning category id
|
|
111
233
|
decoratedItem.category = category.id;
|
|
112
234
|
// assigning category title
|
|
113
235
|
decoratedItem.title = item.title || category.title || '';
|
|
114
236
|
// assigning current or category media
|
|
115
|
-
decoratedItem.media =
|
|
237
|
+
decoratedItem.media = item.media || category.media;
|
|
116
238
|
// find category's index page route
|
|
117
|
-
const route = routes
|
|
239
|
+
const route = findRouteOfCategory(routes, category.id);
|
|
118
240
|
if (route) {
|
|
119
241
|
// hasLink
|
|
120
242
|
decoratedItem.href = route.id;
|
|
@@ -130,32 +252,69 @@ function decorateMenuCategory_(
|
|
|
130
252
|
maxDepth--;
|
|
131
253
|
}
|
|
132
254
|
// search child categories
|
|
133
|
-
const childCategories = categories.
|
|
134
|
-
x.category && (typeof x.category === 'object' ?
|
|
135
|
-
x.category.id === category.id :
|
|
136
|
-
x.category === category.id)
|
|
137
|
-
));
|
|
255
|
+
const childCategories = findChildCategories(categories, category.id);
|
|
138
256
|
if (childCategories.length) {
|
|
139
257
|
// sort child categories
|
|
140
258
|
childCategories.sort((a, b) => {
|
|
141
259
|
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
142
260
|
});
|
|
143
|
-
decoratedItem.items = childCategories.map(c =>
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
261
|
+
decoratedItem.items = childCategories.map(c => {
|
|
262
|
+
const menuCategory = decorateMenuCategoryWithHiddenSubCategories_({
|
|
263
|
+
id: c.id,
|
|
264
|
+
type: 'category',
|
|
265
|
+
category: c.id,
|
|
266
|
+
maxDepth,
|
|
267
|
+
items: [],
|
|
268
|
+
} as IUndecoratedMenuCategory, categories, routes, market, depth + 1);
|
|
269
|
+
if (c.isHidden) {
|
|
270
|
+
const group: IMenuGroup = {
|
|
271
|
+
id: c.id,
|
|
272
|
+
type: 'group',
|
|
273
|
+
title: c.title,
|
|
274
|
+
items: [
|
|
275
|
+
...(menuCategory.items || []),
|
|
276
|
+
],
|
|
277
|
+
};
|
|
278
|
+
// find child routes
|
|
279
|
+
// const childRoutes = findRoutesOfCategory(routes, c.id, false);
|
|
280
|
+
const childRoutes = routes.filter((route: IRoute) =>
|
|
281
|
+
route.category === c.id &&
|
|
282
|
+
Boolean(route.isDefault) === false
|
|
283
|
+
);
|
|
284
|
+
// sort child routes
|
|
285
|
+
childRoutes.sort((a, b) => {
|
|
286
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
287
|
+
});
|
|
288
|
+
const routeLinks = childRoutes.map(x => decorateMenuRoute_(x));
|
|
289
|
+
group.items?.push(...routeLinks);
|
|
290
|
+
return group;
|
|
291
|
+
} else {
|
|
292
|
+
return decorateMenuCategoryWithHiddenSubCategories_({
|
|
293
|
+
id: c.id,
|
|
294
|
+
type: 'category',
|
|
295
|
+
category: c.id,
|
|
296
|
+
maxDepth,
|
|
297
|
+
items: [],
|
|
298
|
+
} as IUndecoratedMenuCategory, categories, routes, market, depth + 1);
|
|
299
|
+
}
|
|
156
300
|
});
|
|
157
|
-
decoratedItem.items = childRoutes.map(x => decorateMenuRoute_(x));
|
|
158
301
|
}
|
|
302
|
+
// find child routes
|
|
303
|
+
// const childRoutes = findRoutesOfCategory(routes, category.id, false);
|
|
304
|
+
const childRoutes = routes.filter((route: IRoute) =>
|
|
305
|
+
route.category === category.id &&
|
|
306
|
+
Boolean(route.isDefault) === false
|
|
307
|
+
);
|
|
308
|
+
// console.log('childRoutes', childRoutes, category.id);
|
|
309
|
+
// sort child routes
|
|
310
|
+
childRoutes.sort((a, b) => {
|
|
311
|
+
return (a.order || MAX_INT) - (b.order || MAX_INT);
|
|
312
|
+
});
|
|
313
|
+
decoratedItem.items = [
|
|
314
|
+
...(decoratedItem.items || []),
|
|
315
|
+
...childRoutes.map(x => decorateMenuRoute_(x)),
|
|
316
|
+
];
|
|
317
|
+
|
|
159
318
|
}
|
|
160
319
|
return decoratedItem;
|
|
161
320
|
}
|
|
@@ -164,7 +323,7 @@ function decorateMenuRoute_(
|
|
|
164
323
|
item: IRoute
|
|
165
324
|
): IMenuItem {
|
|
166
325
|
const decoratedItem: IMenuRoute = {
|
|
167
|
-
id:
|
|
326
|
+
id: uuidv4(),
|
|
168
327
|
type: 'route',
|
|
169
328
|
title: item.title,
|
|
170
329
|
href: item.id,
|
|
@@ -189,7 +348,7 @@ async function decorateMenuPage_(
|
|
|
189
348
|
);
|
|
190
349
|
const page = await store[item.page.relationTo].findOne<ICategorized>(id, { ...params });
|
|
191
350
|
const decoratedItem: IMenuPage = {
|
|
192
|
-
id: item.id ||
|
|
351
|
+
id: item.id || uuidv4(),
|
|
193
352
|
type: item.type,
|
|
194
353
|
title: item.title || page?.title || '',
|
|
195
354
|
abstract: item.abstract || page?.abstract || '',
|