@open-mercato/core 0.9.1-develop.7473.1.de5b22888f → 0.9.1-develop.7475.1.28ca93ed97
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/.turbo/turbo-build.log +2 -2
- package/dist/generated/entities/catalog_price_history_entry/index.js +53 -0
- package/dist/generated/entities/catalog_price_history_entry/index.js.map +7 -0
- package/dist/generated/entities/customer_group_terms/index.js +2 -0
- package/dist/generated/entities/customer_group_terms/index.js.map +2 -2
- package/dist/generated/entities/ecommerce_store/index.js +33 -0
- package/dist/generated/entities/ecommerce_store/index.js.map +7 -0
- package/dist/generated/entities/ecommerce_store_channel_binding/index.js +29 -0
- package/dist/generated/entities/ecommerce_store_channel_binding/index.js.map +7 -0
- package/dist/generated/entities/ecommerce_store_domain_binding/index.js +23 -0
- package/dist/generated/entities/ecommerce_store_domain_binding/index.js.map +7 -0
- package/dist/generated/entities.ids.generated.js +8 -1
- package/dist/generated/entities.ids.generated.js.map +2 -2
- package/dist/generated/entity-fields-registry.js +72 -0
- package/dist/generated/entity-fields-registry.js.map +2 -2
- package/dist/helpers/integration/customerGroupsFixtures.js.map +2 -2
- package/dist/modules/catalog/acl.js +8 -1
- package/dist/modules/catalog/acl.js.map +2 -2
- package/dist/modules/catalog/api/config/omnibus/route.js +184 -0
- package/dist/modules/catalog/api/config/omnibus/route.js.map +7 -0
- package/dist/modules/catalog/api/prices/history/route.js +131 -0
- package/dist/modules/catalog/api/prices/history/route.js.map +7 -0
- package/dist/modules/catalog/api/prices/omnibus-preview/route.js +184 -0
- package/dist/modules/catalog/api/prices/omnibus-preview/route.js.map +7 -0
- package/dist/modules/catalog/api/products/route.js +54 -245
- package/dist/modules/catalog/api/products/route.js.map +3 -3
- package/dist/modules/catalog/api/tags/route.js +6 -0
- package/dist/modules/catalog/api/tags/route.js.map +2 -2
- package/dist/modules/catalog/backend/config/catalog/page.js +3 -1
- package/dist/modules/catalog/backend/config/catalog/page.js.map +2 -2
- package/dist/modules/catalog/cli.js +80 -2
- package/dist/modules/catalog/cli.js.map +2 -2
- package/dist/modules/catalog/commands/categories.js +51 -2
- package/dist/modules/catalog/commands/categories.js.map +2 -2
- package/dist/modules/catalog/commands/prices.js +43 -1
- package/dist/modules/catalog/commands/prices.js.map +2 -2
- package/dist/modules/catalog/commands/products.js +71 -0
- package/dist/modules/catalog/commands/products.js.map +2 -2
- package/dist/modules/catalog/commands/variants.js +7 -0
- package/dist/modules/catalog/commands/variants.js.map +2 -2
- package/dist/modules/catalog/components/OmnibusSettings.js +703 -0
- package/dist/modules/catalog/components/OmnibusSettings.js.map +7 -0
- package/dist/modules/catalog/components/PriceEditorOmnibusRow.js +152 -0
- package/dist/modules/catalog/components/PriceEditorOmnibusRow.js.map +7 -0
- package/dist/modules/catalog/components/lookupSources.js +31 -0
- package/dist/modules/catalog/components/lookupSources.js.map +7 -0
- package/dist/modules/catalog/components/prices/PriceScopeSelectors.js +8 -2
- package/dist/modules/catalog/components/prices/PriceScopeSelectors.js.map +2 -2
- package/dist/modules/catalog/components/products/VariantBuilder.js +11 -1
- package/dist/modules/catalog/components/products/VariantBuilder.js.map +2 -2
- package/dist/modules/catalog/data/entities.js +122 -1
- package/dist/modules/catalog/data/entities.js.map +2 -2
- package/dist/modules/catalog/data/validators.js +78 -0
- package/dist/modules/catalog/data/validators.js.map +2 -2
- package/dist/modules/catalog/di.js +18 -0
- package/dist/modules/catalog/di.js.map +2 -2
- package/dist/modules/catalog/lib/omnibus.js +285 -0
- package/dist/modules/catalog/lib/omnibus.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusBackfill.js +146 -0
- package/dist/modules/catalog/lib/omnibusBackfill.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusCache.js +89 -0
- package/dist/modules/catalog/lib/omnibusCache.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusConfig.js +64 -0
- package/dist/modules/catalog/lib/omnibusConfig.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusHistoryQueries.js +191 -0
- package/dist/modules/catalog/lib/omnibusHistoryQueries.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusPresentedEntry.js +73 -0
- package/dist/modules/catalog/lib/omnibusPresentedEntry.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusProductListEnrichment.js +94 -0
- package/dist/modules/catalog/lib/omnibusProductListEnrichment.js.map +7 -0
- package/dist/modules/catalog/lib/omnibusTypes.js +115 -0
- package/dist/modules/catalog/lib/omnibusTypes.js.map +7 -0
- package/dist/modules/catalog/lib/optionSchemaTranslations.js +55 -0
- package/dist/modules/catalog/lib/optionSchemaTranslations.js.map +7 -0
- package/dist/modules/catalog/lib/priceHistoryQuery.js +103 -0
- package/dist/modules/catalog/lib/priceHistoryQuery.js.map +7 -0
- package/dist/modules/catalog/lib/pricing.js +26 -2
- package/dist/modules/catalog/lib/pricing.js.map +2 -2
- package/dist/modules/catalog/lib/productFilters.js +273 -0
- package/dist/modules/catalog/lib/productFilters.js.map +7 -0
- package/dist/modules/catalog/lib/productScopeKeys.js +105 -0
- package/dist/modules/catalog/lib/productScopeKeys.js.map +7 -0
- package/dist/modules/catalog/lib/productScopeReindex.js +73 -0
- package/dist/modules/catalog/lib/productScopeReindex.js.map +7 -0
- package/dist/modules/catalog/migrations/Migration20261005105352_catalog.js +39 -0
- package/dist/modules/catalog/migrations/Migration20261005105352_catalog.js.map +7 -0
- package/dist/modules/catalog/migrations/Migration20261005150824_catalog.js +39 -0
- package/dist/modules/catalog/migrations/Migration20261005150824_catalog.js.map +7 -0
- package/dist/modules/catalog/services/catalogOmnibusService.js +480 -0
- package/dist/modules/catalog/services/catalogOmnibusService.js.map +7 -0
- package/dist/modules/catalog/setup.js +3 -1
- package/dist/modules/catalog/setup.js.map +2 -2
- package/dist/modules/catalog/subscribers/product-scope-keys-category-deleted.js +16 -0
- package/dist/modules/catalog/subscribers/product-scope-keys-category-deleted.js.map +7 -0
- package/dist/modules/catalog/subscribers/product-scope-keys-category-updated.js +17 -0
- package/dist/modules/catalog/subscribers/product-scope-keys-category-updated.js.map +7 -0
- package/dist/modules/catalog/translations.js +10 -0
- package/dist/modules/catalog/translations.js.map +2 -2
- package/dist/modules/configs/lib/upgrade-actions.js +28 -0
- package/dist/modules/configs/lib/upgrade-actions.js.map +2 -2
- package/dist/modules/customer_groups/api/customer-groups/[id]/terms/route.js +5 -0
- package/dist/modules/customer_groups/api/customer-groups/[id]/terms/route.js.map +2 -2
- package/dist/modules/customer_groups/components/CustomerGroupTermsSection.js +111 -3
- package/dist/modules/customer_groups/components/CustomerGroupTermsSection.js.map +2 -2
- package/dist/modules/customer_groups/components/customerGroupAssortmentScope.js +43 -0
- package/dist/modules/customer_groups/components/customerGroupAssortmentScope.js.map +7 -0
- package/dist/modules/customer_groups/data/entities.js +3 -0
- package/dist/modules/customer_groups/data/entities.js.map +2 -2
- package/dist/modules/customer_groups/data/validators.js +9 -0
- package/dist/modules/customer_groups/data/validators.js.map +2 -2
- package/dist/modules/customer_groups/migrations/Migration20261005110250_customer_groups.js +17 -0
- package/dist/modules/customer_groups/migrations/Migration20261005110250_customer_groups.js.map +7 -0
- package/dist/modules/customer_groups/services/customerGroupsService.js +62 -15
- package/dist/modules/customer_groups/services/customerGroupsService.js.map +2 -2
- package/dist/modules/ecommerce/acl.js +13 -0
- package/dist/modules/ecommerce/acl.js.map +7 -0
- package/dist/modules/ecommerce/api/domain-mappings/route.js +72 -0
- package/dist/modules/ecommerce/api/domain-mappings/route.js.map +7 -0
- package/dist/modules/ecommerce/api/openapi.js +27 -0
- package/dist/modules/ecommerce/api/openapi.js.map +7 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/[id]/assortment-count/route.js +109 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/[id]/assortment-count/route.js.map +7 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/crud.js +265 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/crud.js.map +7 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/route.js +67 -0
- package/dist/modules/ecommerce/api/store-channel-bindings/route.js.map +7 -0
- package/dist/modules/ecommerce/api/store-domain-bindings/crud.js +296 -0
- package/dist/modules/ecommerce/api/store-domain-bindings/crud.js.map +7 -0
- package/dist/modules/ecommerce/api/store-domain-bindings/route.js +73 -0
- package/dist/modules/ecommerce/api/store-domain-bindings/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/categories/[slug]/route.js +87 -0
- package/dist/modules/ecommerce/api/storefront/categories/[slug]/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/categories/openapiSchemas.js +50 -0
- package/dist/modules/ecommerce/api/storefront/categories/openapiSchemas.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/categories/route.js +75 -0
- package/dist/modules/ecommerce/api/storefront/categories/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/context/route.js +163 -0
- package/dist/modules/ecommerce/api/storefront/context/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/products/[idOrHandle]/route.js +87 -0
- package/dist/modules/ecommerce/api/storefront/products/[idOrHandle]/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/products/openapiSchemas.js +177 -0
- package/dist/modules/ecommerce/api/storefront/products/openapiSchemas.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/products/route.js +78 -0
- package/dist/modules/ecommerce/api/storefront/products/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/search/suggest/openapiSchemas.js +25 -0
- package/dist/modules/ecommerce/api/storefront/search/suggest/openapiSchemas.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/search/suggest/route.js +75 -0
- package/dist/modules/ecommerce/api/storefront/search/suggest/route.js.map +7 -0
- package/dist/modules/ecommerce/api/storefront/storefrontRouteSupport.js +58 -0
- package/dist/modules/ecommerce/api/storefront/storefrontRouteSupport.js.map +7 -0
- package/dist/modules/ecommerce/api/stores/[id]/branding/route.js +183 -0
- package/dist/modules/ecommerce/api/stores/[id]/branding/route.js.map +7 -0
- package/dist/modules/ecommerce/api/stores/[id]/preview-branding/route.js +92 -0
- package/dist/modules/ecommerce/api/stores/[id]/preview-branding/route.js.map +7 -0
- package/dist/modules/ecommerce/api/stores/crud.js +401 -0
- package/dist/modules/ecommerce/api/stores/crud.js.map +7 -0
- package/dist/modules/ecommerce/api/stores/route.js +64 -0
- package/dist/modules/ecommerce/api/stores/route.js.map +7 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/[id]/page.js +9 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/[id]/page.js.map +7 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/[id]/page.meta.js +16 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/[id]/page.meta.js.map +7 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/page.js +9 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/page.js.map +7 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/page.meta.js +16 -0
- package/dist/modules/ecommerce/backend/config/ecommerce/page.meta.js.map +7 -0
- package/dist/modules/ecommerce/commands/stores.js +110 -0
- package/dist/modules/ecommerce/commands/stores.js.map +7 -0
- package/dist/modules/ecommerce/components/ChannelAssortmentCount.js +90 -0
- package/dist/modules/ecommerce/components/ChannelAssortmentCount.js.map +7 -0
- package/dist/modules/ecommerce/components/ChannelBindingFormSections.js +33 -0
- package/dist/modules/ecommerce/components/ChannelBindingFormSections.js.map +7 -0
- package/dist/modules/ecommerce/components/ChannelLookupPicker.js +11 -0
- package/dist/modules/ecommerce/components/ChannelLookupPicker.js.map +7 -0
- package/dist/modules/ecommerce/components/DomainStatusWarning.js +24 -0
- package/dist/modules/ecommerce/components/DomainStatusWarning.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreAvailabilityDefaultsSection.js +190 -0
- package/dist/modules/ecommerce/components/StoreAvailabilityDefaultsSection.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreBrandingControls.js +67 -0
- package/dist/modules/ecommerce/components/StoreBrandingControls.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreBrandingPreview.js +69 -0
- package/dist/modules/ecommerce/components/StoreBrandingPreview.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreBrandingTab.js +218 -0
- package/dist/modules/ecommerce/components/StoreBrandingTab.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreChannelBindingDialog.js +270 -0
- package/dist/modules/ecommerce/components/StoreChannelBindingDialog.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreChannelsTab.js +313 -0
- package/dist/modules/ecommerce/components/StoreChannelsTab.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreCreateDialog.js +164 -0
- package/dist/modules/ecommerce/components/StoreCreateDialog.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreDomainBindingDialog.js +162 -0
- package/dist/modules/ecommerce/components/StoreDomainBindingDialog.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreDomainsTab.js +357 -0
- package/dist/modules/ecommerce/components/StoreDomainsTab.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreEditPage.js +155 -0
- package/dist/modules/ecommerce/components/StoreEditPage.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreGeneralTab.js +167 -0
- package/dist/modules/ecommerce/components/StoreGeneralTab.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreListPage.js +290 -0
- package/dist/modules/ecommerce/components/StoreListPage.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreSeoTab.js +132 -0
- package/dist/modules/ecommerce/components/StoreSeoTab.js.map +7 -0
- package/dist/modules/ecommerce/components/StoreStatusBadge.js +20 -0
- package/dist/modules/ecommerce/components/StoreStatusBadge.js.map +7 -0
- package/dist/modules/ecommerce/components/channelLookups.js +28 -0
- package/dist/modules/ecommerce/components/channelLookups.js.map +7 -0
- package/dist/modules/ecommerce/components/storeAdmin.js +41 -0
- package/dist/modules/ecommerce/components/storeAdmin.js.map +7 -0
- package/dist/modules/ecommerce/components/storeBrandingForm.js +197 -0
- package/dist/modules/ecommerce/components/storeBrandingForm.js.map +7 -0
- package/dist/modules/ecommerce/components/storeChannels.js +140 -0
- package/dist/modules/ecommerce/components/storeChannels.js.map +7 -0
- package/dist/modules/ecommerce/components/storeDomains.js +167 -0
- package/dist/modules/ecommerce/components/storeDomains.js.map +7 -0
- package/dist/modules/ecommerce/components/storeEditTabs.js +62 -0
- package/dist/modules/ecommerce/components/storeEditTabs.js.map +7 -0
- package/dist/modules/ecommerce/components/storeGeneral.js +95 -0
- package/dist/modules/ecommerce/components/storeGeneral.js.map +7 -0
- package/dist/modules/ecommerce/components/storeSeo.js +69 -0
- package/dist/modules/ecommerce/components/storeSeo.js.map +7 -0
- package/dist/modules/ecommerce/components/useChannelAssortmentCount.js +45 -0
- package/dist/modules/ecommerce/components/useChannelAssortmentCount.js.map +7 -0
- package/dist/modules/ecommerce/components/useStoreAccess.js +28 -0
- package/dist/modules/ecommerce/components/useStoreAccess.js.map +7 -0
- package/dist/modules/ecommerce/data/enrichers.js +157 -0
- package/dist/modules/ecommerce/data/enrichers.js.map +7 -0
- package/dist/modules/ecommerce/data/entities.js +197 -0
- package/dist/modules/ecommerce/data/entities.js.map +7 -0
- package/dist/modules/ecommerce/data/validators.js +406 -0
- package/dist/modules/ecommerce/data/validators.js.map +7 -0
- package/dist/modules/ecommerce/di.js +11 -0
- package/dist/modules/ecommerce/di.js.map +7 -0
- package/dist/modules/ecommerce/events.js +27 -0
- package/dist/modules/ecommerce/events.js.map +7 -0
- package/dist/modules/ecommerce/index.js +16 -0
- package/dist/modules/ecommerce/index.js.map +7 -0
- package/dist/modules/ecommerce/lib/assortmentCount.js +112 -0
- package/dist/modules/ecommerce/lib/assortmentCount.js.map +7 -0
- package/dist/modules/ecommerce/lib/brandingStyles.js +184 -0
- package/dist/modules/ecommerce/lib/brandingStyles.js.map +7 -0
- package/dist/modules/ecommerce/lib/buyerContext.js +284 -0
- package/dist/modules/ecommerce/lib/buyerContext.js.map +7 -0
- package/dist/modules/ecommerce/lib/cacheInvalidation.js +186 -0
- package/dist/modules/ecommerce/lib/cacheInvalidation.js.map +7 -0
- package/dist/modules/ecommerce/lib/cacheKeys.js +236 -0
- package/dist/modules/ecommerce/lib/cacheKeys.js.map +7 -0
- package/dist/modules/ecommerce/lib/createConflictRecheck.js +29 -0
- package/dist/modules/ecommerce/lib/createConflictRecheck.js.map +7 -0
- package/dist/modules/ecommerce/lib/crudEvents.js +94 -0
- package/dist/modules/ecommerce/lib/crudEvents.js.map +7 -0
- package/dist/modules/ecommerce/lib/crudSupport.js +64 -0
- package/dist/modules/ecommerce/lib/crudSupport.js.map +7 -0
- package/dist/modules/ecommerce/lib/domainBindingRebind.js +99 -0
- package/dist/modules/ecommerce/lib/domainBindingRebind.js.map +7 -0
- package/dist/modules/ecommerce/lib/domainMappingSummaries.js +39 -0
- package/dist/modules/ecommerce/lib/domainMappingSummaries.js.map +7 -0
- package/dist/modules/ecommerce/lib/exclusiveFlag.js +57 -0
- package/dist/modules/ecommerce/lib/exclusiveFlag.js.map +7 -0
- package/dist/modules/ecommerce/lib/references.js +70 -0
- package/dist/modules/ecommerce/lib/references.js.map +7 -0
- package/dist/modules/ecommerce/lib/seedDraftStore.js +99 -0
- package/dist/modules/ecommerce/lib/seedDraftStore.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeBindingCascade.js +109 -0
- package/dist/modules/ecommerce/lib/storeBindingCascade.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeBranding.js +40 -0
- package/dist/modules/ecommerce/lib/storeBranding.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeBrandingRoute.js +76 -0
- package/dist/modules/ecommerce/lib/storeBrandingRoute.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeContext.js +393 -0
- package/dist/modules/ecommerce/lib/storeContext.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeContextService.js +43 -0
- package/dist/modules/ecommerce/lib/storeContextService.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeLocale.js +60 -0
- package/dist/modules/ecommerce/lib/storeLocale.js.map +7 -0
- package/dist/modules/ecommerce/lib/storeNotifications.js +41 -0
- package/dist/modules/ecommerce/lib/storeNotifications.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontCatalogSupport.js +248 -0
- package/dist/modules/ecommerce/lib/storefrontCatalogSupport.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontCategories.js +241 -0
- package/dist/modules/ecommerce/lib/storefrontCategories.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontCategoryCache.js +71 -0
- package/dist/modules/ecommerce/lib/storefrontCategoryCache.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontDetail.js +447 -0
- package/dist/modules/ecommerce/lib/storefrontDetail.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontFacets.js +441 -0
- package/dist/modules/ecommerce/lib/storefrontFacets.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontOptionFilter.js +15 -0
- package/dist/modules/ecommerce/lib/storefrontOptionFilter.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontPricing.js +393 -0
- package/dist/modules/ecommerce/lib/storefrontPricing.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontProductCache.js +90 -0
- package/dist/modules/ecommerce/lib/storefrontProductCache.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontProductScope.js +107 -0
- package/dist/modules/ecommerce/lib/storefrontProductScope.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontProducts.js +670 -0
- package/dist/modules/ecommerce/lib/storefrontProducts.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontQuery.js +156 -0
- package/dist/modules/ecommerce/lib/storefrontQuery.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontRateLimit.js +99 -0
- package/dist/modules/ecommerce/lib/storefrontRateLimit.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontSearch.js +303 -0
- package/dist/modules/ecommerce/lib/storefrontSearch.js.map +7 -0
- package/dist/modules/ecommerce/lib/storefrontSearchCache.js +35 -0
- package/dist/modules/ecommerce/lib/storefrontSearchCache.js.map +7 -0
- package/dist/modules/ecommerce/lib/subscriberSupport.js +33 -0
- package/dist/modules/ecommerce/lib/subscriberSupport.js.map +7 -0
- package/dist/modules/ecommerce/lib/types.js +1 -0
- package/dist/modules/ecommerce/lib/types.js.map +7 -0
- package/dist/modules/ecommerce/migrations/Migration20261005113233_ecommerce.js +32 -0
- package/dist/modules/ecommerce/migrations/Migration20261005113233_ecommerce.js.map +7 -0
- package/dist/modules/ecommerce/migrations/Migration20261006112733_ecommerce.js +17 -0
- package/dist/modules/ecommerce/migrations/Migration20261006112733_ecommerce.js.map +7 -0
- package/dist/modules/ecommerce/notifications.client.js +47 -0
- package/dist/modules/ecommerce/notifications.client.js.map +7 -0
- package/dist/modules/ecommerce/notifications.js +48 -0
- package/dist/modules/ecommerce/notifications.js.map +7 -0
- package/dist/modules/ecommerce/search.js +83 -0
- package/dist/modules/ecommerce/search.js.map +7 -0
- package/dist/modules/ecommerce/setup.js +17 -0
- package/dist/modules/ecommerce/setup.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/assortment-empty-notifications.js +14 -0
- package/dist/modules/ecommerce/subscribers/assortment-empty-notifications.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/availability-policy-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/availability-policy-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/catalog-category-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/catalog-category-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/catalog-price-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/catalog-price-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/catalog-product-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/catalog-product-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/catalog-variant-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/catalog-variant-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/customer-group-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/customer-group-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/customer-group-membership-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/customer-group-membership-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/customer-group-terms-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/customer-group-terms-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/customer-user-deleted-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/customer-user-deleted-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/customer-user-updated-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/customer-user-updated-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/domain-binding-rebind.js +16 -0
- package/dist/modules/ecommerce/subscribers/domain-binding-rebind.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/domain-mapping-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/domain-mapping-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/store-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/store-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/store-channel-binding-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/store-channel-binding-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/store-domain-binding-cache-invalidation.js +14 -0
- package/dist/modules/ecommerce/subscribers/store-domain-binding-cache-invalidation.js.map +7 -0
- package/dist/modules/ecommerce/subscribers/store-notifications.js +14 -0
- package/dist/modules/ecommerce/subscribers/store-notifications.js.map +7 -0
- package/dist/modules/query_index/lib/batch.js +23 -9
- package/dist/modules/query_index/lib/batch.js.map +2 -2
- package/dist/modules/query_index/lib/doc-enrichers.js +212 -0
- package/dist/modules/query_index/lib/doc-enrichers.js.map +7 -0
- package/dist/modules/query_index/lib/document.js +2 -0
- package/dist/modules/query_index/lib/document.js.map +2 -2
- package/dist/modules/query_index/lib/engine.js +68 -1
- package/dist/modules/query_index/lib/engine.js.map +2 -2
- package/dist/modules/query_index/lib/indexer.js +7 -0
- package/dist/modules/query_index/lib/indexer.js.map +2 -2
- package/dist/modules/query_index/lib/search-tokens.js +2 -0
- package/dist/modules/query_index/lib/search-tokens.js.map +2 -2
- package/dist/modules/query_index/migrations/Migration20261005201500_query_index.js +17 -0
- package/dist/modules/query_index/migrations/Migration20261005201500_query_index.js.map +7 -0
- package/dist/modules/translations/components/TranslationManager.js +3 -3
- package/dist/modules/translations/components/TranslationManager.js.map +2 -2
- package/dist/modules/translations/data/validators.js +1 -1
- package/dist/modules/translations/data/validators.js.map +1 -1
- package/dist/modules/translations/lib/batch.js +21 -1
- package/dist/modules/translations/lib/batch.js.map +2 -2
- package/dist/modules/translations/lib/helpers.js +3 -0
- package/dist/modules/translations/lib/helpers.js.map +2 -2
- package/dist/modules/translations/lib/resolve-field-list.js +14 -2
- package/dist/modules/translations/lib/resolve-field-list.js.map +2 -2
- package/generated/entities/catalog_price_history_entry/index.ts +25 -0
- package/generated/entities/customer_group_terms/index.ts +1 -0
- package/generated/entities/ecommerce_store/index.ts +15 -0
- package/generated/entities/ecommerce_store_channel_binding/index.ts +13 -0
- package/generated/entities/ecommerce_store_domain_binding/index.ts +10 -0
- package/generated/entities.ids.generated.ts +8 -1
- package/generated/entity-fields-registry.ts +72 -0
- package/package.json +7 -7
- package/src/helpers/integration/customerGroupsFixtures.ts +2 -0
- package/src/modules/auth/i18n/de.json +8 -0
- package/src/modules/auth/i18n/en.json +8 -0
- package/src/modules/auth/i18n/es.json +8 -0
- package/src/modules/auth/i18n/ko.json +8 -0
- package/src/modules/auth/i18n/pl.json +8 -0
- package/src/modules/catalog/AGENTS.md +5 -2
- package/src/modules/catalog/acl.ts +7 -0
- package/src/modules/catalog/api/config/omnibus/route.ts +204 -0
- package/src/modules/catalog/api/prices/history/route.ts +139 -0
- package/src/modules/catalog/api/prices/omnibus-preview/route.ts +202 -0
- package/src/modules/catalog/api/products/route.ts +53 -308
- package/src/modules/catalog/api/tags/route.ts +6 -0
- package/src/modules/catalog/backend/config/catalog/page.tsx +2 -0
- package/src/modules/catalog/cli.ts +84 -1
- package/src/modules/catalog/commands/categories.ts +54 -2
- package/src/modules/catalog/commands/prices.ts +43 -1
- package/src/modules/catalog/commands/products.ts +84 -1
- package/src/modules/catalog/commands/variants.ts +7 -0
- package/src/modules/catalog/components/OmnibusSettings.tsx +832 -0
- package/src/modules/catalog/components/PriceEditorOmnibusRow.tsx +219 -0
- package/src/modules/catalog/components/lookupSources.ts +29 -0
- package/src/modules/catalog/components/prices/PriceScopeSelectors.tsx +9 -0
- package/src/modules/catalog/components/products/VariantBuilder.tsx +9 -0
- package/src/modules/catalog/data/entities.ts +123 -1
- package/src/modules/catalog/data/validators.ts +118 -0
- package/src/modules/catalog/di.ts +23 -0
- package/src/modules/catalog/i18n/de.json +77 -0
- package/src/modules/catalog/i18n/en.json +77 -0
- package/src/modules/catalog/i18n/es.json +77 -0
- package/src/modules/catalog/i18n/ko.json +77 -0
- package/src/modules/catalog/i18n/pl.json +77 -0
- package/src/modules/catalog/lib/omnibus.ts +406 -0
- package/src/modules/catalog/lib/omnibusBackfill.ts +198 -0
- package/src/modules/catalog/lib/omnibusCache.ts +111 -0
- package/src/modules/catalog/lib/omnibusConfig.ts +73 -0
- package/src/modules/catalog/lib/omnibusHistoryQueries.ts +248 -0
- package/src/modules/catalog/lib/omnibusPresentedEntry.ts +76 -0
- package/src/modules/catalog/lib/omnibusProductListEnrichment.ts +125 -0
- package/src/modules/catalog/lib/omnibusTypes.ts +202 -0
- package/src/modules/catalog/lib/optionSchemaTranslations.ts +55 -0
- package/src/modules/catalog/lib/priceHistoryQuery.ts +155 -0
- package/src/modules/catalog/lib/pricing.ts +42 -4
- package/src/modules/catalog/lib/productFilters.ts +349 -0
- package/src/modules/catalog/lib/productScopeKeys.ts +162 -0
- package/src/modules/catalog/lib/productScopeReindex.ts +139 -0
- package/src/modules/catalog/migrations/.snapshot-open-mercato.json +572 -0
- package/src/modules/catalog/migrations/Migration20261005105352_catalog.ts +39 -0
- package/src/modules/catalog/migrations/Migration20261005150824_catalog.ts +39 -0
- package/src/modules/catalog/services/catalogOmnibusService.ts +642 -0
- package/src/modules/catalog/setup.ts +2 -0
- package/src/modules/catalog/subscribers/product-scope-keys-category-deleted.ts +18 -0
- package/src/modules/catalog/subscribers/product-scope-keys-category-updated.ts +19 -0
- package/src/modules/catalog/translations.ts +12 -0
- package/src/modules/configs/i18n/de.json +5 -1
- package/src/modules/configs/i18n/en.json +5 -1
- package/src/modules/configs/i18n/es.json +5 -1
- package/src/modules/configs/i18n/ko.json +5 -1
- package/src/modules/configs/i18n/pl.json +5 -1
- package/src/modules/configs/lib/upgrade-actions.ts +35 -0
- package/src/modules/customer_groups/api/customer-groups/[id]/terms/route.ts +7 -0
- package/src/modules/customer_groups/components/CustomerGroupTermsSection.tsx +124 -2
- package/src/modules/customer_groups/components/customerGroupAssortmentScope.ts +46 -0
- package/src/modules/customer_groups/data/entities.ts +4 -0
- package/src/modules/customer_groups/data/validators.ts +14 -0
- package/src/modules/customer_groups/i18n/de.json +12 -0
- package/src/modules/customer_groups/i18n/en.json +12 -0
- package/src/modules/customer_groups/i18n/es.json +12 -0
- package/src/modules/customer_groups/i18n/ko.json +12 -0
- package/src/modules/customer_groups/i18n/pl.json +12 -0
- package/src/modules/customer_groups/migrations/.snapshot-open-mercato.json +17 -0
- package/src/modules/customer_groups/migrations/Migration20261005110250_customer_groups.ts +15 -0
- package/src/modules/customer_groups/services/customerGroupsService.ts +74 -23
- package/src/modules/ecommerce/acl.ts +9 -0
- package/src/modules/ecommerce/api/domain-mappings/route.ts +76 -0
- package/src/modules/ecommerce/api/openapi.ts +28 -0
- package/src/modules/ecommerce/api/store-channel-bindings/[id]/assortment-count/route.ts +141 -0
- package/src/modules/ecommerce/api/store-channel-bindings/crud.ts +283 -0
- package/src/modules/ecommerce/api/store-channel-bindings/route.ts +67 -0
- package/src/modules/ecommerce/api/store-domain-bindings/crud.ts +324 -0
- package/src/modules/ecommerce/api/store-domain-bindings/route.ts +73 -0
- package/src/modules/ecommerce/api/storefront/categories/[slug]/route.ts +94 -0
- package/src/modules/ecommerce/api/storefront/categories/openapiSchemas.ts +63 -0
- package/src/modules/ecommerce/api/storefront/categories/route.ts +78 -0
- package/src/modules/ecommerce/api/storefront/context/route.ts +203 -0
- package/src/modules/ecommerce/api/storefront/products/[idOrHandle]/route.ts +94 -0
- package/src/modules/ecommerce/api/storefront/products/openapiSchemas.ts +193 -0
- package/src/modules/ecommerce/api/storefront/products/route.ts +81 -0
- package/src/modules/ecommerce/api/storefront/search/suggest/openapiSchemas.ts +25 -0
- package/src/modules/ecommerce/api/storefront/search/suggest/route.ts +78 -0
- package/src/modules/ecommerce/api/storefront/storefrontRouteSupport.ts +68 -0
- package/src/modules/ecommerce/api/stores/[id]/branding/route.ts +205 -0
- package/src/modules/ecommerce/api/stores/[id]/preview-branding/route.ts +99 -0
- package/src/modules/ecommerce/api/stores/crud.ts +457 -0
- package/src/modules/ecommerce/api/stores/route.ts +66 -0
- package/src/modules/ecommerce/backend/config/ecommerce/[id]/page.meta.ts +12 -0
- package/src/modules/ecommerce/backend/config/ecommerce/[id]/page.tsx +5 -0
- package/src/modules/ecommerce/backend/config/ecommerce/page.meta.ts +12 -0
- package/src/modules/ecommerce/backend/config/ecommerce/page.tsx +5 -0
- package/src/modules/ecommerce/commands/stores.ts +154 -0
- package/src/modules/ecommerce/components/ChannelAssortmentCount.tsx +138 -0
- package/src/modules/ecommerce/components/ChannelBindingFormSections.tsx +40 -0
- package/src/modules/ecommerce/components/ChannelLookupPicker.tsx +5 -0
- package/src/modules/ecommerce/components/DomainStatusWarning.tsx +32 -0
- package/src/modules/ecommerce/components/StoreAvailabilityDefaultsSection.tsx +219 -0
- package/src/modules/ecommerce/components/StoreBrandingControls.tsx +73 -0
- package/src/modules/ecommerce/components/StoreBrandingPreview.tsx +77 -0
- package/src/modules/ecommerce/components/StoreBrandingTab.tsx +242 -0
- package/src/modules/ecommerce/components/StoreChannelBindingDialog.tsx +306 -0
- package/src/modules/ecommerce/components/StoreChannelsTab.tsx +375 -0
- package/src/modules/ecommerce/components/StoreCreateDialog.tsx +204 -0
- package/src/modules/ecommerce/components/StoreDomainBindingDialog.tsx +198 -0
- package/src/modules/ecommerce/components/StoreDomainsTab.tsx +426 -0
- package/src/modules/ecommerce/components/StoreEditPage.tsx +193 -0
- package/src/modules/ecommerce/components/StoreGeneralTab.tsx +189 -0
- package/src/modules/ecommerce/components/StoreListPage.tsx +326 -0
- package/src/modules/ecommerce/components/StoreSeoTab.tsx +152 -0
- package/src/modules/ecommerce/components/StoreStatusBadge.tsx +22 -0
- package/src/modules/ecommerce/components/channelLookups.ts +24 -0
- package/src/modules/ecommerce/components/storeAdmin.ts +56 -0
- package/src/modules/ecommerce/components/storeBrandingForm.ts +230 -0
- package/src/modules/ecommerce/components/storeChannels.ts +210 -0
- package/src/modules/ecommerce/components/storeDomains.ts +221 -0
- package/src/modules/ecommerce/components/storeEditTabs.tsx +76 -0
- package/src/modules/ecommerce/components/storeGeneral.ts +155 -0
- package/src/modules/ecommerce/components/storeSeo.ts +78 -0
- package/src/modules/ecommerce/components/useChannelAssortmentCount.ts +67 -0
- package/src/modules/ecommerce/components/useStoreAccess.ts +36 -0
- package/src/modules/ecommerce/data/enrichers.ts +213 -0
- package/src/modules/ecommerce/data/entities.ts +168 -0
- package/src/modules/ecommerce/data/validators.ts +587 -0
- package/src/modules/ecommerce/di.ts +9 -0
- package/src/modules/ecommerce/events.ts +27 -0
- package/src/modules/ecommerce/i18n/de.json +341 -0
- package/src/modules/ecommerce/i18n/en.json +341 -0
- package/src/modules/ecommerce/i18n/es.json +341 -0
- package/src/modules/ecommerce/i18n/ko.json +341 -0
- package/src/modules/ecommerce/i18n/pl.json +341 -0
- package/src/modules/ecommerce/index.ts +14 -0
- package/src/modules/ecommerce/lib/assortmentCount.ts +175 -0
- package/src/modules/ecommerce/lib/brandingStyles.ts +215 -0
- package/src/modules/ecommerce/lib/buyerContext.ts +401 -0
- package/src/modules/ecommerce/lib/cacheInvalidation.ts +302 -0
- package/src/modules/ecommerce/lib/cacheKeys.ts +340 -0
- package/src/modules/ecommerce/lib/createConflictRecheck.ts +31 -0
- package/src/modules/ecommerce/lib/crudEvents.ts +128 -0
- package/src/modules/ecommerce/lib/crudSupport.ts +85 -0
- package/src/modules/ecommerce/lib/domainBindingRebind.ts +138 -0
- package/src/modules/ecommerce/lib/domainMappingSummaries.ts +71 -0
- package/src/modules/ecommerce/lib/exclusiveFlag.ts +90 -0
- package/src/modules/ecommerce/lib/references.ts +93 -0
- package/src/modules/ecommerce/lib/seedDraftStore.ts +125 -0
- package/src/modules/ecommerce/lib/storeBindingCascade.ts +138 -0
- package/src/modules/ecommerce/lib/storeBranding.ts +48 -0
- package/src/modules/ecommerce/lib/storeBrandingRoute.ts +91 -0
- package/src/modules/ecommerce/lib/storeContext.ts +669 -0
- package/src/modules/ecommerce/lib/storeContextService.ts +71 -0
- package/src/modules/ecommerce/lib/storeLocale.ts +88 -0
- package/src/modules/ecommerce/lib/storeNotifications.ts +55 -0
- package/src/modules/ecommerce/lib/storefrontCatalogSupport.ts +427 -0
- package/src/modules/ecommerce/lib/storefrontCategories.ts +419 -0
- package/src/modules/ecommerce/lib/storefrontCategoryCache.ts +113 -0
- package/src/modules/ecommerce/lib/storefrontDetail.ts +654 -0
- package/src/modules/ecommerce/lib/storefrontFacets.ts +697 -0
- package/src/modules/ecommerce/lib/storefrontOptionFilter.ts +44 -0
- package/src/modules/ecommerce/lib/storefrontPricing.ts +583 -0
- package/src/modules/ecommerce/lib/storefrontProductCache.ts +126 -0
- package/src/modules/ecommerce/lib/storefrontProductScope.ts +181 -0
- package/src/modules/ecommerce/lib/storefrontProducts.ts +963 -0
- package/src/modules/ecommerce/lib/storefrontQuery.ts +215 -0
- package/src/modules/ecommerce/lib/storefrontRateLimit.ts +126 -0
- package/src/modules/ecommerce/lib/storefrontSearch.ts +454 -0
- package/src/modules/ecommerce/lib/storefrontSearchCache.ts +49 -0
- package/src/modules/ecommerce/lib/subscriberSupport.ts +41 -0
- package/src/modules/ecommerce/lib/types.ts +69 -0
- package/src/modules/ecommerce/migrations/.snapshot-open-mercato.json +829 -0
- package/src/modules/ecommerce/migrations/Migration20261005113233_ecommerce.ts +32 -0
- package/src/modules/ecommerce/migrations/Migration20261006112733_ecommerce.ts +15 -0
- package/src/modules/ecommerce/notifications.client.ts +46 -0
- package/src/modules/ecommerce/notifications.ts +46 -0
- package/src/modules/ecommerce/search.ts +93 -0
- package/src/modules/ecommerce/setup.ts +15 -0
- package/src/modules/ecommerce/subscribers/assortment-empty-notifications.ts +12 -0
- package/src/modules/ecommerce/subscribers/availability-policy-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/catalog-category-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/catalog-price-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/catalog-product-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/catalog-variant-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/customer-group-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/customer-group-membership-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/customer-group-terms-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/customer-user-deleted-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/customer-user-updated-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/domain-binding-rebind.ts +14 -0
- package/src/modules/ecommerce/subscribers/domain-mapping-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/store-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/store-channel-binding-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/store-domain-binding-cache-invalidation.ts +12 -0
- package/src/modules/ecommerce/subscribers/store-notifications.ts +12 -0
- package/src/modules/query_index/lib/batch.ts +25 -9
- package/src/modules/query_index/lib/doc-enrichers.ts +306 -0
- package/src/modules/query_index/lib/document.ts +2 -0
- package/src/modules/query_index/lib/engine.ts +58 -1
- package/src/modules/query_index/lib/indexer.ts +8 -0
- package/src/modules/query_index/lib/search-tokens.ts +2 -0
- package/src/modules/query_index/migrations/Migration20261005201500_query_index.ts +42 -0
- package/src/modules/translations/components/TranslationManager.tsx +3 -3
- package/src/modules/translations/data/validators.ts +1 -1
- package/src/modules/translations/lib/batch.ts +47 -0
- package/src/modules/translations/lib/helpers.ts +4 -0
- package/src/modules/translations/lib/resolve-field-list.ts +16 -2
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
const CHANNEL_BINDINGS_API_PATH = "ecommerce/store-channel-bindings";
|
|
3
|
+
const CHANNEL_BINDINGS_API_URL = `/api/${CHANNEL_BINDINGS_API_PATH}`;
|
|
4
|
+
const CHANNEL_BINDINGS_PAGE_SIZE = 100;
|
|
5
|
+
const ASSORTMENT_COUNT_DEBOUNCE_MS = 400;
|
|
6
|
+
const PRICE_SORT_CAP = 5e3;
|
|
7
|
+
const PRICE_SORT_FALLBACKS = ["approximate", "unavailable"];
|
|
8
|
+
const DEFAULT_PRICE_SORT_FALLBACK = "approximate";
|
|
9
|
+
const SCOPE_ID_FIELDS = [
|
|
10
|
+
"categoryIds",
|
|
11
|
+
"tagIds",
|
|
12
|
+
"excludeProductIds",
|
|
13
|
+
"excludeCategoryIds",
|
|
14
|
+
"excludeTagIds"
|
|
15
|
+
];
|
|
16
|
+
const PRICE_SORT_FALLBACK_LABELS = {
|
|
17
|
+
approximate: {
|
|
18
|
+
key: "ecommerce.backend.store.channels.priceSortFallback.approximate",
|
|
19
|
+
fallback: "Approximate order from the default price kind"
|
|
20
|
+
},
|
|
21
|
+
unavailable: {
|
|
22
|
+
key: "ecommerce.backend.store.channels.priceSortFallback.unavailable",
|
|
23
|
+
fallback: "Withdraw price sorting"
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
const PRICE_SORT_FALLBACK_VARIANTS = {
|
|
27
|
+
approximate: "neutral",
|
|
28
|
+
unavailable: "info"
|
|
29
|
+
};
|
|
30
|
+
function isPriceSortFallback(value) {
|
|
31
|
+
return typeof value === "string" && PRICE_SORT_FALLBACKS.includes(value);
|
|
32
|
+
}
|
|
33
|
+
function normalizeIds(value) {
|
|
34
|
+
if (!Array.isArray(value)) return [];
|
|
35
|
+
const seen = /* @__PURE__ */ new Set();
|
|
36
|
+
const ids = [];
|
|
37
|
+
for (const entry of value) {
|
|
38
|
+
if (typeof entry !== "string") continue;
|
|
39
|
+
const trimmed = entry.trim();
|
|
40
|
+
if (!trimmed || seen.has(trimmed)) continue;
|
|
41
|
+
seen.add(trimmed);
|
|
42
|
+
ids.push(trimmed);
|
|
43
|
+
}
|
|
44
|
+
return ids;
|
|
45
|
+
}
|
|
46
|
+
function buildAssortmentScope(values) {
|
|
47
|
+
const scope = {};
|
|
48
|
+
for (const field of SCOPE_ID_FIELDS) {
|
|
49
|
+
const ids = normalizeIds(values[field]);
|
|
50
|
+
if (ids.length > 0) scope[field] = ids;
|
|
51
|
+
}
|
|
52
|
+
return Object.keys(scope).length > 0 ? scope : null;
|
|
53
|
+
}
|
|
54
|
+
function countScopeRules(scope) {
|
|
55
|
+
if (!scope) return 0;
|
|
56
|
+
return SCOPE_ID_FIELDS.reduce((total, field) => total + (scope[field]?.length ?? 0), 0);
|
|
57
|
+
}
|
|
58
|
+
function buildChannelBindingInitialValues(binding, options) {
|
|
59
|
+
const scope = binding?.assortmentScope ?? null;
|
|
60
|
+
return {
|
|
61
|
+
salesChannelId: binding?.salesChannelId ?? "",
|
|
62
|
+
priceKindId: binding?.priceKindId ?? "",
|
|
63
|
+
isDefault: binding ? binding.isDefault : options.firstBinding,
|
|
64
|
+
requireAuthentication: binding?.requireAuthentication ?? false,
|
|
65
|
+
priceSortFallback: isPriceSortFallback(binding?.priceSortFallback) ? binding.priceSortFallback : DEFAULT_PRICE_SORT_FALLBACK,
|
|
66
|
+
categoryIds: normalizeIds(scope?.categoryIds),
|
|
67
|
+
tagIds: normalizeIds(scope?.tagIds),
|
|
68
|
+
excludeProductIds: normalizeIds(scope?.excludeProductIds),
|
|
69
|
+
excludeCategoryIds: normalizeIds(scope?.excludeCategoryIds),
|
|
70
|
+
excludeTagIds: normalizeIds(scope?.excludeTagIds)
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
function buildWritePayload(values) {
|
|
74
|
+
const priceKindId = typeof values.priceKindId === "string" ? values.priceKindId.trim() : "";
|
|
75
|
+
return {
|
|
76
|
+
salesChannelId: values.salesChannelId.trim(),
|
|
77
|
+
priceKindId: priceKindId.length > 0 ? priceKindId : null,
|
|
78
|
+
assortmentScope: buildAssortmentScope(values),
|
|
79
|
+
priceSortFallback: isPriceSortFallback(values.priceSortFallback) ? values.priceSortFallback : DEFAULT_PRICE_SORT_FALLBACK,
|
|
80
|
+
requireAuthentication: values.requireAuthentication === true
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
function buildChannelBindingCreatePayload(storeId, values) {
|
|
84
|
+
return { storeId, ...buildWritePayload(values), isDefault: values.isDefault === true };
|
|
85
|
+
}
|
|
86
|
+
function buildChannelBindingUpdatePayload(bindingId, values) {
|
|
87
|
+
const payload = { id: bindingId, ...buildWritePayload(values) };
|
|
88
|
+
if (values.isDefault === true) payload.isDefault = true;
|
|
89
|
+
return payload;
|
|
90
|
+
}
|
|
91
|
+
function buildAssortmentCountDraft(values) {
|
|
92
|
+
return {
|
|
93
|
+
scope: buildAssortmentScope(values),
|
|
94
|
+
requireAuthentication: values.requireAuthentication === true
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
function buildAssortmentCountUrl(bindingId, draft) {
|
|
98
|
+
const base = `${CHANNEL_BINDINGS_API_URL}/${encodeURIComponent(bindingId)}/assortment-count`;
|
|
99
|
+
if (!draft) return base;
|
|
100
|
+
const params = new URLSearchParams({
|
|
101
|
+
draftScope: JSON.stringify(draft.scope),
|
|
102
|
+
draftRequireAuthentication: draft.requireAuthentication ? "true" : "false"
|
|
103
|
+
});
|
|
104
|
+
return `${base}?${params.toString()}`;
|
|
105
|
+
}
|
|
106
|
+
const REQUIRED_MESSAGE = "ui.forms.errors.required";
|
|
107
|
+
const channelBindingFormSchema = z.object({
|
|
108
|
+
salesChannelId: z.string().trim().min(1, REQUIRED_MESSAGE),
|
|
109
|
+
priceKindId: z.string().default(""),
|
|
110
|
+
isDefault: z.boolean().default(false),
|
|
111
|
+
requireAuthentication: z.boolean().default(false),
|
|
112
|
+
priceSortFallback: z.enum(PRICE_SORT_FALLBACKS).default(DEFAULT_PRICE_SORT_FALLBACK),
|
|
113
|
+
categoryIds: z.array(z.string()).default([]),
|
|
114
|
+
tagIds: z.array(z.string()).default([]),
|
|
115
|
+
excludeProductIds: z.array(z.string()).default([]),
|
|
116
|
+
excludeCategoryIds: z.array(z.string()).default([]),
|
|
117
|
+
excludeTagIds: z.array(z.string()).default([])
|
|
118
|
+
});
|
|
119
|
+
export {
|
|
120
|
+
ASSORTMENT_COUNT_DEBOUNCE_MS,
|
|
121
|
+
CHANNEL_BINDINGS_API_PATH,
|
|
122
|
+
CHANNEL_BINDINGS_API_URL,
|
|
123
|
+
CHANNEL_BINDINGS_PAGE_SIZE,
|
|
124
|
+
DEFAULT_PRICE_SORT_FALLBACK,
|
|
125
|
+
PRICE_SORT_CAP,
|
|
126
|
+
PRICE_SORT_FALLBACKS,
|
|
127
|
+
PRICE_SORT_FALLBACK_LABELS,
|
|
128
|
+
PRICE_SORT_FALLBACK_VARIANTS,
|
|
129
|
+
SCOPE_ID_FIELDS,
|
|
130
|
+
buildAssortmentCountDraft,
|
|
131
|
+
buildAssortmentCountUrl,
|
|
132
|
+
buildAssortmentScope,
|
|
133
|
+
buildChannelBindingCreatePayload,
|
|
134
|
+
buildChannelBindingInitialValues,
|
|
135
|
+
buildChannelBindingUpdatePayload,
|
|
136
|
+
channelBindingFormSchema,
|
|
137
|
+
countScopeRules,
|
|
138
|
+
isPriceSortFallback
|
|
139
|
+
};
|
|
140
|
+
//# sourceMappingURL=storeChannels.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/modules/ecommerce/components/storeChannels.ts"],
|
|
4
|
+
"sourcesContent": ["import { z } from 'zod'\nimport type { StatusBadgeVariant } from '@open-mercato/ui/primitives/status-badge'\n\nexport const CHANNEL_BINDINGS_API_PATH = 'ecommerce/store-channel-bindings'\nexport const CHANNEL_BINDINGS_API_URL = `/api/${CHANNEL_BINDINGS_API_PATH}`\nexport const CHANNEL_BINDINGS_PAGE_SIZE = 100\nexport const ASSORTMENT_COUNT_DEBOUNCE_MS = 400\nexport const PRICE_SORT_CAP = 5000\n\nexport const PRICE_SORT_FALLBACKS = ['approximate', 'unavailable'] as const\n\nexport type PriceSortFallback = (typeof PRICE_SORT_FALLBACKS)[number]\n\nexport const DEFAULT_PRICE_SORT_FALLBACK: PriceSortFallback = 'approximate'\n\nexport const SCOPE_ID_FIELDS = [\n 'categoryIds',\n 'tagIds',\n 'excludeProductIds',\n 'excludeCategoryIds',\n 'excludeTagIds',\n] as const\n\nexport type ScopeIdField = (typeof SCOPE_ID_FIELDS)[number]\n\nexport type ChannelAssortmentScope = Partial<Record<ScopeIdField, string[]>>\n\nexport type ChannelBindingRecord = {\n id: string\n storeId: string\n salesChannelId: string\n priceKindId: string | null\n assortmentScope: ChannelAssortmentScope | null\n priceSortFallback: PriceSortFallback\n isDefault: boolean\n requireAuthentication: boolean\n createdAt: string | null\n updatedAt: string | null\n}\n\nexport type ChannelBindingListResponse = {\n items: ChannelBindingRecord[]\n total: number\n totalPages: number\n}\n\nexport type AssortmentCountResult = {\n count: number\n scopeSource: 'saved' | 'draft'\n requireAuthentication: boolean\n reducedByAuthentication: boolean\n countWithoutAuthentication: number\n unindexedCount: number\n}\n\nexport type AssortmentCountDraft = {\n scope: ChannelAssortmentScope | null\n requireAuthentication: boolean\n}\n\nexport type ChannelBindingWritePayload = {\n salesChannelId: string\n priceKindId: string | null\n assortmentScope: ChannelAssortmentScope | null\n priceSortFallback: PriceSortFallback\n requireAuthentication: boolean\n isDefault?: boolean\n}\n\nexport const PRICE_SORT_FALLBACK_LABELS: Record<PriceSortFallback, { key: string; fallback: string }> = {\n approximate: {\n key: 'ecommerce.backend.store.channels.priceSortFallback.approximate',\n fallback: 'Approximate order from the default price kind',\n },\n unavailable: {\n key: 'ecommerce.backend.store.channels.priceSortFallback.unavailable',\n fallback: 'Withdraw price sorting',\n },\n}\n\nexport const PRICE_SORT_FALLBACK_VARIANTS: Record<PriceSortFallback, StatusBadgeVariant> = {\n approximate: 'neutral',\n unavailable: 'info',\n}\n\nexport function isPriceSortFallback(value: unknown): value is PriceSortFallback {\n return typeof value === 'string' && (PRICE_SORT_FALLBACKS as readonly string[]).includes(value)\n}\n\nfunction normalizeIds(value: unknown): string[] {\n if (!Array.isArray(value)) return []\n const seen = new Set<string>()\n const ids: string[] = []\n for (const entry of value) {\n if (typeof entry !== 'string') continue\n const trimmed = entry.trim()\n if (!trimmed || seen.has(trimmed)) continue\n seen.add(trimmed)\n ids.push(trimmed)\n }\n return ids\n}\n\n/**\n * Builds the `assortment_scope` sent to the server from the picker values. A cleared picker is\n * omitted rather than sent as `[]`, and a scope with every picker cleared is `null` (no\n * restriction), so clearing never reads as \"hide everything\" (US-E1).\n */\nexport function buildAssortmentScope(values: Partial<Record<ScopeIdField, unknown>>): ChannelAssortmentScope | null {\n const scope: ChannelAssortmentScope = {}\n for (const field of SCOPE_ID_FIELDS) {\n const ids = normalizeIds(values[field])\n if (ids.length > 0) scope[field] = ids\n }\n return Object.keys(scope).length > 0 ? scope : null\n}\n\nexport function countScopeRules(scope: ChannelAssortmentScope | null | undefined): number {\n if (!scope) return 0\n return SCOPE_ID_FIELDS.reduce((total, field) => total + (scope[field]?.length ?? 0), 0)\n}\n\nexport function buildChannelBindingInitialValues(\n binding: ChannelBindingRecord | null,\n options: { firstBinding: boolean },\n): ChannelBindingFormValues {\n const scope = binding?.assortmentScope ?? null\n return {\n salesChannelId: binding?.salesChannelId ?? '',\n priceKindId: binding?.priceKindId ?? '',\n isDefault: binding ? binding.isDefault : options.firstBinding,\n requireAuthentication: binding?.requireAuthentication ?? false,\n priceSortFallback: isPriceSortFallback(binding?.priceSortFallback)\n ? binding.priceSortFallback\n : DEFAULT_PRICE_SORT_FALLBACK,\n categoryIds: normalizeIds(scope?.categoryIds),\n tagIds: normalizeIds(scope?.tagIds),\n excludeProductIds: normalizeIds(scope?.excludeProductIds),\n excludeCategoryIds: normalizeIds(scope?.excludeCategoryIds),\n excludeTagIds: normalizeIds(scope?.excludeTagIds),\n }\n}\n\nfunction buildWritePayload(values: ChannelBindingFormValues): ChannelBindingWritePayload {\n const priceKindId = typeof values.priceKindId === 'string' ? values.priceKindId.trim() : ''\n return {\n salesChannelId: values.salesChannelId.trim(),\n priceKindId: priceKindId.length > 0 ? priceKindId : null,\n assortmentScope: buildAssortmentScope(values),\n priceSortFallback: isPriceSortFallback(values.priceSortFallback) ? values.priceSortFallback : DEFAULT_PRICE_SORT_FALLBACK,\n requireAuthentication: values.requireAuthentication === true,\n }\n}\n\nexport function buildChannelBindingCreatePayload(\n storeId: string,\n values: ChannelBindingFormValues,\n): ChannelBindingWritePayload & { storeId: string; isDefault: boolean } {\n return { storeId, ...buildWritePayload(values), isDefault: values.isDefault === true }\n}\n\n/**\n * The default mark is only ever promoted from this form: un-ticking it on the current default\n * would leave the store without a default binding (a `503` for every storefront request), so the\n * update omits `isDefault` unless it asks for the promotion.\n */\nexport function buildChannelBindingUpdatePayload(\n bindingId: string,\n values: ChannelBindingFormValues,\n): ChannelBindingWritePayload & { id: string } {\n const payload: ChannelBindingWritePayload & { id: string } = { id: bindingId, ...buildWritePayload(values) }\n if (values.isDefault === true) payload.isDefault = true\n return payload\n}\n\nexport function buildAssortmentCountDraft(\n values: Partial<Record<ScopeIdField | 'requireAuthentication', unknown>>,\n): AssortmentCountDraft {\n return {\n scope: buildAssortmentScope(values),\n requireAuthentication: values.requireAuthentication === true,\n }\n}\n\nexport function buildAssortmentCountUrl(bindingId: string, draft: AssortmentCountDraft | null): string {\n const base = `${CHANNEL_BINDINGS_API_URL}/${encodeURIComponent(bindingId)}/assortment-count`\n if (!draft) return base\n const params = new URLSearchParams({\n draftScope: JSON.stringify(draft.scope),\n draftRequireAuthentication: draft.requireAuthentication ? 'true' : 'false',\n })\n return `${base}?${params.toString()}`\n}\n\nconst REQUIRED_MESSAGE = 'ui.forms.errors.required'\n\nexport const channelBindingFormSchema = z.object({\n salesChannelId: z.string().trim().min(1, REQUIRED_MESSAGE),\n priceKindId: z.string().default(''),\n isDefault: z.boolean().default(false),\n requireAuthentication: z.boolean().default(false),\n priceSortFallback: z.enum(PRICE_SORT_FALLBACKS).default(DEFAULT_PRICE_SORT_FALLBACK),\n categoryIds: z.array(z.string()).default([]),\n tagIds: z.array(z.string()).default([]),\n excludeProductIds: z.array(z.string()).default([]),\n excludeCategoryIds: z.array(z.string()).default([]),\n excludeTagIds: z.array(z.string()).default([]),\n})\n\nexport type ChannelBindingFormValues = z.infer<typeof channelBindingFormSchema>\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { ecommerceStoreDomainBindingCreateSchema, normalizePathPrefix } from "../data/validators.js";
|
|
3
|
+
import { isDomainMappingStatus } from "../lib/domainMappingSummaries.js";
|
|
4
|
+
const DOMAIN_BINDINGS_API_PATH = "ecommerce/store-domain-bindings";
|
|
5
|
+
const DOMAIN_BINDINGS_API_URL = `/api/${DOMAIN_BINDINGS_API_PATH}`;
|
|
6
|
+
const DOMAIN_MAPPINGS_API_URL = "/api/ecommerce/domain-mappings";
|
|
7
|
+
const DOMAIN_SETTINGS_HREF = "/backend/customer_accounts/settings/domain";
|
|
8
|
+
const DOMAIN_BINDINGS_PAGE_SIZE = 100;
|
|
9
|
+
const DOMAIN_STATUS_VARIANTS = {
|
|
10
|
+
pending: "info",
|
|
11
|
+
verified: "info",
|
|
12
|
+
active: "success",
|
|
13
|
+
dns_failed: "error",
|
|
14
|
+
tls_failed: "warning"
|
|
15
|
+
};
|
|
16
|
+
const DOMAIN_STATUS_LABELS = {
|
|
17
|
+
pending: { key: "ecommerce.backend.store.domains.status.pending", fallback: "Pending" },
|
|
18
|
+
verified: { key: "ecommerce.backend.store.domains.status.verified", fallback: "Verified" },
|
|
19
|
+
active: { key: "ecommerce.backend.store.domains.status.active", fallback: "Active" },
|
|
20
|
+
dns_failed: { key: "ecommerce.backend.store.domains.status.dnsFailed", fallback: "DNS failed" },
|
|
21
|
+
tls_failed: { key: "ecommerce.backend.store.domains.status.tlsFailed", fallback: "TLS failed" }
|
|
22
|
+
};
|
|
23
|
+
const DOMAIN_FAILURE_REASON_PATTERNS = [
|
|
24
|
+
{
|
|
25
|
+
pattern: /^HTTP (\d{3})$/,
|
|
26
|
+
key: "ecommerce.backend.store.domains.failure.httpStatus",
|
|
27
|
+
fallback: "The TLS health check returned HTTP {status}",
|
|
28
|
+
params: ["status"]
|
|
29
|
+
},
|
|
30
|
+
{
|
|
31
|
+
pattern: /^TLS health check timed out$/,
|
|
32
|
+
key: "ecommerce.backend.store.domains.failure.tlsTimeout",
|
|
33
|
+
fallback: "The TLS health check timed out",
|
|
34
|
+
params: []
|
|
35
|
+
},
|
|
36
|
+
{
|
|
37
|
+
pattern: /^TLS health check failed$/,
|
|
38
|
+
key: "ecommerce.backend.store.domains.failure.tlsFailed",
|
|
39
|
+
fallback: "The TLS health check failed",
|
|
40
|
+
params: []
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
pattern: /^DNS lookup error \((CNAME|A)\): /,
|
|
44
|
+
key: "ecommerce.backend.store.domains.failure.dnsLookup",
|
|
45
|
+
fallback: "The DNS lookup for the {recordType} record failed",
|
|
46
|
+
params: ["recordType"]
|
|
47
|
+
},
|
|
48
|
+
{
|
|
49
|
+
pattern: /^CNAME points to (.+) instead of (.+)$/,
|
|
50
|
+
key: "ecommerce.backend.store.domains.failure.cnameMismatch",
|
|
51
|
+
fallback: "The CNAME record points to {actual} instead of {expected}",
|
|
52
|
+
params: ["actual", "expected"]
|
|
53
|
+
},
|
|
54
|
+
{
|
|
55
|
+
pattern: /^No CNAME or A record found for /,
|
|
56
|
+
key: "ecommerce.backend.store.domains.failure.noRecords",
|
|
57
|
+
fallback: "No CNAME or A record was found",
|
|
58
|
+
params: []
|
|
59
|
+
},
|
|
60
|
+
{
|
|
61
|
+
pattern: /^A record points to a known proxy IP, but reverse-resolve over HTTPS did not reach our server$/,
|
|
62
|
+
key: "ecommerce.backend.store.domains.failure.proxyUnreachable",
|
|
63
|
+
fallback: "The domain is behind a proxy that does not forward traffic to this platform",
|
|
64
|
+
params: []
|
|
65
|
+
},
|
|
66
|
+
{
|
|
67
|
+
pattern: /^A record points to (.+) instead of (.+)$/,
|
|
68
|
+
key: "ecommerce.backend.store.domains.failure.aRecordMismatch",
|
|
69
|
+
fallback: "The A record points to {actual} instead of {expected}",
|
|
70
|
+
params: ["actual", "expected"]
|
|
71
|
+
},
|
|
72
|
+
{
|
|
73
|
+
pattern: /^A record points to (.+) but apex-domain registration is not enabled on this deployment$/,
|
|
74
|
+
key: "ecommerce.backend.store.domains.failure.apexNotEnabled",
|
|
75
|
+
fallback: "The A record points to {actual}, but apex domains are not enabled on this deployment",
|
|
76
|
+
params: ["actual"]
|
|
77
|
+
}
|
|
78
|
+
];
|
|
79
|
+
function describeDomainFailureReason(reason) {
|
|
80
|
+
for (const entry of DOMAIN_FAILURE_REASON_PATTERNS) {
|
|
81
|
+
const match = entry.pattern.exec(reason);
|
|
82
|
+
if (!match) continue;
|
|
83
|
+
const params = {};
|
|
84
|
+
entry.params.forEach((name, index) => {
|
|
85
|
+
params[name] = match[index + 1] ?? "";
|
|
86
|
+
});
|
|
87
|
+
return { key: entry.key, fallback: entry.fallback, params };
|
|
88
|
+
}
|
|
89
|
+
return null;
|
|
90
|
+
}
|
|
91
|
+
function isServingStatus(status) {
|
|
92
|
+
return status === "active";
|
|
93
|
+
}
|
|
94
|
+
function describeDomainStatus(status) {
|
|
95
|
+
if (isDomainMappingStatus(status)) {
|
|
96
|
+
return { variant: DOMAIN_STATUS_VARIANTS[status], ...DOMAIN_STATUS_LABELS[status] };
|
|
97
|
+
}
|
|
98
|
+
return { variant: "neutral", key: "", fallback: status };
|
|
99
|
+
}
|
|
100
|
+
function formatBindingAddress(hostname, pathPrefix) {
|
|
101
|
+
return `${hostname}${pathPrefix ?? ""}`;
|
|
102
|
+
}
|
|
103
|
+
function normalizeBindingPrefix(value) {
|
|
104
|
+
const normalized = normalizePathPrefix(value ?? null);
|
|
105
|
+
return typeof normalized === "string" && normalized.length > 0 ? normalized : null;
|
|
106
|
+
}
|
|
107
|
+
function findDuplicateBinding(bindings, candidate, ignoreBindingId) {
|
|
108
|
+
return bindings.find(
|
|
109
|
+
(binding) => binding.id !== ignoreBindingId && binding.domainMappingId === candidate.domainMappingId && (binding.pathPrefix ?? null) === candidate.pathPrefix
|
|
110
|
+
) ?? null;
|
|
111
|
+
}
|
|
112
|
+
function findPreviousPrimary(bindings, nextPrimaryId) {
|
|
113
|
+
return bindings.find((binding) => binding.isPrimary && binding.id !== nextPrimaryId) ?? null;
|
|
114
|
+
}
|
|
115
|
+
const REQUIRED_MESSAGE = "ui.forms.errors.required";
|
|
116
|
+
const domainBindingFormSchema = z.object({
|
|
117
|
+
domainMappingId: z.string().trim().min(1, REQUIRED_MESSAGE),
|
|
118
|
+
pathPrefix: z.string().superRefine((value, ctx) => {
|
|
119
|
+
const parsed = ecommerceStoreDomainBindingCreateSchema.shape.pathPrefix.safeParse(value);
|
|
120
|
+
if (!parsed.success) ctx.addIssue({ code: "custom", message: "ecommerce.validation.pathPrefixInvalid" });
|
|
121
|
+
}),
|
|
122
|
+
isPrimary: z.boolean()
|
|
123
|
+
});
|
|
124
|
+
function buildDomainBindingInitialValues(binding) {
|
|
125
|
+
return {
|
|
126
|
+
domainMappingId: binding?.domainMappingId ?? "",
|
|
127
|
+
pathPrefix: binding?.pathPrefix ?? "",
|
|
128
|
+
isPrimary: binding?.isPrimary ?? false
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
function buildDomainBindingCreatePayload(storeId, values) {
|
|
132
|
+
return {
|
|
133
|
+
storeId,
|
|
134
|
+
domainMappingId: values.domainMappingId,
|
|
135
|
+
pathPrefix: normalizeBindingPrefix(values.pathPrefix),
|
|
136
|
+
isPrimary: values.isPrimary === true
|
|
137
|
+
};
|
|
138
|
+
}
|
|
139
|
+
function buildDomainBindingUpdatePayload(bindingId, values) {
|
|
140
|
+
return {
|
|
141
|
+
id: bindingId,
|
|
142
|
+
domainMappingId: values.domainMappingId,
|
|
143
|
+
pathPrefix: normalizeBindingPrefix(values.pathPrefix),
|
|
144
|
+
isPrimary: values.isPrimary === true
|
|
145
|
+
};
|
|
146
|
+
}
|
|
147
|
+
export {
|
|
148
|
+
DOMAIN_BINDINGS_API_PATH,
|
|
149
|
+
DOMAIN_BINDINGS_API_URL,
|
|
150
|
+
DOMAIN_BINDINGS_PAGE_SIZE,
|
|
151
|
+
DOMAIN_MAPPINGS_API_URL,
|
|
152
|
+
DOMAIN_SETTINGS_HREF,
|
|
153
|
+
DOMAIN_STATUS_LABELS,
|
|
154
|
+
DOMAIN_STATUS_VARIANTS,
|
|
155
|
+
buildDomainBindingCreatePayload,
|
|
156
|
+
buildDomainBindingInitialValues,
|
|
157
|
+
buildDomainBindingUpdatePayload,
|
|
158
|
+
describeDomainFailureReason,
|
|
159
|
+
describeDomainStatus,
|
|
160
|
+
domainBindingFormSchema,
|
|
161
|
+
findDuplicateBinding,
|
|
162
|
+
findPreviousPrimary,
|
|
163
|
+
formatBindingAddress,
|
|
164
|
+
isServingStatus,
|
|
165
|
+
normalizeBindingPrefix
|
|
166
|
+
};
|
|
167
|
+
//# sourceMappingURL=storeDomains.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/modules/ecommerce/components/storeDomains.ts"],
|
|
4
|
+
"sourcesContent": ["import { z } from 'zod'\nimport type { StatusBadgeVariant } from '@open-mercato/ui/primitives/status-badge'\nimport type { DomainBindingMappingState } from '../data/enrichers'\nimport { ecommerceStoreDomainBindingCreateSchema, normalizePathPrefix } from '../data/validators'\nimport { isDomainMappingStatus, type DomainMappingStatus, type DomainMappingSummary } from '../lib/domainMappingSummaries'\n\nexport const DOMAIN_BINDINGS_API_PATH = 'ecommerce/store-domain-bindings'\nexport const DOMAIN_BINDINGS_API_URL = `/api/${DOMAIN_BINDINGS_API_PATH}`\nexport const DOMAIN_MAPPINGS_API_URL = '/api/ecommerce/domain-mappings'\nexport const DOMAIN_SETTINGS_HREF = '/backend/customer_accounts/settings/domain'\nexport const DOMAIN_BINDINGS_PAGE_SIZE = 100\n\nexport type DomainBindingRecord = {\n id: string\n storeId: string\n domainMappingId: string\n pathPrefix: string | null\n isPrimary: boolean\n createdAt: string | null\n updatedAt: string | null\n _domainMapping?: DomainBindingMappingState\n}\n\nexport type DomainBindingListResponse = {\n items: DomainBindingRecord[]\n total: number\n totalPages: number\n}\n\nexport type DomainMappingListResponse = {\n items: DomainMappingSummary[]\n total: number\n}\n\nexport type DomainBindingFormValues = {\n domainMappingId: string\n pathPrefix: string\n isPrimary: boolean\n}\n\nexport const DOMAIN_STATUS_VARIANTS: Record<DomainMappingStatus, StatusBadgeVariant> = {\n pending: 'info',\n verified: 'info',\n active: 'success',\n dns_failed: 'error',\n tls_failed: 'warning',\n}\n\nexport const DOMAIN_STATUS_LABELS: Record<DomainMappingStatus, { key: string; fallback: string }> = {\n pending: { key: 'ecommerce.backend.store.domains.status.pending', fallback: 'Pending' },\n verified: { key: 'ecommerce.backend.store.domains.status.verified', fallback: 'Verified' },\n active: { key: 'ecommerce.backend.store.domains.status.active', fallback: 'Active' },\n dns_failed: { key: 'ecommerce.backend.store.domains.status.dnsFailed', fallback: 'DNS failed' },\n tls_failed: { key: 'ecommerce.backend.store.domains.status.tlsFailed', fallback: 'TLS failed' },\n}\n\nexport type DomainFailureReasonLabel = { key: string; fallback: string; params: Record<string, string> }\n\ntype DomainFailureReasonPattern = {\n pattern: RegExp\n key: string\n fallback: string\n params: readonly string[]\n}\n\nconst DOMAIN_FAILURE_REASON_PATTERNS: readonly DomainFailureReasonPattern[] = [\n {\n pattern: /^HTTP (\\d{3})$/,\n key: 'ecommerce.backend.store.domains.failure.httpStatus',\n fallback: 'The TLS health check returned HTTP {status}',\n params: ['status'],\n },\n {\n pattern: /^TLS health check timed out$/,\n key: 'ecommerce.backend.store.domains.failure.tlsTimeout',\n fallback: 'The TLS health check timed out',\n params: [],\n },\n {\n pattern: /^TLS health check failed$/,\n key: 'ecommerce.backend.store.domains.failure.tlsFailed',\n fallback: 'The TLS health check failed',\n params: [],\n },\n {\n pattern: /^DNS lookup error \\((CNAME|A)\\): /,\n key: 'ecommerce.backend.store.domains.failure.dnsLookup',\n fallback: 'The DNS lookup for the {recordType} record failed',\n params: ['recordType'],\n },\n {\n pattern: /^CNAME points to (.+) instead of (.+)$/,\n key: 'ecommerce.backend.store.domains.failure.cnameMismatch',\n fallback: 'The CNAME record points to {actual} instead of {expected}',\n params: ['actual', 'expected'],\n },\n {\n pattern: /^No CNAME or A record found for /,\n key: 'ecommerce.backend.store.domains.failure.noRecords',\n fallback: 'No CNAME or A record was found',\n params: [],\n },\n {\n pattern: /^A record points to a known proxy IP, but reverse-resolve over HTTPS did not reach our server$/,\n key: 'ecommerce.backend.store.domains.failure.proxyUnreachable',\n fallback: 'The domain is behind a proxy that does not forward traffic to this platform',\n params: [],\n },\n {\n pattern: /^A record points to (.+) instead of (.+)$/,\n key: 'ecommerce.backend.store.domains.failure.aRecordMismatch',\n fallback: 'The A record points to {actual} instead of {expected}',\n params: ['actual', 'expected'],\n },\n {\n pattern: /^A record points to (.+) but apex-domain registration is not enabled on this deployment$/,\n key: 'ecommerce.backend.store.domains.failure.apexNotEnabled',\n fallback: 'The A record points to {actual}, but apex domains are not enabled on this deployment',\n params: ['actual'],\n },\n]\n\nexport function describeDomainFailureReason(reason: string): DomainFailureReasonLabel | null {\n for (const entry of DOMAIN_FAILURE_REASON_PATTERNS) {\n const match = entry.pattern.exec(reason)\n if (!match) continue\n const params: Record<string, string> = {}\n entry.params.forEach((name, index) => {\n params[name] = match[index + 1] ?? ''\n })\n return { key: entry.key, fallback: entry.fallback, params }\n }\n return null\n}\n\nexport function isServingStatus(status: string): boolean {\n return status === 'active'\n}\n\nexport function describeDomainStatus(status: string): { variant: StatusBadgeVariant; key: string; fallback: string } {\n if (isDomainMappingStatus(status)) {\n return { variant: DOMAIN_STATUS_VARIANTS[status], ...DOMAIN_STATUS_LABELS[status] }\n }\n return { variant: 'neutral', key: '', fallback: status }\n}\n\nexport function formatBindingAddress(hostname: string, pathPrefix: string | null): string {\n return `${hostname}${pathPrefix ?? ''}`\n}\n\nexport function normalizeBindingPrefix(value: string | null | undefined): string | null {\n const normalized = normalizePathPrefix(value ?? null)\n return typeof normalized === 'string' && normalized.length > 0 ? normalized : null\n}\n\nexport function findDuplicateBinding(\n bindings: readonly DomainBindingRecord[],\n candidate: { domainMappingId: string; pathPrefix: string | null },\n ignoreBindingId: string | null,\n): DomainBindingRecord | null {\n return (\n bindings.find(\n (binding) =>\n binding.id !== ignoreBindingId &&\n binding.domainMappingId === candidate.domainMappingId &&\n (binding.pathPrefix ?? null) === candidate.pathPrefix,\n ) ?? null\n )\n}\n\nexport function findPreviousPrimary(\n bindings: readonly DomainBindingRecord[],\n nextPrimaryId: string,\n): DomainBindingRecord | null {\n return bindings.find((binding) => binding.isPrimary && binding.id !== nextPrimaryId) ?? null\n}\n\nconst REQUIRED_MESSAGE = 'ui.forms.errors.required'\n\nexport const domainBindingFormSchema = z.object({\n domainMappingId: z.string().trim().min(1, REQUIRED_MESSAGE),\n pathPrefix: z\n .string()\n .superRefine((value, ctx) => {\n const parsed = ecommerceStoreDomainBindingCreateSchema.shape.pathPrefix.safeParse(value)\n if (!parsed.success) ctx.addIssue({ code: 'custom', message: 'ecommerce.validation.pathPrefixInvalid' })\n }),\n isPrimary: z.boolean(),\n})\n\nexport function buildDomainBindingInitialValues(binding: DomainBindingRecord | null): DomainBindingFormValues {\n return {\n domainMappingId: binding?.domainMappingId ?? '',\n pathPrefix: binding?.pathPrefix ?? '',\n isPrimary: binding?.isPrimary ?? false,\n }\n}\n\nexport function buildDomainBindingCreatePayload(\n storeId: string,\n values: DomainBindingFormValues,\n): { storeId: string; domainMappingId: string; pathPrefix: string | null; isPrimary: boolean } {\n return {\n storeId,\n domainMappingId: values.domainMappingId,\n pathPrefix: normalizeBindingPrefix(values.pathPrefix),\n isPrimary: values.isPrimary === true,\n }\n}\n\nexport function buildDomainBindingUpdatePayload(\n bindingId: string,\n values: DomainBindingFormValues,\n): { id: string; domainMappingId: string; pathPrefix: string | null; isPrimary: boolean } {\n return {\n id: bindingId,\n domainMappingId: values.domainMappingId,\n pathPrefix: normalizeBindingPrefix(values.pathPrefix),\n isPrimary: values.isPrimary === true,\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { jsx } from "react/jsx-runtime";
|
|
2
|
+
import { StoreBrandingTab } from "./StoreBrandingTab.js";
|
|
3
|
+
import { StoreChannelsTab } from "./StoreChannelsTab.js";
|
|
4
|
+
import { StoreDomainsTab } from "./StoreDomainsTab.js";
|
|
5
|
+
import { StoreGeneralTab } from "./StoreGeneralTab.js";
|
|
6
|
+
import { StoreSeoTab } from "./StoreSeoTab.js";
|
|
7
|
+
import { STORE_LIST_HREF } from "./storeAdmin.js";
|
|
8
|
+
const STORE_TAB_QUERY_PARAM = "tab";
|
|
9
|
+
const STORE_EDIT_TAB_IDS = ["general", "branding", "domains", "channels", "seo"];
|
|
10
|
+
const STORE_EDIT_TABS = [
|
|
11
|
+
{
|
|
12
|
+
id: "general",
|
|
13
|
+
labelKey: "ecommerce.backend.store.tabs.general",
|
|
14
|
+
fallbackLabel: "General",
|
|
15
|
+
render: ({ store, reload }) => /* @__PURE__ */ jsx(StoreGeneralTab, { store, reload })
|
|
16
|
+
},
|
|
17
|
+
{
|
|
18
|
+
id: "branding",
|
|
19
|
+
labelKey: "ecommerce.backend.store.tabs.branding",
|
|
20
|
+
fallbackLabel: "Branding",
|
|
21
|
+
render: ({ store, reload }) => /* @__PURE__ */ jsx(StoreBrandingTab, { store, reload })
|
|
22
|
+
},
|
|
23
|
+
{
|
|
24
|
+
id: "domains",
|
|
25
|
+
labelKey: "ecommerce.backend.store.tabs.domains",
|
|
26
|
+
fallbackLabel: "Domains",
|
|
27
|
+
render: ({ store, reload }) => /* @__PURE__ */ jsx(StoreDomainsTab, { store, reload })
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
id: "channels",
|
|
31
|
+
labelKey: "ecommerce.backend.store.tabs.channels",
|
|
32
|
+
fallbackLabel: "Channels",
|
|
33
|
+
render: ({ store, reload }) => /* @__PURE__ */ jsx(StoreChannelsTab, { store, reload })
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
id: "seo",
|
|
37
|
+
labelKey: "ecommerce.backend.store.tabs.seo",
|
|
38
|
+
fallbackLabel: "SEO",
|
|
39
|
+
render: ({ store, reload }) => /* @__PURE__ */ jsx(StoreSeoTab, { store, reload })
|
|
40
|
+
}
|
|
41
|
+
];
|
|
42
|
+
function isStoreEditTabId(value) {
|
|
43
|
+
return typeof value === "string" && STORE_EDIT_TAB_IDS.includes(value);
|
|
44
|
+
}
|
|
45
|
+
function buildStoreEditHref(storeId, tab) {
|
|
46
|
+
const base = `${STORE_LIST_HREF}/${encodeURIComponent(storeId)}`;
|
|
47
|
+
return tab ? `${base}?${STORE_TAB_QUERY_PARAM}=${tab}` : base;
|
|
48
|
+
}
|
|
49
|
+
function resolveActiveStoreTab(requested, tabs) {
|
|
50
|
+
if (!tabs.length) return null;
|
|
51
|
+
const match = tabs.find((tab) => tab.id === requested);
|
|
52
|
+
return (match ?? tabs[0]).id;
|
|
53
|
+
}
|
|
54
|
+
export {
|
|
55
|
+
STORE_EDIT_TABS,
|
|
56
|
+
STORE_EDIT_TAB_IDS,
|
|
57
|
+
STORE_TAB_QUERY_PARAM,
|
|
58
|
+
buildStoreEditHref,
|
|
59
|
+
isStoreEditTabId,
|
|
60
|
+
resolveActiveStoreTab
|
|
61
|
+
};
|
|
62
|
+
//# sourceMappingURL=storeEditTabs.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/modules/ecommerce/components/storeEditTabs.tsx"],
|
|
4
|
+
"sourcesContent": ["import type * as React from 'react'\nimport { StoreBrandingTab } from './StoreBrandingTab'\nimport { StoreChannelsTab } from './StoreChannelsTab'\nimport { StoreDomainsTab } from './StoreDomainsTab'\nimport { StoreGeneralTab } from './StoreGeneralTab'\nimport { StoreSeoTab } from './StoreSeoTab'\nimport { STORE_LIST_HREF, type StoreAdminRecord } from './storeAdmin'\n\nexport const STORE_TAB_QUERY_PARAM = 'tab'\n\nexport const STORE_EDIT_TAB_IDS = ['general', 'branding', 'domains', 'channels', 'seo'] as const\n\nexport type StoreEditTabId = (typeof STORE_EDIT_TAB_IDS)[number]\n\nexport type StoreEditTabContext = {\n store: StoreAdminRecord\n reload: () => Promise<void>\n}\n\nexport type StoreEditTabDefinition = {\n id: StoreEditTabId\n labelKey: string\n fallbackLabel: string\n render: (context: StoreEditTabContext) => React.ReactNode\n}\n\nexport const STORE_EDIT_TABS: readonly StoreEditTabDefinition[] = [\n {\n id: 'general',\n labelKey: 'ecommerce.backend.store.tabs.general',\n fallbackLabel: 'General',\n render: ({ store, reload }) => <StoreGeneralTab store={store} reload={reload} />,\n },\n {\n id: 'branding',\n labelKey: 'ecommerce.backend.store.tabs.branding',\n fallbackLabel: 'Branding',\n render: ({ store, reload }) => <StoreBrandingTab store={store} reload={reload} />,\n },\n {\n id: 'domains',\n labelKey: 'ecommerce.backend.store.tabs.domains',\n fallbackLabel: 'Domains',\n render: ({ store, reload }) => <StoreDomainsTab store={store} reload={reload} />,\n },\n {\n id: 'channels',\n labelKey: 'ecommerce.backend.store.tabs.channels',\n fallbackLabel: 'Channels',\n render: ({ store, reload }) => <StoreChannelsTab store={store} reload={reload} />,\n },\n {\n id: 'seo',\n labelKey: 'ecommerce.backend.store.tabs.seo',\n fallbackLabel: 'SEO',\n render: ({ store, reload }) => <StoreSeoTab store={store} reload={reload} />,\n },\n]\n\nexport function isStoreEditTabId(value: unknown): value is StoreEditTabId {\n return typeof value === 'string' && (STORE_EDIT_TAB_IDS as readonly string[]).includes(value)\n}\n\nexport function buildStoreEditHref(storeId: string, tab?: StoreEditTabId): string {\n const base = `${STORE_LIST_HREF}/${encodeURIComponent(storeId)}`\n return tab ? `${base}?${STORE_TAB_QUERY_PARAM}=${tab}` : base\n}\n\nexport function resolveActiveStoreTab(\n requested: string | null | undefined,\n tabs: readonly StoreEditTabDefinition[],\n): StoreEditTabId | null {\n if (!tabs.length) return null\n const match = tabs.find((tab) => tab.id === requested)\n return (match ?? tabs[0]).id\n}\n"],
|
|
5
|
+
"mappings": "AA+BmC;AA9BnC,SAAS,wBAAwB;AACjC,SAAS,wBAAwB;AACjC,SAAS,uBAAuB;AAChC,SAAS,uBAAuB;AAChC,SAAS,mBAAmB;AAC5B,SAAS,uBAA8C;AAEhD,MAAM,wBAAwB;AAE9B,MAAM,qBAAqB,CAAC,WAAW,YAAY,WAAW,YAAY,KAAK;AAgB/E,MAAM,kBAAqD;AAAA,EAChE;AAAA,IACE,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,eAAe;AAAA,IACf,QAAQ,CAAC,EAAE,OAAO,OAAO,MAAM,oBAAC,mBAAgB,OAAc,QAAgB;AAAA,EAChF;AAAA,EACA;AAAA,IACE,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,eAAe;AAAA,IACf,QAAQ,CAAC,EAAE,OAAO,OAAO,MAAM,oBAAC,oBAAiB,OAAc,QAAgB;AAAA,EACjF;AAAA,EACA;AAAA,IACE,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,eAAe;AAAA,IACf,QAAQ,CAAC,EAAE,OAAO,OAAO,MAAM,oBAAC,mBAAgB,OAAc,QAAgB;AAAA,EAChF;AAAA,EACA;AAAA,IACE,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,eAAe;AAAA,IACf,QAAQ,CAAC,EAAE,OAAO,OAAO,MAAM,oBAAC,oBAAiB,OAAc,QAAgB;AAAA,EACjF;AAAA,EACA;AAAA,IACE,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,eAAe;AAAA,IACf,QAAQ,CAAC,EAAE,OAAO,OAAO,MAAM,oBAAC,eAAY,OAAc,QAAgB;AAAA,EAC5E;AACF;AAEO,SAAS,iBAAiB,OAAyC;AACxE,SAAO,OAAO,UAAU,YAAa,mBAAyC,SAAS,KAAK;AAC9F;AAEO,SAAS,mBAAmB,SAAiB,KAA8B;AAChF,QAAM,OAAO,GAAG,eAAe,IAAI,mBAAmB,OAAO,CAAC;AAC9D,SAAO,MAAM,GAAG,IAAI,IAAI,qBAAqB,IAAI,GAAG,KAAK;AAC3D;AAEO,SAAS,sBACd,WACA,MACuB;AACvB,MAAI,CAAC,KAAK,OAAQ,QAAO;AACzB,QAAM,QAAQ,KAAK,KAAK,CAAC,QAAQ,IAAI,OAAO,SAAS;AACrD,UAAQ,SAAS,KAAK,CAAC,GAAG;AAC5B;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { refineDefaultLocaleSupported, storeIdentityFormShape } from "./StoreCreateDialog.js";
|
|
3
|
+
import { STORE_STATUSES } from "./storeAdmin.js";
|
|
4
|
+
const storeGeneralFormSchema = z.object({ ...storeIdentityFormShape, status: z.enum(STORE_STATUSES) }).superRefine(refineDefaultLocaleSupported);
|
|
5
|
+
function buildStoreGeneralInitialValues(store) {
|
|
6
|
+
return {
|
|
7
|
+
name: store.name,
|
|
8
|
+
code: store.code,
|
|
9
|
+
slug: store.slug,
|
|
10
|
+
status: store.status,
|
|
11
|
+
defaultLocale: store.defaultLocale,
|
|
12
|
+
supportedLocales: [...store.supportedLocales],
|
|
13
|
+
defaultCurrencyCode: store.defaultCurrencyCode
|
|
14
|
+
};
|
|
15
|
+
}
|
|
16
|
+
function buildStoreGeneralPayload(storeId, values) {
|
|
17
|
+
return {
|
|
18
|
+
id: storeId,
|
|
19
|
+
name: values.name.trim(),
|
|
20
|
+
code: values.code.trim(),
|
|
21
|
+
slug: values.slug.trim(),
|
|
22
|
+
status: values.status,
|
|
23
|
+
defaultLocale: values.defaultLocale.trim(),
|
|
24
|
+
supportedLocales: values.supportedLocales.map((locale) => locale.trim()),
|
|
25
|
+
defaultCurrencyCode: values.defaultCurrencyCode.trim().toUpperCase()
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
function isStoreDefaultPolicy(policy, storeId) {
|
|
29
|
+
return policy.storeId === storeId && !policy.productId && !policy.variantId;
|
|
30
|
+
}
|
|
31
|
+
const AVAILABILITY_LEAD_TIME_REQUIRED_MESSAGE = "ecommerce.validation.backorderLeadTimeRequired";
|
|
32
|
+
function parseLeadTimeDays(value) {
|
|
33
|
+
if (value === null || value === void 0) return null;
|
|
34
|
+
if (typeof value === "number") return Number.isInteger(value) && value >= 0 ? value : null;
|
|
35
|
+
const trimmed = value.trim();
|
|
36
|
+
if (!/^\d+$/.test(trimmed)) return null;
|
|
37
|
+
return Number.parseInt(trimmed, 10);
|
|
38
|
+
}
|
|
39
|
+
const availabilityDefaultsFormSchema = z.object({
|
|
40
|
+
hideWhenOutOfStock: z.boolean(),
|
|
41
|
+
allowBackorder: z.boolean(),
|
|
42
|
+
backorderLeadTimeDays: z.union([z.number(), z.string(), z.null()]).optional()
|
|
43
|
+
}).superRefine((value, ctx) => {
|
|
44
|
+
if (!value.allowBackorder) return;
|
|
45
|
+
if (parseLeadTimeDays(value.backorderLeadTimeDays) !== null) return;
|
|
46
|
+
ctx.addIssue({
|
|
47
|
+
code: "custom",
|
|
48
|
+
path: ["backorderLeadTimeDays"],
|
|
49
|
+
message: AVAILABILITY_LEAD_TIME_REQUIRED_MESSAGE
|
|
50
|
+
});
|
|
51
|
+
});
|
|
52
|
+
function buildAvailabilityInitialValues(policy) {
|
|
53
|
+
return {
|
|
54
|
+
hideWhenOutOfStock: policy?.hideWhenOutOfStock ?? false,
|
|
55
|
+
allowBackorder: policy?.allowBackorder ?? false,
|
|
56
|
+
backorderLeadTimeDays: policy?.backorderLeadTimeDays ?? null
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
function buildAvailabilityFields(values) {
|
|
60
|
+
const fields = {
|
|
61
|
+
hideWhenOutOfStock: values.hideWhenOutOfStock,
|
|
62
|
+
allowBackorder: values.allowBackorder
|
|
63
|
+
};
|
|
64
|
+
if (values.allowBackorder) {
|
|
65
|
+
const leadTime = parseLeadTimeDays(values.backorderLeadTimeDays);
|
|
66
|
+
if (leadTime !== null) fields.backorderLeadTimeDays = leadTime;
|
|
67
|
+
}
|
|
68
|
+
return fields;
|
|
69
|
+
}
|
|
70
|
+
function buildAvailabilityCreatePayload(store, values) {
|
|
71
|
+
if (!store.organizationId || !store.tenantId) return null;
|
|
72
|
+
return {
|
|
73
|
+
organizationId: store.organizationId,
|
|
74
|
+
tenantId: store.tenantId,
|
|
75
|
+
storeId: store.id,
|
|
76
|
+
productId: null,
|
|
77
|
+
variantId: null,
|
|
78
|
+
...buildAvailabilityFields(values)
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
function buildAvailabilityUpdatePayload(policyId, values) {
|
|
82
|
+
return { id: policyId, ...buildAvailabilityFields(values) };
|
|
83
|
+
}
|
|
84
|
+
export {
|
|
85
|
+
AVAILABILITY_LEAD_TIME_REQUIRED_MESSAGE,
|
|
86
|
+
availabilityDefaultsFormSchema,
|
|
87
|
+
buildAvailabilityCreatePayload,
|
|
88
|
+
buildAvailabilityInitialValues,
|
|
89
|
+
buildAvailabilityUpdatePayload,
|
|
90
|
+
buildStoreGeneralInitialValues,
|
|
91
|
+
buildStoreGeneralPayload,
|
|
92
|
+
isStoreDefaultPolicy,
|
|
93
|
+
storeGeneralFormSchema
|
|
94
|
+
};
|
|
95
|
+
//# sourceMappingURL=storeGeneral.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/modules/ecommerce/components/storeGeneral.ts"],
|
|
4
|
+
"sourcesContent": ["import { z } from 'zod'\nimport { refineDefaultLocaleSupported, storeIdentityFormShape } from './StoreCreateDialog'\nimport { STORE_STATUSES, type StoreAdminRecord, type StoreStatus } from './storeAdmin'\n\nexport type StoreGeneralFormValues = {\n name: string\n code: string\n slug: string\n status: StoreStatus\n defaultLocale: string\n supportedLocales: string[]\n defaultCurrencyCode: string\n}\n\nexport const storeGeneralFormSchema = z\n .object({ ...storeIdentityFormShape, status: z.enum(STORE_STATUSES) })\n .superRefine(refineDefaultLocaleSupported)\n\nexport function buildStoreGeneralInitialValues(store: StoreAdminRecord): StoreGeneralFormValues {\n return {\n name: store.name,\n code: store.code,\n slug: store.slug,\n status: store.status,\n defaultLocale: store.defaultLocale,\n supportedLocales: [...store.supportedLocales],\n defaultCurrencyCode: store.defaultCurrencyCode,\n }\n}\n\nexport type StoreGeneralUpdatePayload = StoreGeneralFormValues & { id: string }\n\nexport function buildStoreGeneralPayload(storeId: string, values: StoreGeneralFormValues): StoreGeneralUpdatePayload {\n return {\n id: storeId,\n name: values.name.trim(),\n code: values.code.trim(),\n slug: values.slug.trim(),\n status: values.status,\n defaultLocale: values.defaultLocale.trim(),\n supportedLocales: values.supportedLocales.map((locale) => locale.trim()),\n defaultCurrencyCode: values.defaultCurrencyCode.trim().toUpperCase(),\n }\n}\n\nexport type StoreDefaultPolicy = {\n id: string\n storeId: string | null\n productId: string | null\n variantId: string | null\n allowBackorder: boolean\n backorderLeadTimeDays: number | null\n hideWhenOutOfStock: boolean\n updatedAt: string | null\n}\n\nexport type PolicyListResponse = {\n items: StoreDefaultPolicy[]\n total: number\n totalPages: number\n}\n\nexport function isStoreDefaultPolicy(policy: StoreDefaultPolicy, storeId: string): boolean {\n return policy.storeId === storeId && !policy.productId && !policy.variantId\n}\n\nexport type AvailabilityDefaultsFormValues = {\n hideWhenOutOfStock: boolean\n allowBackorder: boolean\n backorderLeadTimeDays?: number | string | null\n}\n\nexport const AVAILABILITY_LEAD_TIME_REQUIRED_MESSAGE = 'ecommerce.validation.backorderLeadTimeRequired'\n\nfunction parseLeadTimeDays(value: number | string | null | undefined): number | null {\n if (value === null || value === undefined) return null\n if (typeof value === 'number') return Number.isInteger(value) && value >= 0 ? value : null\n const trimmed = value.trim()\n if (!/^\\d+$/.test(trimmed)) return null\n return Number.parseInt(trimmed, 10)\n}\n\nexport const availabilityDefaultsFormSchema = z\n .object({\n hideWhenOutOfStock: z.boolean(),\n allowBackorder: z.boolean(),\n backorderLeadTimeDays: z.union([z.number(), z.string(), z.null()]).optional(),\n })\n .superRefine((value, ctx) => {\n if (!value.allowBackorder) return\n if (parseLeadTimeDays(value.backorderLeadTimeDays) !== null) return\n ctx.addIssue({\n code: 'custom',\n path: ['backorderLeadTimeDays'],\n message: AVAILABILITY_LEAD_TIME_REQUIRED_MESSAGE,\n })\n })\n\nexport function buildAvailabilityInitialValues(policy: StoreDefaultPolicy | null): AvailabilityDefaultsFormValues {\n return {\n hideWhenOutOfStock: policy?.hideWhenOutOfStock ?? false,\n allowBackorder: policy?.allowBackorder ?? false,\n backorderLeadTimeDays: policy?.backorderLeadTimeDays ?? null,\n }\n}\n\ntype AvailabilityPolicyFields = {\n hideWhenOutOfStock: boolean\n allowBackorder: boolean\n backorderLeadTimeDays?: number\n}\n\nfunction buildAvailabilityFields(values: AvailabilityDefaultsFormValues): AvailabilityPolicyFields {\n const fields: AvailabilityPolicyFields = {\n hideWhenOutOfStock: values.hideWhenOutOfStock,\n allowBackorder: values.allowBackorder,\n }\n if (values.allowBackorder) {\n const leadTime = parseLeadTimeDays(values.backorderLeadTimeDays)\n if (leadTime !== null) fields.backorderLeadTimeDays = leadTime\n }\n return fields\n}\n\nexport type AvailabilityCreatePayload = AvailabilityPolicyFields & {\n organizationId: string\n tenantId: string\n storeId: string\n productId: null\n variantId: null\n}\n\nexport function buildAvailabilityCreatePayload(\n store: Pick<StoreAdminRecord, 'id' | 'organizationId' | 'tenantId'>,\n values: AvailabilityDefaultsFormValues,\n): AvailabilityCreatePayload | null {\n if (!store.organizationId || !store.tenantId) return null\n return {\n organizationId: store.organizationId,\n tenantId: store.tenantId,\n storeId: store.id,\n productId: null,\n variantId: null,\n ...buildAvailabilityFields(values),\n }\n}\n\nexport type AvailabilityUpdatePayload = AvailabilityPolicyFields & { id: string }\n\nexport function buildAvailabilityUpdatePayload(\n policyId: string,\n values: AvailabilityDefaultsFormValues,\n): AvailabilityUpdatePayload {\n return { id: policyId, ...buildAvailabilityFields(values) }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import {
|
|
3
|
+
ECOMMERCE_SEO_GOOGLE_VERIFICATION_MAX,
|
|
4
|
+
ECOMMERCE_SEO_META_DESCRIPTION_MAX,
|
|
5
|
+
ECOMMERCE_SEO_ROBOTS_TXT_MAX,
|
|
6
|
+
ECOMMERCE_SEO_SITE_NAME_MAX,
|
|
7
|
+
ecommerceStoreSeoSchema
|
|
8
|
+
} from "../data/validators.js";
|
|
9
|
+
const STORE_SEO_FIELD_KEYS = ["siteName", "defaultMetaDescription", "googleSiteVerification", "robotsTxt"];
|
|
10
|
+
const STORE_SEO_FIELD_LIMITS = {
|
|
11
|
+
siteName: ECOMMERCE_SEO_SITE_NAME_MAX,
|
|
12
|
+
defaultMetaDescription: ECOMMERCE_SEO_META_DESCRIPTION_MAX,
|
|
13
|
+
googleSiteVerification: ECOMMERCE_SEO_GOOGLE_VERIFICATION_MAX,
|
|
14
|
+
robotsTxt: ECOMMERCE_SEO_ROBOTS_TXT_MAX
|
|
15
|
+
};
|
|
16
|
+
const SEO_FIELD_ERROR_PREFIX = "settings.seo.";
|
|
17
|
+
function buildStoreSeoInput(values) {
|
|
18
|
+
const input = {};
|
|
19
|
+
for (const key of STORE_SEO_FIELD_KEYS) {
|
|
20
|
+
const value = values[key];
|
|
21
|
+
if (typeof value !== "string") continue;
|
|
22
|
+
if (value.trim().length === 0) continue;
|
|
23
|
+
input[key] = value;
|
|
24
|
+
}
|
|
25
|
+
return input;
|
|
26
|
+
}
|
|
27
|
+
const seoFormShape = {
|
|
28
|
+
siteName: z.string(),
|
|
29
|
+
defaultMetaDescription: z.string(),
|
|
30
|
+
googleSiteVerification: z.string(),
|
|
31
|
+
robotsTxt: z.string()
|
|
32
|
+
};
|
|
33
|
+
const storeSeoFormSchema = z.object(seoFormShape).superRefine((values, context) => {
|
|
34
|
+
const result = ecommerceStoreSeoSchema.safeParse(buildStoreSeoInput(values));
|
|
35
|
+
if (result.success) return;
|
|
36
|
+
for (const issue of result.error.issues) {
|
|
37
|
+
context.addIssue({ code: "custom", path: issue.path, message: issue.message });
|
|
38
|
+
}
|
|
39
|
+
});
|
|
40
|
+
function buildStoreSeoInitialValues(store) {
|
|
41
|
+
const parsed = ecommerceStoreSeoSchema.safeParse(store.settings?.seo ?? {});
|
|
42
|
+
const stored = parsed.success ? parsed.data : {};
|
|
43
|
+
return {
|
|
44
|
+
siteName: stored.siteName ?? "",
|
|
45
|
+
defaultMetaDescription: stored.defaultMetaDescription ?? "",
|
|
46
|
+
googleSiteVerification: stored.googleSiteVerification ?? "",
|
|
47
|
+
robotsTxt: stored.robotsTxt ?? ""
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
function buildStoreSeoPayload(storeId, values) {
|
|
51
|
+
return { id: storeId, settings: { seo: buildStoreSeoInput(values) } };
|
|
52
|
+
}
|
|
53
|
+
function remapStoreSeoFieldErrors(fieldErrors) {
|
|
54
|
+
if (!fieldErrors) return void 0;
|
|
55
|
+
const mapped = {};
|
|
56
|
+
for (const [key, message] of Object.entries(fieldErrors)) {
|
|
57
|
+
mapped[key.startsWith(SEO_FIELD_ERROR_PREFIX) ? key.slice(SEO_FIELD_ERROR_PREFIX.length) : key] = message;
|
|
58
|
+
}
|
|
59
|
+
return mapped;
|
|
60
|
+
}
|
|
61
|
+
export {
|
|
62
|
+
STORE_SEO_FIELD_KEYS,
|
|
63
|
+
STORE_SEO_FIELD_LIMITS,
|
|
64
|
+
buildStoreSeoInitialValues,
|
|
65
|
+
buildStoreSeoPayload,
|
|
66
|
+
remapStoreSeoFieldErrors,
|
|
67
|
+
storeSeoFormSchema
|
|
68
|
+
};
|
|
69
|
+
//# sourceMappingURL=storeSeo.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/modules/ecommerce/components/storeSeo.ts"],
|
|
4
|
+
"sourcesContent": ["import { z } from 'zod'\nimport {\n ECOMMERCE_SEO_GOOGLE_VERIFICATION_MAX,\n ECOMMERCE_SEO_META_DESCRIPTION_MAX,\n ECOMMERCE_SEO_ROBOTS_TXT_MAX,\n ECOMMERCE_SEO_SITE_NAME_MAX,\n ecommerceStoreSeoSchema,\n} from '../data/validators'\nimport type { StoreAdminRecord } from './storeAdmin'\n\nexport const STORE_SEO_FIELD_KEYS = ['siteName', 'defaultMetaDescription', 'googleSiteVerification', 'robotsTxt'] as const\n\nexport type StoreSeoFieldKey = (typeof STORE_SEO_FIELD_KEYS)[number]\n\nexport type StoreSeoFormValues = Record<StoreSeoFieldKey, string>\n\nexport const STORE_SEO_FIELD_LIMITS: Record<StoreSeoFieldKey, number> = {\n siteName: ECOMMERCE_SEO_SITE_NAME_MAX,\n defaultMetaDescription: ECOMMERCE_SEO_META_DESCRIPTION_MAX,\n googleSiteVerification: ECOMMERCE_SEO_GOOGLE_VERIFICATION_MAX,\n robotsTxt: ECOMMERCE_SEO_ROBOTS_TXT_MAX,\n}\n\nconst SEO_FIELD_ERROR_PREFIX = 'settings.seo.'\n\ntype StoreSeoPayloadInput = Partial<Record<StoreSeoFieldKey, string>>\n\nfunction buildStoreSeoInput(values: Partial<Record<StoreSeoFieldKey, unknown>>): StoreSeoPayloadInput {\n const input: StoreSeoPayloadInput = {}\n for (const key of STORE_SEO_FIELD_KEYS) {\n const value = values[key]\n if (typeof value !== 'string') continue\n if (value.trim().length === 0) continue\n input[key] = value\n }\n return input\n}\n\nconst seoFormShape = {\n siteName: z.string(),\n defaultMetaDescription: z.string(),\n googleSiteVerification: z.string(),\n robotsTxt: z.string(),\n} satisfies Record<StoreSeoFieldKey, z.ZodString>\n\nexport const storeSeoFormSchema = z.object(seoFormShape).superRefine((values, context) => {\n const result = ecommerceStoreSeoSchema.safeParse(buildStoreSeoInput(values))\n if (result.success) return\n for (const issue of result.error.issues) {\n context.addIssue({ code: 'custom', path: issue.path, message: issue.message })\n }\n})\n\nexport function buildStoreSeoInitialValues(store: Pick<StoreAdminRecord, 'settings'>): StoreSeoFormValues {\n const parsed = ecommerceStoreSeoSchema.safeParse(store.settings?.seo ?? {})\n const stored = parsed.success ? parsed.data : {}\n return {\n siteName: stored.siteName ?? '',\n defaultMetaDescription: stored.defaultMetaDescription ?? '',\n googleSiteVerification: stored.googleSiteVerification ?? '',\n robotsTxt: stored.robotsTxt ?? '',\n }\n}\n\nexport type StoreSeoUpdatePayload = { id: string; settings: { seo: StoreSeoPayloadInput } }\n\nexport function buildStoreSeoPayload(storeId: string, values: Partial<Record<StoreSeoFieldKey, unknown>>): StoreSeoUpdatePayload {\n return { id: storeId, settings: { seo: buildStoreSeoInput(values) } }\n}\n\nexport function remapStoreSeoFieldErrors(fieldErrors: Record<string, string> | undefined): Record<string, string> | undefined {\n if (!fieldErrors) return undefined\n const mapped: Record<string, string> = {}\n for (const [key, message] of Object.entries(fieldErrors)) {\n mapped[key.startsWith(SEO_FIELD_ERROR_PREFIX) ? key.slice(SEO_FIELD_ERROR_PREFIX.length) : key] = message\n }\n return mapped\n}\n"],
|
|
5
|
+
"mappings": "AAAA,SAAS,SAAS;AAClB;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAGA,MAAM,uBAAuB,CAAC,YAAY,0BAA0B,0BAA0B,WAAW;AAMzG,MAAM,yBAA2D;AAAA,EACtE,UAAU;AAAA,EACV,wBAAwB;AAAA,EACxB,wBAAwB;AAAA,EACxB,WAAW;AACb;AAEA,MAAM,yBAAyB;AAI/B,SAAS,mBAAmB,QAA0E;AACpG,QAAM,QAA8B,CAAC;AACrC,aAAW,OAAO,sBAAsB;AACtC,UAAM,QAAQ,OAAO,GAAG;AACxB,QAAI,OAAO,UAAU,SAAU;AAC/B,QAAI,MAAM,KAAK,EAAE,WAAW,EAAG;AAC/B,UAAM,GAAG,IAAI;AAAA,EACf;AACA,SAAO;AACT;AAEA,MAAM,eAAe;AAAA,EACnB,UAAU,EAAE,OAAO;AAAA,EACnB,wBAAwB,EAAE,OAAO;AAAA,EACjC,wBAAwB,EAAE,OAAO;AAAA,EACjC,WAAW,EAAE,OAAO;AACtB;AAEO,MAAM,qBAAqB,EAAE,OAAO,YAAY,EAAE,YAAY,CAAC,QAAQ,YAAY;AACxF,QAAM,SAAS,wBAAwB,UAAU,mBAAmB,MAAM,CAAC;AAC3E,MAAI,OAAO,QAAS;AACpB,aAAW,SAAS,OAAO,MAAM,QAAQ;AACvC,YAAQ,SAAS,EAAE,MAAM,UAAU,MAAM,MAAM,MAAM,SAAS,MAAM,QAAQ,CAAC;AAAA,EAC/E;AACF,CAAC;AAEM,SAAS,2BAA2B,OAA+D;AACxG,QAAM,SAAS,wBAAwB,UAAU,MAAM,UAAU,OAAO,CAAC,CAAC;AAC1E,QAAM,SAAS,OAAO,UAAU,OAAO,OAAO,CAAC;AAC/C,SAAO;AAAA,IACL,UAAU,OAAO,YAAY;AAAA,IAC7B,wBAAwB,OAAO,0BAA0B;AAAA,IACzD,wBAAwB,OAAO,0BAA0B;AAAA,IACzD,WAAW,OAAO,aAAa;AAAA,EACjC;AACF;AAIO,SAAS,qBAAqB,SAAiB,QAA2E;AAC/H,SAAO,EAAE,IAAI,SAAS,UAAU,EAAE,KAAK,mBAAmB,MAAM,EAAE,EAAE;AACtE;AAEO,SAAS,yBAAyB,aAAqF;AAC5H,MAAI,CAAC,YAAa,QAAO;AACzB,QAAM,SAAiC,CAAC;AACxC,aAAW,CAAC,KAAK,OAAO,KAAK,OAAO,QAAQ,WAAW,GAAG;AACxD,WAAO,IAAI,WAAW,sBAAsB,IAAI,IAAI,MAAM,uBAAuB,MAAM,IAAI,GAAG,IAAI;AAAA,EACpG;AACA,SAAO;AACT;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|