@reactionary/hcl 0.9.11 → 0.9.13

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.
Files changed (39) hide show
  1. package/capabilities/analytics.capability.js +98 -0
  2. package/capabilities/order-search.capability.js +79 -0
  3. package/capabilities/order.capability.js +62 -0
  4. package/capabilities/personalization-profile.capability.js +85 -0
  5. package/capabilities/product-associations.capability.js +117 -0
  6. package/capabilities/product-recommendations.capability.js +143 -0
  7. package/capabilities/profile.capability.js +215 -0
  8. package/core/initialize.js +136 -2
  9. package/factories/index.js +6 -0
  10. package/factories/order/order.factory.js +124 -0
  11. package/factories/order-search/order-search.factory.js +59 -0
  12. package/factories/personalization-profile/personalization-profile.factory.js +16 -0
  13. package/factories/product-associations/product-associations.factory.js +16 -0
  14. package/factories/product-recommendations/product-recommendations.factory.js +17 -0
  15. package/factories/profile/profile.factory.js +49 -0
  16. package/index.js +7 -0
  17. package/package.json +2 -2
  18. package/schema/capabilities.schema.js +16 -2
  19. package/schema/configuration.schema.js +37 -1
  20. package/src/capabilities/analytics.capability.d.ts +17 -0
  21. package/src/capabilities/order-search.capability.d.ts +13 -0
  22. package/src/capabilities/order.capability.d.ts +13 -0
  23. package/src/capabilities/personalization-profile.capability.d.ts +19 -0
  24. package/src/capabilities/product-associations.capability.d.ts +22 -0
  25. package/src/capabilities/product-recommendations.capability.d.ts +29 -0
  26. package/src/capabilities/profile.capability.d.ts +31 -0
  27. package/src/core/initialize.types.d.ts +7 -1
  28. package/src/factories/index.d.ts +6 -0
  29. package/src/factories/order/order.factory.d.ts +11 -0
  30. package/src/factories/order-search/order-search.factory.d.ts +9 -0
  31. package/src/factories/personalization-profile/personalization-profile.factory.d.ts +11 -0
  32. package/src/factories/product-associations/product-associations.factory.d.ts +8 -0
  33. package/src/factories/product-recommendations/product-recommendations.factory.d.ts +12 -0
  34. package/src/factories/profile/profile.factory.d.ts +9 -0
  35. package/src/index.d.ts +7 -0
  36. package/src/schema/capabilities.schema.d.ts +45 -1
  37. package/src/schema/configuration.schema.d.ts +24 -0
  38. package/src/schema/hcl.schema.d.ts +122 -1
  39. package/src/test/test-utils.d.ts +4 -1
