@websolutespa/bom-core 1.8.16 → 1.8.18

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 CHANGED
@@ -1,5 +1,17 @@
1
1
  # @websolutespa/bom-core
2
2
 
3
+ ## 1.8.18
4
+
5
+ ### Patch Changes
6
+
7
+ - Modified: type IComponent
8
+
9
+ ## 1.8.17
10
+
11
+ ### Patch Changes
12
+
13
+ - Added: isMedia, eachMedia, eachValue, isComponent, hasComponents, components utils
14
+
3
15
  ## 1.8.16
4
16
 
5
17
  ### Patch Changes
package/dist/index.d.ts CHANGED
@@ -132,12 +132,6 @@ type IAnchor = {
132
132
  title: string;
133
133
  };
134
134
 
135
- type IComponent = {
136
- schema: string;
137
- anchor?: IAnchor;
138
- [key: string]: unknown;
139
- };
140
-
141
135
  type IEquatable = number | string;
142
136
  type SchemaType = string;
143
137
  type ISchema = {
@@ -166,6 +160,17 @@ type IFeatureType = IEntity & {
166
160
  features: IFeature[];
167
161
  };
168
162
 
163
+ type Headings = 'h1' | 'h2' | 'h3' | 'h4' | 'h5' | 'h6';
164
+
165
+ type IComponent = {
166
+ id?: IEquatable;
167
+ blockType?: string;
168
+ schema?: string;
169
+ anchor?: IAnchor;
170
+ seoWeight?: Headings;
171
+ [key: string]: unknown;
172
+ };
173
+
169
174
  type IMediaType = 'image' | 'video' | 'json' | 'pdf' | string;
170
175
  type IMediaInfo = {
171
176
  id: string;
@@ -183,7 +188,7 @@ type IMedia = Record<string, unknown> & Partial<IMediaInfo> & {
183
188
  title?: string;
184
189
  abstract?: string;
185
190
  type: IMediaType;
186
- src: string;
191
+ src?: string;
187
192
  media?: IMedia;
188
193
  width?: string | number;
189
194
  height?: string | number;
@@ -220,6 +225,7 @@ declare function isMediaPdf(media: {
220
225
  type?: string;
221
226
  mimeType?: string;
222
227
  }): media is IMediaPdf;
228
+ declare function isMedia(item: unknown): item is IMedia;
223
229
 
224
230
  type IMeta = {
225
231
  title?: string;
@@ -1179,6 +1185,13 @@ declare function collectFeatureTypes__<T extends IEntity = IEntity>(items: T[],
1179
1185
  */
1180
1186
  declare function collectOptions<T extends IEntity = IEntity>(items: T[], ...keys: string[]): Promise<Partial<Record<keyof T, IOption[]>>>;
1181
1187
 
1188
+ declare function isComponentOfType<T extends Partial<IComponent> = Partial<IComponent>>(item: unknown, ...blockTypes: string[]): item is T;
1189
+ declare function pickComponent(items: IComponent[] | undefined, ...blockTypes: string[]): IComponent[] | undefined;
1190
+ declare function excludeComponent(items: IComponent[] | undefined, ...blockTypes: string[]): IComponent[] | undefined;
1191
+ declare function pickHero(items: IComponent[] | undefined, blockTypes?: string[]): [IComponent[] | undefined, IComponent[] | undefined];
1192
+ declare function prependHero(items: IComponent[] | undefined, hero: IComponent | string, blockType?: string): IComponent[];
1193
+ declare function groupComponents(items: IComponent[] | undefined, blockTypes: string[], blockType: string): IComponent[];
1194
+
1182
1195
  /**
1183
1196
  * Represents a primitive value that can be used in the deep merge operation.
1184
1197
  */
@@ -1198,6 +1211,10 @@ type Dynamic = {
1198
1211
  */
1199
1212
  declare function deepMerge<T extends Dynamic, R extends Dynamic = T>(target?: Partial<T>, source?: Partial<R>): T & R;
1200
1213
 
1214
+ declare function eachMedia(item: unknown, callback: (value: IMedia) => void): void;
1215
+
1216
+ declare function eachValue(item: unknown, callback: (value: unknown) => void): void;
1217
+
1201
1218
  type ListItem<T> = {
1202
1219
  [K in keyof T]: {
1203
1220
  readonly key: string;
@@ -1265,6 +1282,10 @@ declare function isEquatable(item: unknown): item is IEquatable;
1265
1282
  * @returns True if the item is an entity, false otherwise.
1266
1283
  */
1267
1284
  declare function isEntity<T = IEntity>(item: unknown): item is T;
1285
+ declare function isComponent<T = IComponent>(item: unknown): item is T;
1286
+ declare function hasComponents<T = IEntity & {
1287
+ components: IComponent[];
1288
+ }>(item: unknown): item is T;
1268
1289
  /**
1269
1290
  * Checks if the given item is an unresolved relation.
1270
1291
  * @param item The item to check.
@@ -1323,4 +1344,4 @@ declare function asServerProps(props: any): any;
1323
1344
  declare function awaitAll(array: any, callback: (item: any, index: number) => Promise<any>): Promise<any[]>;
1324
1345
  declare function merge(target: any, source: any): any;
1325
1346
 
1326
- export { DeepPartial, Dynamic, FetchError, FetchRequestOptions, FetchService, FindParams, FindWhereParams, IAction, IActionEmailData, IAnchor, ICategorized, ICategory, ICategoryItem, IClassName, IClassNameCollection, IClassNameValue, ICollectionDescription, IComponent, IConfig, IConsentPreference, IContextBaseParams, IContextParams, IDecoratedNav, IEmailConfig, IEndUser, IEntity, IEquatable, IFeature, IFeatureType, IImageResize, ILabel, ILayout, ILegalNotice, ILetter, ILocale, ILocaleId, ILocalizable, ILocalized, ILocalizedMenu, ILocalizedString, IMarket, IMedia, IMediaImage, IMediaInfo, IMediaJson, IMediaPdf, IMediaType, IMediaVideo, IMemoryStore, IMenu, IMenuBase, IMenuCategory, IMenuCustom, IMenuGroup, IMenuHref, IMenuItem, IMenuLink, IMenuPage, IMenuRoute, INamedEntity, IOption, IOverride, IOverrideReturnValue, IOverrideValue, IPackages, IPage, IPageItem, IPageRelation, IPageRelationResult, IPageUnresolvedRelation, IPagedResult, IPaginationResult, IPartial, IPreference, IPrettify, IQuerable, IRedirect, IRoute, IRouteCanonical, IRouteLink, IRouteParams, ISchema, ISerializedCollection, ISerializedStore, IServerSideContext, IServerSideSplatContext, IStaticContext, IStore, ITemplate, ITitledEntity, IUndecoratedMenu, IUndecoratedMenuBase, IUndecoratedMenuCategory, IUndecoratedMenuCustom, IUndecoratedMenuGroup, IUndecoratedMenuItem, IUndecoratedMenuLink, IUndecoratedMenuPage, IUndecoratedNav, ImageStrategy, Json, JsonService, LiteralUnion, Logger, LoggerLevel, MenuCategoryStrategy, NextApiRequestCookies, Operator, PageProps, Pagination, PreviewData, Primitive, QueryParams, RedirectReason, RequireAtLeastOne, RouteStrategy, SchemaType, ServerSidePropsContext, StaticPropsContext, User, UserRole, UserWithRoles, ValueOf, Where, WhereAndOr, WhereBase, WhereField, arrayShuffle, asCategoryId, asEntityId, asEquatable, asEquatableNumber, asEquatableString, asServerProps, asSortedOptions, awaitAll, base64ToString, camelToSnakeCase, cloneItem, collectFeatureTypes, collectFeatureTypes__, collectOptions, collectRoutes, consoleWarn, decryptImageResize, deepMerge, defaultLocale, defaultMarket, eachCategorized, eachMarketLocale, encryptImageToken, enumToList, findCategoryInCategories, findChildCategories, findRouteOfCategory, findRoutesOfCategory, getCategorySegments, getCategorySegmentsByCategory, getClassNames, getCollectionDescription, getEnv, getHost, getIsDevelopment, getIsProduction, getOrigin, getParentCategoriesById, getParentCategory, getProto, getRootCategory, getRouteHref, httpDelete, httpFetch, httpGet, httpPatch, httpPost, httpPut, isArray, isBrowser, isDevelopment, isEntity, isEquatable, isHeaders, isIncomingHttpHeaders, isLocalizedString, isMediaImage, isMediaJson, isMediaPdf, isMediaVideo, isMenuCategory, isMenuGroup, isMenuHref, isMenuLink, isMenuPage, isMenuRoute, isNotNullString, isNumber, isObject, isProduction, isPromise, isRelation, isReservedCollectionDescription, isStage, isString, isUndecoratedCategory, isUndecoratedMenuCategory, isUndecoratedMenuItem, isUndecoratedMenuPage, isUndecoratedNav, isUnresolvedCategory, isUnresolvedRelation, isValidCollectionDescription, isValidString, localize, localizeItem, localizeValue, localizedToString, merge, pascalCaseToCamelCase, pascalCaseToCharCase, pascalCaseToKebabCase, pascalCaseToSnakeCase, passwordStrategy, qsDeserialize, qsDeserializeRaw, qsSerialize, qsSerializeRaw, resolveMediaType, stringToBase64, toCamelCase, toCharCase, toDisplayName, toFindParams, toKebabCase, toPascalCase, toPluralName, toSnakeCase, toTitleCase, toValidCollectionName, unknownCaseToPascalCase, uuidv4, withSchema };
1347
+ export { DeepPartial, Dynamic, FetchError, FetchRequestOptions, FetchService, FindParams, FindWhereParams, Headings, IAction, IActionEmailData, IAnchor, ICategorized, ICategory, ICategoryItem, IClassName, IClassNameCollection, IClassNameValue, ICollectionDescription, IComponent, IConfig, IConsentPreference, IContextBaseParams, IContextParams, IDecoratedNav, IEmailConfig, IEndUser, IEntity, IEquatable, IFeature, IFeatureType, IImageResize, ILabel, ILayout, ILegalNotice, ILetter, ILocale, ILocaleId, ILocalizable, ILocalized, ILocalizedMenu, ILocalizedString, IMarket, IMedia, IMediaImage, IMediaInfo, IMediaJson, IMediaPdf, IMediaType, IMediaVideo, IMemoryStore, IMenu, IMenuBase, IMenuCategory, IMenuCustom, IMenuGroup, IMenuHref, IMenuItem, IMenuLink, IMenuPage, IMenuRoute, INamedEntity, IOption, IOverride, IOverrideReturnValue, IOverrideValue, IPackages, IPage, IPageItem, IPageRelation, IPageRelationResult, IPageUnresolvedRelation, IPagedResult, IPaginationResult, IPartial, IPreference, IPrettify, IQuerable, IRedirect, IRoute, IRouteCanonical, IRouteLink, IRouteParams, ISchema, ISerializedCollection, ISerializedStore, IServerSideContext, IServerSideSplatContext, IStaticContext, IStore, ITemplate, ITitledEntity, IUndecoratedMenu, IUndecoratedMenuBase, IUndecoratedMenuCategory, IUndecoratedMenuCustom, IUndecoratedMenuGroup, IUndecoratedMenuItem, IUndecoratedMenuLink, IUndecoratedMenuPage, IUndecoratedNav, ImageStrategy, Json, JsonService, LiteralUnion, Logger, LoggerLevel, MenuCategoryStrategy, NextApiRequestCookies, Operator, PageProps, Pagination, PreviewData, Primitive, QueryParams, RedirectReason, RequireAtLeastOne, RouteStrategy, SchemaType, ServerSidePropsContext, StaticPropsContext, User, UserRole, UserWithRoles, ValueOf, Where, WhereAndOr, WhereBase, WhereField, arrayShuffle, asCategoryId, asEntityId, asEquatable, asEquatableNumber, asEquatableString, asServerProps, asSortedOptions, awaitAll, base64ToString, camelToSnakeCase, cloneItem, collectFeatureTypes, collectFeatureTypes__, collectOptions, collectRoutes, consoleWarn, decryptImageResize, deepMerge, defaultLocale, defaultMarket, eachCategorized, eachMarketLocale, eachMedia, eachValue, encryptImageToken, enumToList, excludeComponent, findCategoryInCategories, findChildCategories, findRouteOfCategory, findRoutesOfCategory, getCategorySegments, getCategorySegmentsByCategory, getClassNames, getCollectionDescription, getEnv, getHost, getIsDevelopment, getIsProduction, getOrigin, getParentCategoriesById, getParentCategory, getProto, getRootCategory, getRouteHref, groupComponents, hasComponents, httpDelete, httpFetch, httpGet, httpPatch, httpPost, httpPut, isArray, isBrowser, isComponent, isComponentOfType, isDevelopment, isEntity, isEquatable, isHeaders, isIncomingHttpHeaders, isLocalizedString, isMedia, isMediaImage, isMediaJson, isMediaPdf, isMediaVideo, isMenuCategory, isMenuGroup, isMenuHref, isMenuLink, isMenuPage, isMenuRoute, isNotNullString, isNumber, isObject, isProduction, isPromise, isRelation, isReservedCollectionDescription, isStage, isString, isUndecoratedCategory, isUndecoratedMenuCategory, isUndecoratedMenuItem, isUndecoratedMenuPage, isUndecoratedNav, isUnresolvedCategory, isUnresolvedRelation, isValidCollectionDescription, isValidString, localize, localizeItem, localizeValue, localizedToString, merge, pascalCaseToCamelCase, pascalCaseToCharCase, pascalCaseToKebabCase, pascalCaseToSnakeCase, passwordStrategy, pickComponent, pickHero, prependHero, qsDeserialize, qsDeserializeRaw, qsSerialize, qsSerializeRaw, resolveMediaType, stringToBase64, toCamelCase, toCharCase, toDisplayName, toFindParams, toKebabCase, toPascalCase, toPluralName, toSnakeCase, toTitleCase, toValidCollectionName, unknownCaseToPascalCase, uuidv4, withSchema };
package/dist/index.js CHANGED
@@ -60,8 +60,11 @@ __export(src_exports, {
60
60
  defaultMarket: () => defaultMarket,
61
61
  eachCategorized: () => eachCategorized,
62
62
  eachMarketLocale: () => eachMarketLocale,
63
+ eachMedia: () => eachMedia,
64
+ eachValue: () => eachValue,
63
65
  encryptImageToken: () => encryptImageToken,
64
66
  enumToList: () => enumToList,
67
+ excludeComponent: () => excludeComponent,
65
68
  findCategoryInCategories: () => findCategoryInCategories,
66
69
  findChildCategories: () => findChildCategories,
67
70
  findRouteOfCategory: () => findRouteOfCategory,
@@ -80,6 +83,8 @@ __export(src_exports, {
80
83
  getProto: () => getProto,
81
84
  getRootCategory: () => getRootCategory,
82
85
  getRouteHref: () => getRouteHref,
86
+ groupComponents: () => groupComponents,
87
+ hasComponents: () => hasComponents,
83
88
  httpDelete: () => httpDelete,
84
89
  httpFetch: () => httpFetch,
85
90
  httpGet: () => httpGet,
@@ -88,12 +93,15 @@ __export(src_exports, {
88
93
  httpPut: () => httpPut,
89
94
  isArray: () => isArray,
90
95
  isBrowser: () => isBrowser,
96
+ isComponent: () => isComponent,
97
+ isComponentOfType: () => isComponentOfType,
91
98
  isDevelopment: () => isDevelopment,
92
99
  isEntity: () => isEntity,
93
100
  isEquatable: () => isEquatable,
94
101
  isHeaders: () => isHeaders,
95
102
  isIncomingHttpHeaders: () => isIncomingHttpHeaders,
96
103
  isLocalizedString: () => isLocalizedString,
104
+ isMedia: () => isMedia,
97
105
  isMediaImage: () => isMediaImage,
98
106
  isMediaJson: () => isMediaJson,
99
107
  isMediaPdf: () => isMediaPdf,
@@ -132,6 +140,9 @@ __export(src_exports, {
132
140
  pascalCaseToKebabCase: () => pascalCaseToKebabCase,
133
141
  pascalCaseToSnakeCase: () => pascalCaseToSnakeCase,
134
142
  passwordStrategy: () => passwordStrategy,
143
+ pickComponent: () => pickComponent,
144
+ pickHero: () => pickHero,
145
+ prependHero: () => prependHero,
135
146
  qsDeserialize: () => qsDeserialize,
136
147
  qsDeserializeRaw: () => qsDeserializeRaw,
137
148
  qsSerialize: () => qsSerialize,
@@ -187,6 +198,12 @@ function isEquatable(item) {
187
198
  function isEntity(item) {
188
199
  return isObject(item) && isEquatable(item.id);
189
200
  }
201
+ function isComponent(item) {
202
+ return isObject(item) && (isValidString(item.blockType) || isValidString(item.schema));
203
+ }
204
+ function hasComponents(item) {
205
+ return isObject(item) && "components" in item && Array.isArray(item.components) && item.components.length > 0;
206
+ }
190
207
  function isUnresolvedRelation(item) {
191
208
  return isObject(item) && isNotNullString(item.relationTo) && (isEquatable(item.value) || isArray(item.value));
192
209
  }
@@ -417,6 +434,73 @@ async function collectOptions(items, ...keys) {
417
434
  return optionsGroup;
418
435
  }
419
436
 
437
+ // src/utils/uuid.ts
438
+ function uuidv4() {
439
+ return "10000000-1000-4000-8000-100000000000".replace(
440
+ /[018]/g,
441
+ (c) => (+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16)
442
+ );
443
+ }
444
+
445
+ // src/utils/components.ts
446
+ function isComponentOfType(item, ...blockTypes) {
447
+ return isComponent(item) && blockTypes.includes(item.blockType || item.schema || "");
448
+ }
449
+ function pickComponent(items, ...blockTypes) {
450
+ return items?.filter((x) => isComponentOfType(x, ...blockTypes));
451
+ }
452
+ function excludeComponent(items, ...blockTypes) {
453
+ return items?.filter((x) => !isComponentOfType(x, ...blockTypes));
454
+ }
455
+ function pickHero(items, blockTypes = ["hero"]) {
456
+ const heroComponents = pickComponent(items, ...blockTypes);
457
+ const otherComponents = excludeComponent(items, ...blockTypes);
458
+ return [heroComponents, otherComponents];
459
+ }
460
+ function prependHero(items, hero, blockType = "hero") {
461
+ const components = items || [];
462
+ const heroIndex = components.findIndex((x) => isComponentOfType(x, blockType));
463
+ if (heroIndex === -1) {
464
+ const component = typeof hero === "string" ? {
465
+ id: uuidv4(),
466
+ blockType: hero
467
+ } : hero;
468
+ components.unshift(component);
469
+ }
470
+ return components;
471
+ }
472
+ function groupComponents(items, blockTypes, blockType) {
473
+ const components = [];
474
+ let previousGroup;
475
+ let previousItem;
476
+ (items || []).forEach((item) => {
477
+ if (blockTypes.includes(item.blockType || item.schema || "unkown_type")) {
478
+ if (previousItem) {
479
+ if (previousGroup) {
480
+ previousGroup.components.push(item);
481
+ } else {
482
+ previousGroup = {
483
+ id: uuidv4(),
484
+ blockType,
485
+ components: [previousItem, item]
486
+ };
487
+ }
488
+ }
489
+ previousItem = item;
490
+ } else {
491
+ if (previousGroup) {
492
+ components.push(previousGroup);
493
+ } else if (previousItem) {
494
+ components.push(previousItem);
495
+ }
496
+ previousGroup = void 0;
497
+ previousItem = void 0;
498
+ components.push(item);
499
+ }
500
+ });
501
+ return components;
502
+ }
503
+
420
504
  // src/utils/deepMerge.ts
421
505
  function deepMerge(target, source) {
422
506
  const output = { ...target };
@@ -435,6 +519,134 @@ function deepMerge(target, source) {
435
519
  return output;
436
520
  }
437
521
 
522
+ // src/types/image.ts
523
+ var ImageStrategy = /* @__PURE__ */ ((ImageStrategy2) => {
524
+ ImageStrategy2["None"] = "none";
525
+ ImageStrategy2["Next"] = "next";
526
+ ImageStrategy2["Mixer"] = "mixer";
527
+ ImageStrategy2["Oven"] = "oven";
528
+ ImageStrategy2["Token"] = "token";
529
+ ImageStrategy2["Custom"] = "custom";
530
+ return ImageStrategy2;
531
+ })(ImageStrategy || {});
532
+
533
+ // src/types/media.ts
534
+ function resolveMediaType(media) {
535
+ if (typeof media.type === "string" && media.type.length > 0) {
536
+ return media.type;
537
+ }
538
+ if (typeof media.mimeType === "string" && media.mimeType.length > 0) {
539
+ const mime = media.mimeType.split("/");
540
+ return mime[0] === "application" ? mime[1] : mime[0];
541
+ }
542
+ return "unknown";
543
+ }
544
+ function isMediaImage(media) {
545
+ const type = resolveMediaType(media);
546
+ if (type === "image") {
547
+ media.type = type;
548
+ return true;
549
+ }
550
+ return false;
551
+ }
552
+ function isMediaVideo(media) {
553
+ const type = resolveMediaType(media);
554
+ if (type === "video") {
555
+ media.type = type;
556
+ return true;
557
+ }
558
+ return false;
559
+ }
560
+ function isMediaJson(media) {
561
+ const type = resolveMediaType(media);
562
+ if (type === "json") {
563
+ media.type = type;
564
+ return true;
565
+ }
566
+ return false;
567
+ }
568
+ function isMediaPdf(media) {
569
+ const type = resolveMediaType(media);
570
+ if (type === "pdf") {
571
+ media.type = type;
572
+ return true;
573
+ }
574
+ return false;
575
+ }
576
+ function isMedia(item) {
577
+ return isObject(item) && "type" in item && (isValidString(item.url) || isValidString(item.src));
578
+ }
579
+
580
+ // src/types/menu.ts
581
+ function isMenuHref(item) {
582
+ return ["category", "link", "page", "route"].includes(item.type);
583
+ }
584
+ function isMenuCategory(item) {
585
+ return item.type === "category";
586
+ }
587
+ function isMenuGroup(item) {
588
+ return item.type === "group";
589
+ }
590
+ function isMenuLink(item) {
591
+ return item.type === "link";
592
+ }
593
+ function isMenuPage(item) {
594
+ return item.type === "page";
595
+ }
596
+ function isMenuRoute(item) {
597
+ return item.type === "route";
598
+ }
599
+ var MenuCategoryStrategy = /* @__PURE__ */ ((MenuCategoryStrategy2) => {
600
+ MenuCategoryStrategy2["Default"] = "default";
601
+ MenuCategoryStrategy2["ExcludeHidden"] = "exclude-hidden";
602
+ return MenuCategoryStrategy2;
603
+ })(MenuCategoryStrategy || {});
604
+
605
+ // src/types/querable.ts
606
+ function toFindParams(idOrParams) {
607
+ if (typeof idOrParams === "number" || typeof idOrParams === "string") {
608
+ return { where: { id: idOrParams } };
609
+ } else {
610
+ return idOrParams;
611
+ }
612
+ }
613
+
614
+ // src/types/redirect.ts
615
+ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
616
+ RedirectReason2["MovedPermanently"] = "301";
617
+ RedirectReason2["Found"] = "302";
618
+ RedirectReason2["TemporaryRedirect"] = "307";
619
+ RedirectReason2["PermanentRedirect"] = "308";
620
+ RedirectReason2["Gone"] = "410";
621
+ return RedirectReason2;
622
+ })(RedirectReason || {});
623
+
624
+ // src/utils/eachValue.ts
625
+ function eachValue(item, callback) {
626
+ if (isArray(item)) {
627
+ item.forEach((value) => {
628
+ callback(value);
629
+ eachValue(value, callback);
630
+ });
631
+ } else if (isObject(item)) {
632
+ Object.values(item).forEach((value) => {
633
+ callback(value);
634
+ eachValue(value, callback);
635
+ });
636
+ } else {
637
+ callback(item);
638
+ }
639
+ }
640
+
641
+ // src/utils/eachMedia.ts
642
+ function eachMedia(item, callback) {
643
+ eachValue(item, (value) => {
644
+ if (isMedia(value)) {
645
+ callback(value);
646
+ }
647
+ });
648
+ }
649
+
438
650
  // src/utils/enumToList.ts
439
651
  function enumToList(enumeration, separatorRegex = /_/g) {
440
652
  const array = Object.keys(enumeration);
@@ -444,14 +656,6 @@ function enumToList(enumeration, separatorRegex = /_/g) {
444
656
  }));
445
657
  }
446
658
 
447
- // src/utils/uuid.ts
448
- function uuidv4() {
449
- return "10000000-1000-4000-8000-100000000000".replace(
450
- /[018]/g,
451
- (c) => (+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16)
452
- );
453
- }
454
-
455
659
  // src/utils/index.ts
456
660
  function getIsDevelopment() {
457
661
  return process && (!process.env.NODE_ENV || process.env.NODE_ENV === "development");
@@ -1595,105 +1799,6 @@ function getRouteHref(segments, market, locale, markets, locales) {
1595
1799
  const prefix = prefixes.length ? `/${prefixes.join("-")}` : "";
1596
1800
  return `${prefix}${href}`;
1597
1801
  }
1598
-
1599
- // src/types/image.ts
1600
- var ImageStrategy = /* @__PURE__ */ ((ImageStrategy2) => {
1601
- ImageStrategy2["None"] = "none";
1602
- ImageStrategy2["Next"] = "next";
1603
- ImageStrategy2["Mixer"] = "mixer";
1604
- ImageStrategy2["Oven"] = "oven";
1605
- ImageStrategy2["Token"] = "token";
1606
- ImageStrategy2["Custom"] = "custom";
1607
- return ImageStrategy2;
1608
- })(ImageStrategy || {});
1609
-
1610
- // src/types/media.ts
1611
- function resolveMediaType(media) {
1612
- if (typeof media.type === "string" && media.type.length > 0) {
1613
- return media.type;
1614
- }
1615
- if (typeof media.mimeType === "string" && media.mimeType.length > 0) {
1616
- const mime = media.mimeType.split("/");
1617
- return mime[0] === "application" ? mime[1] : mime[0];
1618
- }
1619
- return "unknown";
1620
- }
1621
- function isMediaImage(media) {
1622
- const type = resolveMediaType(media);
1623
- if (type === "image") {
1624
- media.type = type;
1625
- return true;
1626
- }
1627
- return false;
1628
- }
1629
- function isMediaVideo(media) {
1630
- const type = resolveMediaType(media);
1631
- if (type === "video") {
1632
- media.type = type;
1633
- return true;
1634
- }
1635
- return false;
1636
- }
1637
- function isMediaJson(media) {
1638
- const type = resolveMediaType(media);
1639
- if (type === "json") {
1640
- media.type = type;
1641
- return true;
1642
- }
1643
- return false;
1644
- }
1645
- function isMediaPdf(media) {
1646
- const type = resolveMediaType(media);
1647
- if (type === "pdf") {
1648
- media.type = type;
1649
- return true;
1650
- }
1651
- return false;
1652
- }
1653
-
1654
- // src/types/menu.ts
1655
- function isMenuHref(item) {
1656
- return ["category", "link", "page", "route"].includes(item.type);
1657
- }
1658
- function isMenuCategory(item) {
1659
- return item.type === "category";
1660
- }
1661
- function isMenuGroup(item) {
1662
- return item.type === "group";
1663
- }
1664
- function isMenuLink(item) {
1665
- return item.type === "link";
1666
- }
1667
- function isMenuPage(item) {
1668
- return item.type === "page";
1669
- }
1670
- function isMenuRoute(item) {
1671
- return item.type === "route";
1672
- }
1673
- var MenuCategoryStrategy = /* @__PURE__ */ ((MenuCategoryStrategy2) => {
1674
- MenuCategoryStrategy2["Default"] = "default";
1675
- MenuCategoryStrategy2["ExcludeHidden"] = "exclude-hidden";
1676
- return MenuCategoryStrategy2;
1677
- })(MenuCategoryStrategy || {});
1678
-
1679
- // src/types/querable.ts
1680
- function toFindParams(idOrParams) {
1681
- if (typeof idOrParams === "number" || typeof idOrParams === "string") {
1682
- return { where: { id: idOrParams } };
1683
- } else {
1684
- return idOrParams;
1685
- }
1686
- }
1687
-
1688
- // src/types/redirect.ts
1689
- var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1690
- RedirectReason2["MovedPermanently"] = "301";
1691
- RedirectReason2["Found"] = "302";
1692
- RedirectReason2["TemporaryRedirect"] = "307";
1693
- RedirectReason2["PermanentRedirect"] = "308";
1694
- RedirectReason2["Gone"] = "410";
1695
- return RedirectReason2;
1696
- })(RedirectReason || {});
1697
1802
  // Annotate the CommonJS export names for ESM import in node:
1698
1803
  0 && (module.exports = {
1699
1804
  ImageStrategy,
@@ -1726,8 +1831,11 @@ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1726
1831
  defaultMarket,
1727
1832
  eachCategorized,
1728
1833
  eachMarketLocale,
1834
+ eachMedia,
1835
+ eachValue,
1729
1836
  encryptImageToken,
1730
1837
  enumToList,
1838
+ excludeComponent,
1731
1839
  findCategoryInCategories,
1732
1840
  findChildCategories,
1733
1841
  findRouteOfCategory,
@@ -1746,6 +1854,8 @@ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1746
1854
  getProto,
1747
1855
  getRootCategory,
1748
1856
  getRouteHref,
1857
+ groupComponents,
1858
+ hasComponents,
1749
1859
  httpDelete,
1750
1860
  httpFetch,
1751
1861
  httpGet,
@@ -1754,12 +1864,15 @@ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1754
1864
  httpPut,
1755
1865
  isArray,
1756
1866
  isBrowser,
1867
+ isComponent,
1868
+ isComponentOfType,
1757
1869
  isDevelopment,
1758
1870
  isEntity,
1759
1871
  isEquatable,
1760
1872
  isHeaders,
1761
1873
  isIncomingHttpHeaders,
1762
1874
  isLocalizedString,
1875
+ isMedia,
1763
1876
  isMediaImage,
1764
1877
  isMediaJson,
1765
1878
  isMediaPdf,
@@ -1798,6 +1911,9 @@ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1798
1911
  pascalCaseToKebabCase,
1799
1912
  pascalCaseToSnakeCase,
1800
1913
  passwordStrategy,
1914
+ pickComponent,
1915
+ pickHero,
1916
+ prependHero,
1801
1917
  qsDeserialize,
1802
1918
  qsDeserializeRaw,
1803
1919
  qsSerialize,
package/dist/index.mjs CHANGED
@@ -31,6 +31,12 @@ function isEquatable(item) {
31
31
  function isEntity(item) {
32
32
  return isObject(item) && isEquatable(item.id);
33
33
  }
34
+ function isComponent(item) {
35
+ return isObject(item) && (isValidString(item.blockType) || isValidString(item.schema));
36
+ }
37
+ function hasComponents(item) {
38
+ return isObject(item) && "components" in item && Array.isArray(item.components) && item.components.length > 0;
39
+ }
34
40
  function isUnresolvedRelation(item) {
35
41
  return isObject(item) && isNotNullString(item.relationTo) && (isEquatable(item.value) || isArray(item.value));
36
42
  }
@@ -261,6 +267,73 @@ async function collectOptions(items, ...keys) {
261
267
  return optionsGroup;
262
268
  }
263
269
 
270
+ // src/utils/uuid.ts
271
+ function uuidv4() {
272
+ return "10000000-1000-4000-8000-100000000000".replace(
273
+ /[018]/g,
274
+ (c) => (+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16)
275
+ );
276
+ }
277
+
278
+ // src/utils/components.ts
279
+ function isComponentOfType(item, ...blockTypes) {
280
+ return isComponent(item) && blockTypes.includes(item.blockType || item.schema || "");
281
+ }
282
+ function pickComponent(items, ...blockTypes) {
283
+ return items?.filter((x) => isComponentOfType(x, ...blockTypes));
284
+ }
285
+ function excludeComponent(items, ...blockTypes) {
286
+ return items?.filter((x) => !isComponentOfType(x, ...blockTypes));
287
+ }
288
+ function pickHero(items, blockTypes = ["hero"]) {
289
+ const heroComponents = pickComponent(items, ...blockTypes);
290
+ const otherComponents = excludeComponent(items, ...blockTypes);
291
+ return [heroComponents, otherComponents];
292
+ }
293
+ function prependHero(items, hero, blockType = "hero") {
294
+ const components = items || [];
295
+ const heroIndex = components.findIndex((x) => isComponentOfType(x, blockType));
296
+ if (heroIndex === -1) {
297
+ const component = typeof hero === "string" ? {
298
+ id: uuidv4(),
299
+ blockType: hero
300
+ } : hero;
301
+ components.unshift(component);
302
+ }
303
+ return components;
304
+ }
305
+ function groupComponents(items, blockTypes, blockType) {
306
+ const components = [];
307
+ let previousGroup;
308
+ let previousItem;
309
+ (items || []).forEach((item) => {
310
+ if (blockTypes.includes(item.blockType || item.schema || "unkown_type")) {
311
+ if (previousItem) {
312
+ if (previousGroup) {
313
+ previousGroup.components.push(item);
314
+ } else {
315
+ previousGroup = {
316
+ id: uuidv4(),
317
+ blockType,
318
+ components: [previousItem, item]
319
+ };
320
+ }
321
+ }
322
+ previousItem = item;
323
+ } else {
324
+ if (previousGroup) {
325
+ components.push(previousGroup);
326
+ } else if (previousItem) {
327
+ components.push(previousItem);
328
+ }
329
+ previousGroup = void 0;
330
+ previousItem = void 0;
331
+ components.push(item);
332
+ }
333
+ });
334
+ return components;
335
+ }
336
+
264
337
  // src/utils/deepMerge.ts
265
338
  function deepMerge(target, source) {
266
339
  const output = { ...target };
@@ -279,6 +352,134 @@ function deepMerge(target, source) {
279
352
  return output;
280
353
  }
281
354
 
355
+ // src/types/image.ts
356
+ var ImageStrategy = /* @__PURE__ */ ((ImageStrategy2) => {
357
+ ImageStrategy2["None"] = "none";
358
+ ImageStrategy2["Next"] = "next";
359
+ ImageStrategy2["Mixer"] = "mixer";
360
+ ImageStrategy2["Oven"] = "oven";
361
+ ImageStrategy2["Token"] = "token";
362
+ ImageStrategy2["Custom"] = "custom";
363
+ return ImageStrategy2;
364
+ })(ImageStrategy || {});
365
+
366
+ // src/types/media.ts
367
+ function resolveMediaType(media) {
368
+ if (typeof media.type === "string" && media.type.length > 0) {
369
+ return media.type;
370
+ }
371
+ if (typeof media.mimeType === "string" && media.mimeType.length > 0) {
372
+ const mime = media.mimeType.split("/");
373
+ return mime[0] === "application" ? mime[1] : mime[0];
374
+ }
375
+ return "unknown";
376
+ }
377
+ function isMediaImage(media) {
378
+ const type = resolveMediaType(media);
379
+ if (type === "image") {
380
+ media.type = type;
381
+ return true;
382
+ }
383
+ return false;
384
+ }
385
+ function isMediaVideo(media) {
386
+ const type = resolveMediaType(media);
387
+ if (type === "video") {
388
+ media.type = type;
389
+ return true;
390
+ }
391
+ return false;
392
+ }
393
+ function isMediaJson(media) {
394
+ const type = resolveMediaType(media);
395
+ if (type === "json") {
396
+ media.type = type;
397
+ return true;
398
+ }
399
+ return false;
400
+ }
401
+ function isMediaPdf(media) {
402
+ const type = resolveMediaType(media);
403
+ if (type === "pdf") {
404
+ media.type = type;
405
+ return true;
406
+ }
407
+ return false;
408
+ }
409
+ function isMedia(item) {
410
+ return isObject(item) && "type" in item && (isValidString(item.url) || isValidString(item.src));
411
+ }
412
+
413
+ // src/types/menu.ts
414
+ function isMenuHref(item) {
415
+ return ["category", "link", "page", "route"].includes(item.type);
416
+ }
417
+ function isMenuCategory(item) {
418
+ return item.type === "category";
419
+ }
420
+ function isMenuGroup(item) {
421
+ return item.type === "group";
422
+ }
423
+ function isMenuLink(item) {
424
+ return item.type === "link";
425
+ }
426
+ function isMenuPage(item) {
427
+ return item.type === "page";
428
+ }
429
+ function isMenuRoute(item) {
430
+ return item.type === "route";
431
+ }
432
+ var MenuCategoryStrategy = /* @__PURE__ */ ((MenuCategoryStrategy2) => {
433
+ MenuCategoryStrategy2["Default"] = "default";
434
+ MenuCategoryStrategy2["ExcludeHidden"] = "exclude-hidden";
435
+ return MenuCategoryStrategy2;
436
+ })(MenuCategoryStrategy || {});
437
+
438
+ // src/types/querable.ts
439
+ function toFindParams(idOrParams) {
440
+ if (typeof idOrParams === "number" || typeof idOrParams === "string") {
441
+ return { where: { id: idOrParams } };
442
+ } else {
443
+ return idOrParams;
444
+ }
445
+ }
446
+
447
+ // src/types/redirect.ts
448
+ var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
449
+ RedirectReason2["MovedPermanently"] = "301";
450
+ RedirectReason2["Found"] = "302";
451
+ RedirectReason2["TemporaryRedirect"] = "307";
452
+ RedirectReason2["PermanentRedirect"] = "308";
453
+ RedirectReason2["Gone"] = "410";
454
+ return RedirectReason2;
455
+ })(RedirectReason || {});
456
+
457
+ // src/utils/eachValue.ts
458
+ function eachValue(item, callback) {
459
+ if (isArray(item)) {
460
+ item.forEach((value) => {
461
+ callback(value);
462
+ eachValue(value, callback);
463
+ });
464
+ } else if (isObject(item)) {
465
+ Object.values(item).forEach((value) => {
466
+ callback(value);
467
+ eachValue(value, callback);
468
+ });
469
+ } else {
470
+ callback(item);
471
+ }
472
+ }
473
+
474
+ // src/utils/eachMedia.ts
475
+ function eachMedia(item, callback) {
476
+ eachValue(item, (value) => {
477
+ if (isMedia(value)) {
478
+ callback(value);
479
+ }
480
+ });
481
+ }
482
+
282
483
  // src/utils/enumToList.ts
283
484
  function enumToList(enumeration, separatorRegex = /_/g) {
284
485
  const array = Object.keys(enumeration);
@@ -288,14 +489,6 @@ function enumToList(enumeration, separatorRegex = /_/g) {
288
489
  }));
289
490
  }
290
491
 
291
- // src/utils/uuid.ts
292
- function uuidv4() {
293
- return "10000000-1000-4000-8000-100000000000".replace(
294
- /[018]/g,
295
- (c) => (+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16)
296
- );
297
- }
298
-
299
492
  // src/utils/index.ts
300
493
  function getIsDevelopment() {
301
494
  return process && (!process.env.NODE_ENV || process.env.NODE_ENV === "development");
@@ -1439,105 +1632,6 @@ function getRouteHref(segments, market, locale, markets, locales) {
1439
1632
  const prefix = prefixes.length ? `/${prefixes.join("-")}` : "";
1440
1633
  return `${prefix}${href}`;
1441
1634
  }
1442
-
1443
- // src/types/image.ts
1444
- var ImageStrategy = /* @__PURE__ */ ((ImageStrategy2) => {
1445
- ImageStrategy2["None"] = "none";
1446
- ImageStrategy2["Next"] = "next";
1447
- ImageStrategy2["Mixer"] = "mixer";
1448
- ImageStrategy2["Oven"] = "oven";
1449
- ImageStrategy2["Token"] = "token";
1450
- ImageStrategy2["Custom"] = "custom";
1451
- return ImageStrategy2;
1452
- })(ImageStrategy || {});
1453
-
1454
- // src/types/media.ts
1455
- function resolveMediaType(media) {
1456
- if (typeof media.type === "string" && media.type.length > 0) {
1457
- return media.type;
1458
- }
1459
- if (typeof media.mimeType === "string" && media.mimeType.length > 0) {
1460
- const mime = media.mimeType.split("/");
1461
- return mime[0] === "application" ? mime[1] : mime[0];
1462
- }
1463
- return "unknown";
1464
- }
1465
- function isMediaImage(media) {
1466
- const type = resolveMediaType(media);
1467
- if (type === "image") {
1468
- media.type = type;
1469
- return true;
1470
- }
1471
- return false;
1472
- }
1473
- function isMediaVideo(media) {
1474
- const type = resolveMediaType(media);
1475
- if (type === "video") {
1476
- media.type = type;
1477
- return true;
1478
- }
1479
- return false;
1480
- }
1481
- function isMediaJson(media) {
1482
- const type = resolveMediaType(media);
1483
- if (type === "json") {
1484
- media.type = type;
1485
- return true;
1486
- }
1487
- return false;
1488
- }
1489
- function isMediaPdf(media) {
1490
- const type = resolveMediaType(media);
1491
- if (type === "pdf") {
1492
- media.type = type;
1493
- return true;
1494
- }
1495
- return false;
1496
- }
1497
-
1498
- // src/types/menu.ts
1499
- function isMenuHref(item) {
1500
- return ["category", "link", "page", "route"].includes(item.type);
1501
- }
1502
- function isMenuCategory(item) {
1503
- return item.type === "category";
1504
- }
1505
- function isMenuGroup(item) {
1506
- return item.type === "group";
1507
- }
1508
- function isMenuLink(item) {
1509
- return item.type === "link";
1510
- }
1511
- function isMenuPage(item) {
1512
- return item.type === "page";
1513
- }
1514
- function isMenuRoute(item) {
1515
- return item.type === "route";
1516
- }
1517
- var MenuCategoryStrategy = /* @__PURE__ */ ((MenuCategoryStrategy2) => {
1518
- MenuCategoryStrategy2["Default"] = "default";
1519
- MenuCategoryStrategy2["ExcludeHidden"] = "exclude-hidden";
1520
- return MenuCategoryStrategy2;
1521
- })(MenuCategoryStrategy || {});
1522
-
1523
- // src/types/querable.ts
1524
- function toFindParams(idOrParams) {
1525
- if (typeof idOrParams === "number" || typeof idOrParams === "string") {
1526
- return { where: { id: idOrParams } };
1527
- } else {
1528
- return idOrParams;
1529
- }
1530
- }
1531
-
1532
- // src/types/redirect.ts
1533
- var RedirectReason = /* @__PURE__ */ ((RedirectReason2) => {
1534
- RedirectReason2["MovedPermanently"] = "301";
1535
- RedirectReason2["Found"] = "302";
1536
- RedirectReason2["TemporaryRedirect"] = "307";
1537
- RedirectReason2["PermanentRedirect"] = "308";
1538
- RedirectReason2["Gone"] = "410";
1539
- return RedirectReason2;
1540
- })(RedirectReason || {});
1541
1635
  export {
1542
1636
  ImageStrategy,
1543
1637
  JsonService,
@@ -1569,8 +1663,11 @@ export {
1569
1663
  defaultMarket,
1570
1664
  eachCategorized,
1571
1665
  eachMarketLocale,
1666
+ eachMedia,
1667
+ eachValue,
1572
1668
  encryptImageToken,
1573
1669
  enumToList,
1670
+ excludeComponent,
1574
1671
  findCategoryInCategories,
1575
1672
  findChildCategories,
1576
1673
  findRouteOfCategory,
@@ -1589,6 +1686,8 @@ export {
1589
1686
  getProto,
1590
1687
  getRootCategory,
1591
1688
  getRouteHref,
1689
+ groupComponents,
1690
+ hasComponents,
1592
1691
  httpDelete,
1593
1692
  httpFetch,
1594
1693
  httpGet,
@@ -1597,12 +1696,15 @@ export {
1597
1696
  httpPut,
1598
1697
  isArray,
1599
1698
  isBrowser,
1699
+ isComponent,
1700
+ isComponentOfType,
1600
1701
  isDevelopment,
1601
1702
  isEntity,
1602
1703
  isEquatable,
1603
1704
  isHeaders,
1604
1705
  isIncomingHttpHeaders,
1605
1706
  isLocalizedString,
1707
+ isMedia,
1606
1708
  isMediaImage,
1607
1709
  isMediaJson,
1608
1710
  isMediaPdf,
@@ -1641,6 +1743,9 @@ export {
1641
1743
  pascalCaseToKebabCase,
1642
1744
  pascalCaseToSnakeCase,
1643
1745
  passwordStrategy,
1746
+ pickComponent,
1747
+ pickHero,
1748
+ prependHero,
1644
1749
  qsDeserialize,
1645
1750
  qsDeserializeRaw,
1646
1751
  qsSerialize,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@websolutespa/bom-core",
3
- "version": "1.8.16",
3
+ "version": "1.8.18",
4
4
  "description": "Core module of the BOM Repository",
5
5
  "keywords": [
6
6
  "bom",