package/package.json CHANGED
@@ -1,11 +1,11 @@
1
1
  {
2
2
  "name": "@reactionary/hcl",
3
- "version": "0.9.11",
3
+ "version": "0.9.13",
4
4
  "type": "module",
5
5
  "main": "./index.js",
6
6
  "types": "./src/index.d.ts",
7
7
  "dependencies": {
8
- "@reactionary/core": "0.9.11",
8
+ "@reactionary/core": "0.9.13",
9
9
  "debug": "^4.4.3",
10
10
  "zod": "4.1.9"
11
11
  },
@@ -13,7 +13,14 @@ const HclCapabilitiesSchema = CapabilitiesSchema.pick({
13
13
  price: true,
14
14
  inventory: true,
15
15
  identity: true,
16
- productSearch: true
16
+ productSearch: true,
17
+ profile: true,
18
+ order: true,
19
+ orderSearch: true,
20
+ analytics: true,
21
+ productAssociations: true,
22
+ productRecommendations: true,
23
+ personalizationProfile: true
17
24
  }).extend({
18
25
  cart: OverridableCapabilitySchema.optional(),
19
26
  checkout: OverridableCapabilitySchema.optional(),
@@ -22,7 +29,14 @@ const HclCapabilitiesSchema = CapabilitiesSchema.pick({
22
29
  price: OverridableCapabilitySchema.optional(),
23
30
  inventory: OverridableCapabilitySchema.optional(),
24
31
  identity: OverridableCapabilitySchema.optional(),
25
- productSearch: OverridableCapabilitySchema.optional()
32
+ productSearch: OverridableCapabilitySchema.optional(),
33
+ profile: OverridableCapabilitySchema.optional(),
34
+ order: OverridableCapabilitySchema.optional(),
35
+ orderSearch: OverridableCapabilitySchema.optional(),
36
+ analytics: OverridableCapabilitySchema.optional(),
37
+ productAssociations: OverridableCapabilitySchema.optional(),
38
+ productRecommendations: OverridableCapabilitySchema.optional(),
39
+ personalizationProfile: OverridableCapabilitySchema.optional()
26
40
  }).partial();
27
41
  export {
28
42
  HclCapabilitiesSchema
@@ -37,7 +37,43 @@ const HclConfigurationSchema = z.looseObject({
37
37
  */
38
38
  priceRuleId: z.string().optional().meta({
39
39
  description: "Price rule ID for /display_price WCS calls. Optional \u2014 the server uses its default rule when absent."
40
- })
40
+ }),
41
+ /**
42
+ * Maps Reactionary association types to the HCL `associationCodeType` values
43
+ * returned in `merchandisingAssociations` on product detail responses.
44
+ * Override to match custom HCL store configuration.
45
+ */
46
+ associationTypes: z.looseObject({
47
+ accessories: z.array(z.string()).default(["ACCESSORY"]),
48
+ spareparts: z.array(z.string()).default(["SPAREPART"]),
49
+ replacements: z.array(z.string()).default(["REPLACEMENT"])
50
+ }).default(() => ({
51
+ accessories: ["ACCESSORY"],
52
+ spareparts: ["SPAREPART"],
53
+ replacements: ["REPLACEMENT"]
54
+ })),
55
+ /**
56
+ * Names of HCL marketing spots used for product recommendation algorithms.
57
+ * Each algorithm calls the corresponding named espot via the WCS Transaction Service.
58
+ * These espots must be configured in HCL Commerce to return catalog entry data.
59
+ */
60
+ espotNames: z.looseObject({
61
+ frequentlyBoughtTogether: z.string().default("Reactionary_FrequentlyBoughtTogether"),
62
+ similar: z.string().default("Reactionary_SimilarProducts"),
63
+ related: z.string().default("Reactionary_RelatedProducts"),
64
+ trendingInCategory: z.string().default("Reactionary_TrendingInCategory"),
65
+ popular: z.string().default("Reactionary_Popular"),
66
+ topPicks: z.string().default("Reactionary_TopPicks"),
67
+ alsoViewed: z.string().default("Reactionary_AlsoViewed")
68
+ }).default(() => ({
69
+ frequentlyBoughtTogether: "Reactionary_FrequentlyBoughtTogether",
70
+ similar: "Reactionary_SimilarProducts",
71
+ related: "Reactionary_RelatedProducts",
72
+ trendingInCategory: "Reactionary_TrendingInCategory",
73
+ popular: "Reactionary_Popular",
74
+ topPicks: "Reactionary_TopPicks",
75
+ alsoViewed: "Reactionary_AlsoViewed"
76
+ }))
41
77
  });
42
78
  export {
43
79
  HclConfigurationSchema
@@ -0,0 +1,17 @@
1
+ import { AnalyticsCapability, type AnalyticsMutation, type AnalyticsMutationProductAddToCartEvent, type AnalyticsMutationProductDetailsViewEvent, type AnalyticsMutationProductSummaryClickEvent, type AnalyticsMutationProductSummaryViewEvent, type AnalyticsMutationPurchaseEvent, type AnalyticsResult, type Cache, type RequestContext } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ export declare class HclAnalyticsCapability extends AnalyticsCapability {
5
+ protected readonly config: HclConfiguration;
6
+ protected readonly client: HclClient;
7
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient);
8
+ track(event: AnalyticsMutation): Promise<AnalyticsResult>;
9
+ protected processProductSummaryView(event: AnalyticsMutationProductSummaryViewEvent): Promise<AnalyticsResult>;
10
+ protected processProductSummaryClick(event: AnalyticsMutationProductSummaryClickEvent): Promise<AnalyticsResult>;
11
+ protected processProductDetailsView(event: AnalyticsMutationProductDetailsViewEvent): Promise<AnalyticsResult>;
12
+ protected processProductAddToCart(event: AnalyticsMutationProductAddToCartEvent): Promise<AnalyticsResult>;
13
+ protected processPurchase(event: AnalyticsMutationPurchaseEvent): Promise<AnalyticsResult>;
14
+ protected fireEvent(extra: Record<string, string>): Promise<void>;
15
+ protected getEventUrl(): string;
16
+ protected getEventBody(extra: Record<string, string>): Record<string, string>;
17
+ }
@@ -0,0 +1,13 @@
1
+ import { type Cache, OrderSearchCapability, type OrderSearchFactory, type OrderSearchFactoryOutput, type OrderSearchFactoryWithOutput, type OrderSearchQueryByTerm, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclOrderSearchFactory } from '../factories/order-search/order-search.factory.js';
5
+ export declare class HclOrderSearchCapability<TFactory extends OrderSearchFactory = HclOrderSearchFactory> extends OrderSearchCapability<OrderSearchFactoryOutput<TFactory>> {
6
+ protected config: HclConfiguration;
7
+ protected client: HclClient;
8
+ protected factory: OrderSearchFactoryWithOutput<TFactory>;
9
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: OrderSearchFactoryWithOutput<TFactory>);
10
+ queryByTerm(payload: OrderSearchQueryByTerm): Promise<Result<OrderSearchFactoryOutput<TFactory>>>;
11
+ protected orderByStatusUrl(statuses: string): string;
12
+ protected orderByStatusParams(maxResults: number, startIndex: number): URLSearchParams;
13
+ }
@@ -0,0 +1,13 @@
1
+ import { type Cache, type NotFoundError, OrderCapability, type OrderFactory, type OrderFactoryOutput, type OrderFactoryWithOutput, type OrderQueryById, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclOrderFactory } from '../factories/order/order.factory.js';
5
+ export declare class HclOrderCapability<TFactory extends OrderFactory = HclOrderFactory> extends OrderCapability<OrderFactoryOutput<TFactory>> {
6
+ protected config: HclConfiguration;
7
+ protected client: HclClient;
8
+ protected factory: OrderFactoryWithOutput<TFactory>;
9
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: OrderFactoryWithOutput<TFactory>);
10
+ getById(payload: OrderQueryById): Promise<Result<OrderFactoryOutput<TFactory>, NotFoundError>>;
11
+ protected orderUrl(orderId: string): string;
12
+ protected orderParams(): URLSearchParams;
13
+ }
@@ -0,0 +1,19 @@
1
+ import { PersonalizationProfileCapability, type Cache, type NotFoundError, type PersonalizationProfileFactory, type PersonalizationProfileFactoryOutput, type PersonalizationProfileFactoryWithOutput, type PersonalizationProfileQueryGetProfile, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclPersonalizationProfileFactory } from '../factories/personalization-profile/personalization-profile.factory.js';
5
+ export declare class HclPersonalizationProfileCapability<TFactory extends PersonalizationProfileFactory = HclPersonalizationProfileFactory> extends PersonalizationProfileCapability<PersonalizationProfileFactoryOutput<TFactory>> {
6
+ protected readonly config: HclConfiguration;
7
+ protected readonly client: HclClient;
8
+ protected readonly factory: PersonalizationProfileFactoryWithOutput<TFactory>;
9
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: PersonalizationProfileFactoryWithOutput<TFactory>);
10
+ getPersonalizationProfile(_payload: PersonalizationProfileQueryGetProfile): Promise<Result<PersonalizationProfileFactoryOutput<TFactory>, NotFoundError>>;
11
+ /**
12
+ * Calls the WCS segment API to retrieve the customer segments for the given
13
+ * personalization ID. Returns an empty array when the API call fails or
14
+ * returns no segment data.
15
+ */
16
+ protected fetchSegments(personalizationId: string): Promise<string[]>;
17
+ protected getSegmentsUrl(): string;
18
+ protected getSegmentsParams(personalizationId: string): URLSearchParams;
19
+ }
@@ -0,0 +1,22 @@
1
+ import { ProductAssociationsCapability, type Cache, type ProductAssociationsFactory, type ProductAssociationsFactoryOutput, type ProductAssociationsFactoryWithOutput, type ProductAssociationsGetAccessoriesQuery, type ProductAssociationsGetReplacementsQuery, type ProductAssociationsGetSparepartsQuery, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclAssociation } from '../schema/hcl.schema.js';
5
+ import type { HclProductAssociationsFactory } from '../factories/product-associations/product-associations.factory.js';
6
+ export declare class HclProductAssociationsCapability<TFactory extends ProductAssociationsFactory = HclProductAssociationsFactory> extends ProductAssociationsCapability<ProductAssociationsFactoryOutput<TFactory>> {
7
+ protected readonly config: HclConfiguration;
8
+ protected readonly client: HclClient;
9
+ protected readonly factory: ProductAssociationsFactoryWithOutput<TFactory>;
10
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: ProductAssociationsFactoryWithOutput<TFactory>);
11
+ getAccessories(query: ProductAssociationsGetAccessoriesQuery): Promise<Result<ProductAssociationsFactoryOutput<TFactory>[]>>;
12
+ getSpareparts(query: ProductAssociationsGetSparepartsQuery): Promise<Result<ProductAssociationsFactoryOutput<TFactory>[]>>;
13
+ getReplacements(query: ProductAssociationsGetReplacementsQuery): Promise<Result<ProductAssociationsFactoryOutput<TFactory>[]>>;
14
+ /**
15
+ * Fetches the product detail for the given part number and returns the
16
+ * `merchandisingAssociations` filtered to the requested association types,
17
+ * capped at `maxCount`.
18
+ */
19
+ protected fetchAssociations(partNumber: string, types: string[], maxCount: number): Promise<HclAssociation[]>;
20
+ protected getProductsUrl(): string;
21
+ protected getProductsParams(partNumber: string): URLSearchParams;
22
+ }
@@ -0,0 +1,29 @@
1
+ import { ProductRecommendationsCapability, type Cache, type ProductRecommendation, type ProductRecommendationAlgorithmAlsoViewedProductsQuery, type ProductRecommendationAlgorithmFrequentlyBoughtTogetherQuery, type ProductRecommendationAlgorithmPopuplarProductsQuery, type ProductRecommendationAlgorithmRelatedProductsQuery, type ProductRecommendationAlgorithmSimilarProductsQuery, type ProductRecommendationAlgorithmTopPicksProductsQuery, type ProductRecommendationAlgorithmTrendingInCategoryQuery, type ProductRecommendationsByCollectionQuery, type ProductRecommendationsFactory, type ProductRecommendationsFactoryWithOutput, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclProductRecommendationsFactory } from '../factories/product-recommendations/product-recommendations.factory.js';
5
+ export declare class HclProductRecommendationsCapability<TFactory extends ProductRecommendationsFactory = HclProductRecommendationsFactory> extends ProductRecommendationsCapability {
6
+ protected readonly config: HclConfiguration;
7
+ protected readonly client: HclClient;
8
+ protected readonly factory: ProductRecommendationsFactoryWithOutput<TFactory>;
9
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: ProductRecommendationsFactoryWithOutput<TFactory>);
10
+ getRecommendations(...args: Parameters<ProductRecommendationsCapability['getRecommendations']>): Promise<Result<ProductRecommendation[]>>;
11
+ getCollection(query: ProductRecommendationsByCollectionQuery): Promise<Result<ProductRecommendation[]>>;
12
+ protected getFrequentlyBoughtTogetherRecommendations(query: ProductRecommendationAlgorithmFrequentlyBoughtTogetherQuery): Promise<ProductRecommendation[]>;
13
+ protected getSimilarProductsRecommendations(query: ProductRecommendationAlgorithmSimilarProductsQuery): Promise<ProductRecommendation[]>;
14
+ protected getRelatedProductsRecommendations(query: ProductRecommendationAlgorithmRelatedProductsQuery): Promise<ProductRecommendation[]>;
15
+ protected getTrendingInCategoryRecommendations(query: ProductRecommendationAlgorithmTrendingInCategoryQuery): Promise<ProductRecommendation[]>;
16
+ protected getPopularProductsRecommendations(query: ProductRecommendationAlgorithmPopuplarProductsQuery): Promise<ProductRecommendation[]>;
17
+ protected getTopPicksProductsRecommendations(query: ProductRecommendationAlgorithmTopPicksProductsQuery): Promise<ProductRecommendation[]>;
18
+ protected getAlsoViewedProductsRecommendations(query: ProductRecommendationAlgorithmAlsoViewedProductsQuery): Promise<ProductRecommendation[]>;
19
+ /**
20
+ * Calls an HCL marketing spot (espot) by name and maps its catalog entry
21
+ * activity data to `ProductRecommendation[]` using the factory.
22
+ *
23
+ * Returns an empty array when the espot is not found (404) or returns no
24
+ * catalog entry data — allowing teams to configure only the espots they need.
25
+ */
26
+ protected fetchEspot(name: string, algorithm: string, params?: Record<string, string | undefined>): Promise<ProductRecommendation[]>;
27
+ protected getEspotUrl(name: string): string;
28
+ protected getEspotParams(params: Record<string, string | undefined>): URLSearchParams;
29
+ }
@@ -0,0 +1,31 @@
1
+ import { type Address, type Cache, type NotFoundError, ProfileCapability, type ProfileFactory, type ProfileFactoryOutput, type ProfileFactoryWithOutput, type ProfileMutationAddShippingAddress, type ProfileMutationMakeShippingAddressDefault, type ProfileMutationRemoveShippingAddress, type ProfileMutationSetBillingAddress, type ProfileMutationUpdate, type ProfileMutationUpdateShippingAddress, type ProfileQuerySelf, type RequestContext, type Result } from '@reactionary/core';
2
+ import type { HclConfiguration } from '../schema/configuration.schema.js';
3
+ import type { HclClient } from '../core/client.js';
4
+ import type { HclProfileFactory } from '../factories/profile/profile.factory.js';
5
+ import type { HclPersonResponse, HclWcsPersonContact } from '../schema/hcl.schema.js';
6
+ export declare class HclProfileCapability<TFactory extends ProfileFactory = HclProfileFactory> extends ProfileCapability<ProfileFactoryOutput<TFactory>> {
7
+ protected config: HclConfiguration;
8
+ protected client: HclClient;
9
+ protected factory: ProfileFactoryWithOutput<TFactory>;
10
+ constructor(cache: Cache, context: RequestContext, config: HclConfiguration, client: HclClient, factory: ProfileFactoryWithOutput<TFactory>);
11
+ protected fetchPerson(): Promise<HclPersonResponse>;
12
+ protected fetchProfile(): Promise<ProfileFactoryOutput<TFactory>>;
13
+ protected toWcsContact(address: Address): Partial<HclWcsPersonContact>;
14
+ protected personSelfUrl(): string;
15
+ protected updatePersonPayload(email?: string, phone?: string): {
16
+ email1?: string;
17
+ phone1?: string;
18
+ };
19
+ protected personContactListUrl(): string;
20
+ protected contactUrl(nickName: string): string;
21
+ protected makeShippingAddressDefaultPayload(): {
22
+ primary: string;
23
+ };
24
+ getById(_payload: ProfileQuerySelf): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
25
+ update(payload: ProfileMutationUpdate): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
26
+ addShippingAddress(payload: ProfileMutationAddShippingAddress): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
27
+ updateShippingAddress(payload: ProfileMutationUpdateShippingAddress): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
28
+ removeShippingAddress(payload: ProfileMutationRemoveShippingAddress): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
29
+ makeShippingAddressDefault(payload: ProfileMutationMakeShippingAddressDefault): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
30
+ setBillingAddress(payload: ProfileMutationSetBillingAddress): Promise<Result<ProfileFactoryOutput<TFactory>, NotFoundError>>;
31
+ }
@@ -8,7 +8,10 @@ import type { HclProductSearchCapability } from '../capabilities/product-search.
8
8
  import type { HclPriceCapability } from '../capabilities/price.capability.js';
9
9
  import type { HclInventoryCapability } from '../capabilities/inventory.capability.js';
10
10
  import type { HclIdentityCapability } from '../capabilities/identity.capability.js';
11
- type OverridableCapabilityKey = 'product' | 'productSearch' | 'cart' | 'checkout' | 'category' | 'price' | 'inventory' | 'identity';
11
+ import type { HclProfileCapability } from '../capabilities/profile.capability.js';
12
+ import type { HclOrderCapability } from '../capabilities/order.capability.js';
13
+ import type { HclOrderSearchCapability } from '../capabilities/order-search.capability.js';
14
+ type OverridableCapabilityKey = 'product' | 'productSearch' | 'cart' | 'checkout' | 'category' | 'price' | 'inventory' | 'identity' | 'profile' | 'order' | 'orderSearch';
12
15
  type EnabledCapability<TCapability> = TCapability extends {
13
16
  enabled: true;
14
17
  } ? true : false;
@@ -28,6 +31,9 @@ type DefaultCapabilityMap = {
28
31
  price: HclPriceCapability;
29
32
  inventory: HclInventoryCapability;
30
33
  identity: HclIdentityCapability;
34
+ profile: HclProfileCapability;
35
+ order: HclOrderCapability;
36
+ orderSearch: HclOrderSearchCapability;
31
37
  };
32
38
  type CapabilityImplementationMap<T extends HclCapabilities> = {
33
39
  [K in OverridableCapabilityKey]: ExtractCapabilityImplementation<T[K], DefaultCapabilityMap[K]>;
@@ -6,3 +6,9 @@ export * from './product-search/product-search.factory.js';
6
6
  export * from './price/price.factory.js';
7
7
  export * from './inventory/inventory.factory.js';
8
8
  export * from './identity/identity.factory.js';
9
+ export * from './profile/profile.factory.js';
10
+ export * from './order/order.factory.js';
11
+ export * from './order-search/order-search.factory.js';
12
+ export * from './product-associations/product-associations.factory.js';
13
+ export * from './product-recommendations/product-recommendations.factory.js';
14
+ export * from './personalization-profile/personalization-profile.factory.js';
@@ -0,0 +1,11 @@
1
+ import type { AnyOrderSchema, CostBreakDown, Currency, OrderFactory, OrderItem, OrderSchema, PaymentInstruction, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ import type { HclWcsOrderDetailResponse, HclWcsOrderItem, HclWcsPaymentInstruction } from '../../schema/hcl.schema.js';
4
+ export declare class HclOrderFactory<TOrderSchema extends AnyOrderSchema = typeof OrderSchema> implements OrderFactory<TOrderSchema> {
5
+ readonly orderSchema: TOrderSchema;
6
+ constructor(orderSchema: TOrderSchema);
7
+ parseOrder(context: RequestContext, data: HclWcsOrderDetailResponse): z.output<TOrderSchema>;
8
+ protected parseOrderItem(_context: RequestContext, item: HclWcsOrderItem, defaultCurrency: Currency): OrderItem;
9
+ protected parseCostBreakdown(_context: RequestContext, data: HclWcsOrderDetailResponse, currency: Currency): CostBreakDown;
10
+ protected parsePaymentInstruction(_context: RequestContext, pi: HclWcsPaymentInstruction, defaultCurrency: Currency): PaymentInstruction;
11
+ }
@@ -0,0 +1,9 @@
1
+ import type { AnyOrderSearchResultSchema, OrderSearchFactory, OrderSearchQueryByTerm, OrderSearchResultItem, OrderSearchResultSchema, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ import type { HclWcsCartResponse, HclWcsOrderListResponse } from '../../schema/hcl.schema.js';
4
+ export declare class HclOrderSearchFactory<TOrderSearchResultSchema extends AnyOrderSearchResultSchema = typeof OrderSearchResultSchema> implements OrderSearchFactory<TOrderSearchResultSchema> {
5
+ readonly orderSearchResultSchema: TOrderSearchResultSchema;
6
+ constructor(orderSearchResultSchema: TOrderSearchResultSchema);
7
+ parseOrderSearchResult(context: RequestContext, data: HclWcsOrderListResponse, query: OrderSearchQueryByTerm): z.output<TOrderSearchResultSchema>;
8
+ protected parseOrderSearchResultItem(_context: RequestContext, item: HclWcsCartResponse): OrderSearchResultItem;
9
+ }
@@ -0,0 +1,11 @@
1
+ import type { AnyPersonalizationProfileSchema, PersonalizationProfileFactory, PersonalizationProfileSchema, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ export interface HclPersonalizationProfileData {
4
+ personalizationId: string;
5
+ segments: string[];
6
+ }
7
+ export declare class HclPersonalizationProfileFactory<TPersonalizationProfileSchema extends AnyPersonalizationProfileSchema = typeof PersonalizationProfileSchema> implements PersonalizationProfileFactory<TPersonalizationProfileSchema> {
8
+ readonly personalizationProfileSchema: TPersonalizationProfileSchema;
9
+ constructor(personalizationProfileSchema: TPersonalizationProfileSchema);
10
+ parsePersonalizationProfile(_context: RequestContext, data: HclPersonalizationProfileData): z.output<TPersonalizationProfileSchema>;
11
+ }
@@ -0,0 +1,8 @@
1
+ import type { AnyProductAssociationSchema, ProductAssociationSchema, ProductAssociationsFactory, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ import type { HclAssociation } from '../../schema/hcl.schema.js';
4
+ export declare class HclProductAssociationsFactory<TProductAssociationSchema extends AnyProductAssociationSchema = typeof ProductAssociationSchema> implements ProductAssociationsFactory<TProductAssociationSchema> {
5
+ readonly productAssociationSchema: TProductAssociationSchema;
6
+ constructor(productAssociationSchema: TProductAssociationSchema);
7
+ parseAssociation(_context: RequestContext, data: HclAssociation): z.output<TProductAssociationSchema>;
8
+ }
@@ -0,0 +1,12 @@
1
+ import type { AnyProductRecommendationSchema, ProductRecommendationSchema, ProductRecommendationsFactory, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ import type { HclEspotActivityData } from '../../schema/hcl.schema.js';
4
+ export interface HclEspotRecommendationData {
5
+ activityData: HclEspotActivityData;
6
+ algorithm: string;
7
+ }
8
+ export declare class HclProductRecommendationsFactory<TProductRecommendationSchema extends AnyProductRecommendationSchema = typeof ProductRecommendationSchema> implements ProductRecommendationsFactory<TProductRecommendationSchema> {
9
+ readonly productRecommendationSchema: TProductRecommendationSchema;
10
+ constructor(productRecommendationSchema: TProductRecommendationSchema);
11
+ parseRecommendation(_context: RequestContext, data: HclEspotRecommendationData): z.output<TProductRecommendationSchema>;
12
+ }
@@ -0,0 +1,9 @@
1
+ import type { Address, AnyProfileSchema, ProfileFactory, ProfileSchema, RequestContext } from '@reactionary/core';
2
+ import type * as z from 'zod';
3
+ import type { HclPersonResponse, HclWcsPersonContact } from '../../schema/hcl.schema.js';
4
+ export declare class HclProfileFactory<TProfileSchema extends AnyProfileSchema = typeof ProfileSchema> implements ProfileFactory<TProfileSchema> {
5
+ readonly profileSchema: TProfileSchema;
6
+ constructor(profileSchema: TProfileSchema);
7
+ parseProfile(context: RequestContext, data: HclPersonResponse): z.output<TProfileSchema>;
8
+ protected parseAddress(_context: RequestContext, contact: HclWcsPersonContact): Address;
9
+ }
package/src/index.d.ts CHANGED
@@ -14,3 +14,10 @@ export * from './capabilities/product-search.capability.js';
14
14
  export * from './capabilities/price.capability.js';
15
15
  export * from './capabilities/inventory.capability.js';
16
16
  export * from './capabilities/identity.capability.js';
17
+ export * from './capabilities/profile.capability.js';
18
+ export * from './capabilities/order.capability.js';
19
+ export * from './capabilities/order-search.capability.js';
20
+ export * from './capabilities/analytics.capability.js';
21
+ export * from './capabilities/product-associations.capability.js';
22
+ export * from './capabilities/product-recommendations.capability.js';
23
+ export * from './capabilities/personalization-profile.capability.js';
@@ -1,4 +1,4 @@
1
- import type { Cache, RequestContext, CartFactory, CartFactoryWithOutput, CartCapability, CategoryFactory, CategoryFactoryWithOutput, CategoryCapability, CheckoutFactory, CheckoutFactoryWithOutput, CheckoutCapability, IdentityFactory, IdentityFactoryWithOutput, IdentityCapability, InventoryFactory, InventoryFactoryWithOutput, InventoryCapability, PriceFactory, PriceFactoryWithOutput, PriceCapability, ProductFactory, ProductFactoryWithOutput, ProductCapability, ProductSearchFactory, ProductSearchFactoryWithOutput, ProductSearchCapability } from '@reactionary/core';
1
+ import type { Cache, RequestContext, AnalyticsCapability, CartFactory, CartFactoryWithOutput, CartCapability, CategoryFactory, CategoryFactoryWithOutput, CategoryCapability, CheckoutFactory, CheckoutFactoryWithOutput, CheckoutCapability, IdentityFactory, IdentityFactoryWithOutput, IdentityCapability, InventoryFactory, InventoryFactoryWithOutput, InventoryCapability, OrderFactory, OrderFactoryWithOutput, OrderCapability, OrderSearchFactory, OrderSearchFactoryWithOutput, OrderSearchCapability, PersonalizationProfileCapability, PersonalizationProfileFactory, PersonalizationProfileFactoryWithOutput, PriceFactory, PriceFactoryWithOutput, PriceCapability, ProductAssociationsCapability, ProductAssociationsFactory, ProductAssociationsFactoryWithOutput, ProductFactory, ProductFactoryWithOutput, ProductCapability, ProductRecommendationsCapability, ProductRecommendationsFactory, ProductRecommendationsFactoryWithOutput, ProductSearchFactory, ProductSearchFactoryWithOutput, ProductSearchCapability, ProfileFactory, ProfileFactoryWithOutput, ProfileCapability } from '@reactionary/core';
2
2
  import type { HclConfiguration } from './configuration.schema.js';
3
3
  import type { HclClient } from '../core/client.js';
4
4
  import * as z from 'zod';
@@ -43,6 +43,41 @@ export declare const HclCapabilitiesSchema: z.ZodObject<{
43
43
  factory: z.ZodOptional<z.ZodUnknown>;
44
44
  capability: z.ZodOptional<z.ZodUnknown>;
45
45
  }, z.core.$loose>>>;
46
+ profile: z.ZodOptional<z.ZodOptional<z.ZodObject<{
47
+ enabled: z.ZodBoolean;
48
+ factory: z.ZodOptional<z.ZodUnknown>;
49
+ capability: z.ZodOptional<z.ZodUnknown>;
50
+ }, z.core.$loose>>>;
51
+ order: z.ZodOptional<z.ZodOptional<z.ZodObject<{
52
+ enabled: z.ZodBoolean;
53
+ factory: z.ZodOptional<z.ZodUnknown>;
54
+ capability: z.ZodOptional<z.ZodUnknown>;
55
+ }, z.core.$loose>>>;
56
+ orderSearch: z.ZodOptional<z.ZodOptional<z.ZodObject<{
57
+ enabled: z.ZodBoolean;
58
+ factory: z.ZodOptional<z.ZodUnknown>;
59
+ capability: z.ZodOptional<z.ZodUnknown>;
60
+ }, z.core.$loose>>>;
61
+ analytics: z.ZodOptional<z.ZodOptional<z.ZodObject<{
62
+ enabled: z.ZodBoolean;
63
+ factory: z.ZodOptional<z.ZodUnknown>;
64
+ capability: z.ZodOptional<z.ZodUnknown>;
65
+ }, z.core.$loose>>>;
66
+ productAssociations: z.ZodOptional<z.ZodOptional<z.ZodObject<{
67
+ enabled: z.ZodBoolean;
68
+ factory: z.ZodOptional<z.ZodUnknown>;
69
+ capability: z.ZodOptional<z.ZodUnknown>;
70
+ }, z.core.$loose>>>;
71
+ productRecommendations: z.ZodOptional<z.ZodOptional<z.ZodObject<{
72
+ enabled: z.ZodBoolean;
73
+ factory: z.ZodOptional<z.ZodUnknown>;
74
+ capability: z.ZodOptional<z.ZodUnknown>;
75
+ }, z.core.$loose>>>;
76
+ personalizationProfile: z.ZodOptional<z.ZodOptional<z.ZodObject<{
77
+ enabled: z.ZodBoolean;
78
+ factory: z.ZodOptional<z.ZodUnknown>;
79
+ capability: z.ZodOptional<z.ZodUnknown>;
80
+ }, z.core.$loose>>>;
46
81
  }, z.core.$loose>;
47
82
  export type HclCapabilities = z.infer<typeof HclCapabilitiesSchema>;
48
83
  export interface HclCapabilityFactoryArgs {
@@ -67,3 +102,12 @@ export type HclPriceCapabilityConfig = HclCapabilityConfig<PriceFactoryWithOutpu
67
102
  export type HclProductCapabilityConfig = HclCapabilityConfig<ProductFactoryWithOutput<ProductFactory>, ProductCapability>;
68
103
  export type HclProductSearchCapabilityConfig = HclCapabilityConfig<ProductSearchFactoryWithOutput<ProductSearchFactory>, ProductSearchCapability>;
69
104
  export type HclIdentityCapabilityConfig = HclCapabilityConfig<IdentityFactoryWithOutput<IdentityFactory>, IdentityCapability>;
105
+ export type HclProfileCapabilityConfig = HclCapabilityConfig<ProfileFactoryWithOutput<ProfileFactory>, ProfileCapability>;
106
+ export type HclOrderCapabilityConfig = HclCapabilityConfig<OrderFactoryWithOutput<OrderFactory>, OrderCapability>;
107
+ export type HclOrderSearchCapabilityConfig = HclCapabilityConfig<OrderSearchFactoryWithOutput<OrderSearchFactory>, OrderSearchCapability>;
108
+ /** Analytics does not use a factory — the capability writes events directly. */
109
+ export type HclAnalyticsCapabilityConfig = HclCapabilityConfig<never, AnalyticsCapability>;
110
+ export type HclProductAssociationsCapabilityConfig = HclCapabilityConfig<ProductAssociationsFactoryWithOutput<ProductAssociationsFactory>, ProductAssociationsCapability>;
111
+ /** Product recommendations uses a factory to parse espot activity data into recommendations. */
112
+ export type HclProductRecommendationsCapabilityConfig = HclCapabilityConfig<ProductRecommendationsFactoryWithOutput<ProductRecommendationsFactory>, ProductRecommendationsCapability>;
113
+ export type HclPersonalizationProfileCapabilityConfig = HclCapabilityConfig<PersonalizationProfileFactoryWithOutput<PersonalizationProfileFactory>, PersonalizationProfileCapability>;
@@ -21,5 +21,29 @@ export declare const HclConfigurationSchema: z.ZodObject<{
21
21
  * In Karkkainen this is '10003'.
22
22
  */
23
23
  priceRuleId: z.ZodOptional<z.ZodString>;
24
+ /**
25
+ * Maps Reactionary association types to the HCL `associationCodeType` values
26
+ * returned in `merchandisingAssociations` on product detail responses.
27
+ * Override to match custom HCL store configuration.
28
+ */
29
+ associationTypes: z.ZodDefault<z.ZodObject<{
30
+ accessories: z.ZodDefault<z.ZodArray<z.ZodString>>;
31
+ spareparts: z.ZodDefault<z.ZodArray<z.ZodString>>;
32
+ replacements: z.ZodDefault<z.ZodArray<z.ZodString>>;
33
+ }, z.core.$loose>>;
34
+ /**
35
+ * Names of HCL marketing spots used for product recommendation algorithms.
36
+ * Each algorithm calls the corresponding named espot via the WCS Transaction Service.
37
+ * These espots must be configured in HCL Commerce to return catalog entry data.
38
+ */
39
+ espotNames: z.ZodDefault<z.ZodObject<{
40
+ frequentlyBoughtTogether: z.ZodDefault<z.ZodString>;
41
+ similar: z.ZodDefault<z.ZodString>;
42
+ related: z.ZodDefault<z.ZodString>;
43
+ trendingInCategory: z.ZodDefault<z.ZodString>;
44
+ popular: z.ZodDefault<z.ZodString>;
45
+ topPicks: z.ZodDefault<z.ZodString>;
46
+ alsoViewed: z.ZodDefault<z.ZodString>;
47
+ }, z.core.$loose>>;
24
48
  }, z.core.$loose>;
25
49
  export type HclConfiguration = z.infer<typeof HclConfigurationSchema>;
@@ -234,7 +234,7 @@ export interface HclProductResponse extends HclProductSearchItem {
234
234
  components?: HclProductResponse[];
235
235
  /** Quantity — only present on components array elements */
236
236
  quantity?: string;
237
- merchandisingAssociations?: HclProductResponse[];
237
+ merchandisingAssociations?: HclAssociation[];
238
238
  attachments?: HclAttachment[];
239
239
  images?: HclImage[];
240
240
  /**
@@ -427,6 +427,31 @@ export interface HclWcsIdentityResponse {
427
427
  personalizationID?: string;
428
428
  resourceName?: string;
429
429
  }
430
+ /**
431
+ * A single entry in a WCS person address book (contact list).
432
+ * Returned as part of the GET /person/@self response (contact[] field)
433
+ * and used for POST/PUT /person/@self/contact operations.
434
+ */
435
+ export interface HclWcsPersonContact {
436
+ /** Unique identifier / display name for this address (e.g. 'Home', 'Work', 'Billing'). */
437
+ nickName: string;
438
+ firstName?: string;
439
+ lastName?: string;
440
+ /** Street address lines. Index 0 = street, index 1 = apartment / second line. */
441
+ addressLine?: string[];
442
+ /** Alternative single-field address (some WCS endpoint variants). */
443
+ address1?: string;
444
+ city?: string;
445
+ stateOrProvinceName?: string;
446
+ zipCode?: string;
447
+ /** ISO country code, e.g. 'US'. */
448
+ country?: string;
449
+ phone1?: string;
450
+ email1?: string;
451
+ /** '1' marks this as the default / primary shipping address. */
452
+ primary?: string;
453
+ addressType?: string;
454
+ }
430
455
  /**
431
456
  * Response from GET /wcs/resources/store/{storeId}/person/@self.
432
457
  * Only the fields we use are typed; the full WCS schema has many more.
@@ -439,9 +464,12 @@ export interface HclPersonResponse {
439
464
  email1?: string;
440
465
  firstName?: string;
441
466
  lastName?: string;
467
+ phone1?: string;
442
468
  resourceName?: string;
443
469
  /** Organization ID. `-2000` indicates the default anonymous org. */
444
470
  orgizationId?: string;
471
+ /** Address book entries embedded in the person/@self response. */
472
+ contact?: HclWcsPersonContact[];
445
473
  }
446
474
  /** A single order item embedded in a WCS cart/@self response. */
447
475
  export interface HclWcsOrderItem {
@@ -631,3 +659,96 @@ export interface HclWcsCreateOrderResponse {
631
659
  redirecturl?: string;
632
660
  viewTaskName?: string;
633
661
  }
662
+ /**
663
+ * A full order as returned by GET /wcs/resources/store/{storeId}/order/{orderId}.
664
+ * Extends the cart response shape with the `placedDate` field that is only
665
+ * present on placed (non-active) orders.
666
+ */
667
+ export interface HclWcsOrderDetailResponse extends HclWcsCartResponse {
668
+ /** Date/time when the order was placed, e.g. '2024-01-15T10:30:00.000Z'. */
669
+ placedDate?: string;
670
+ }
671
+ /**
672
+ * A single summary entry in a GET /wcs/resources/store/{storeId}/order/@history response.
673
+ * Contains only the fields available in the history list; use getById for full detail.
674
+ */
675
+ export interface HclWcsOrderHistoryItem {
676
+ orderId: string;
677
+ /** WCS order status code, e.g. 'P', 'M', 'S', 'X'. */
678
+ status: string;
679
+ placedDate?: string;
680
+ grandTotal?: string;
681
+ grandTotalCurrency?: string;
682
+ totalProductPrice?: string;
683
+ orderDescription?: string;
684
+ buyerDistinguishedName?: string;
685
+ }
686
+ /**
687
+ * Top-level response from GET /wcs/resources/store/{storeId}/order/@history.
688
+ * Returns a paginated list of the buyer's past orders.
689
+ */
690
+ export interface HclWcsOrderHistoryResponse {
691
+ Order?: HclWcsOrderHistoryItem[];
692
+ recordSetTotal?: string;
693
+ recordSetCount?: string;
694
+ recordSetStartNumber?: string;
695
+ recordSetComplete?: string;
696
+ }
697
+ /**
698
+ * A product item returned within a `merchandisingAssociations` array on a
699
+ * HCL detail-profile product response. Extends the search item shape with
700
+ * an `associationCodeType` that identifies the semantic relationship.
701
+ *
702
+ * Known values: 'ACCESSORY', 'SPAREPART', 'REPLACEMENT', 'CROSSSELL', 'UPSELL', 'UPGRADE'
703
+ */
704
+ export interface HclAssociation extends HclProductSearchItem {
705
+ /** The association type code. e.g. 'ACCESSORY', 'SPAREPART', 'REPLACEMENT'. */
706
+ associationCodeType?: string;
707
+ /** Display sequence for ordering associations within a type. */
708
+ associationSequence?: string;
709
+ }
710
+ /**
711
+ * A single activity data entry within a marketing spot response.
712
+ * When `baseMarketingSpotDataType` is 'CatalogEntry' or 'CatalogEntryId',
713
+ * the entry represents a product recommendation from the spot.
714
+ */
715
+ export interface HclEspotActivityData {
716
+ /** 'CatalogEntry' | 'CatalogEntryId' | 'CatalogGroupId' | 'MarketingContent' */
717
+ baseMarketingSpotDataType?: string;
718
+ /** Internal HCL product uniqueID (numeric string). Present for CatalogEntry/CatalogEntryId types. */
719
+ contentId?: string;
720
+ /** Part number of the product, if returned inline by the spot configuration. */
721
+ partNumber?: string;
722
+ /** Display name of the product or content entry. */
723
+ contentName?: string;
724
+ }
725
+ /** A single marketing spot entry in a WCS espot response. */
726
+ export interface HclEspotMarketingSpot {
727
+ eSpotName?: string;
728
+ baseMarketingSpotActivityData?: HclEspotActivityData[];
729
+ }
730
+ /** Top-level response from GET /wcs/resources/store/{storeId}/espot/{name}. */
731
+ export interface HclEspotResponse {
732
+ MarketingSpotData?: HclEspotMarketingSpot[];
733
+ }
734
+ /** A single customer segment (member group) entry in a WCS segment response. */
735
+ export interface HclSegmentMemberGroup {
736
+ id: string;
737
+ displayName?: {
738
+ language: number;
739
+ value: string;
740
+ };
741
+ description?: {
742
+ language: number;
743
+ value: string;
744
+ };
745
+ usage?: string[];
746
+ }
747
+ /** Top-level response from GET /wcs/resources/store/{storeId}/segment. */
748
+ export interface HclSegmentResponse {
749
+ MemberGroup?: HclSegmentMemberGroup[];
750
+ recordSetTotal?: number;
751
+ recordSetCount?: number;
752
+ recordSetStartNumber?: number;
753
+ recordSetComplete?: boolean;
754
+ }
@@ -5,12 +5,15 @@ export declare function createHclClient(contextOverrides?: Partial<RequestContex
5
5
  product?: true | undefined;
6
6
  productSearch?: true | undefined;
7
7
  price?: false | undefined;
8
+ order?: false | undefined;
8
9
  cart?: false | undefined;
9
10
  checkout?: false | undefined;
10
11
  identity?: false | undefined;
12
+ profile?: false | undefined;
11
13
  inventory?: false | undefined;
12
14
  category?: true | undefined;
13
- }>, "product" | "productSearch" | "price" | "cart" | "checkout" | "identity" | "inventory" | "category"> & {
15
+ orderSearch?: false | undefined;
16
+ }>, "product" | "productSearch" | "price" | "order" | "cart" | "checkout" | "identity" | "profile" | "inventory" | "category" | "orderSearch"> & {
14
17
  product: import("../index.js").HclProductCapability<import("../index.js").HclProductFactory<import("zod").ZodObject<{
15
18
  identifier: import("zod").ZodObject<{
16
19
  key: import("zod").ZodString;