@wix/headless-bookings 0.0.115 → 0.0.117
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/cjs/dist/react/booking-form/BookingForm.d.ts +2 -0
- package/cjs/dist/react/booking-form/BookingForm.js +2 -2
- package/cjs/dist/react/core/booking-form/BookingForm.d.ts +2 -0
- package/cjs/dist/react/core/booking-form/BookingForm.js +3 -3
- package/cjs/dist/services/booking/book-action/bookAction.js +1 -0
- package/cjs/dist/services/booking/book-action/buildCheckoutRequest.d.ts +2 -0
- package/cjs/dist/services/booking/book-action/buildCheckoutRequest.js +2 -2
- package/cjs/dist/services/booking/book-action/types.d.ts +2 -0
- package/cjs/dist/services/booking/booking.d.ts +2 -0
- package/cjs/dist/services/booking/booking.js +1 -0
- package/cjs/dist/services/booking-form/booking-form.d.ts +4 -0
- package/cjs/dist/services/booking-form/booking-form.js +11 -8
- package/cjs/dist/services/service-list/service-list.js +18 -12
- package/dist/react/booking-form/BookingForm.d.ts +2 -0
- package/dist/react/booking-form/BookingForm.js +2 -2
- package/dist/react/core/booking-form/BookingForm.d.ts +2 -0
- package/dist/react/core/booking-form/BookingForm.js +3 -3
- package/dist/services/booking/book-action/bookAction.js +1 -0
- package/dist/services/booking/book-action/buildCheckoutRequest.d.ts +2 -0
- package/dist/services/booking/book-action/buildCheckoutRequest.js +2 -2
- package/dist/services/booking/book-action/types.d.ts +2 -0
- package/dist/services/booking/booking.d.ts +2 -0
- package/dist/services/booking/booking.js +1 -0
- package/dist/services/booking-form/booking-form.d.ts +4 -0
- package/dist/services/booking-form/booking-form.js +11 -8
- package/dist/services/service-list/service-list.js +18 -12
- package/package.json +2 -2
|
@@ -21,6 +21,8 @@ export interface RootProps {
|
|
|
21
21
|
serviceIds?: string[];
|
|
22
22
|
/** Optional additional metadata to pass to FormService */
|
|
23
23
|
additionalMetadata?: Record<string, string | string[]>;
|
|
24
|
+
/** Optional namespace override for the form. Defaults to the bookings namespace. */
|
|
25
|
+
namespace?: string;
|
|
24
26
|
/** Field map to override default booking field components */
|
|
25
27
|
fieldMap: FieldMap;
|
|
26
28
|
/**
|
|
@@ -151,8 +151,8 @@ exports.TestIds = {
|
|
|
151
151
|
* ```
|
|
152
152
|
*/
|
|
153
153
|
exports.Root = react_1.default.forwardRef((props, ref) => {
|
|
154
|
-
const { children, asChild, className, formId, serviceIds, additionalMetadata, fieldMap, rowGapClassname = 'gap-y-4', columnGapClassname = 'gap-x-2', loadErrorFallback, ...otherProps } = props;
|
|
155
|
-
return ((0, jsx_runtime_1.jsx)(BookingFormErrorBoundary, { fallback: loadErrorFallback, children: (0, jsx_runtime_1.jsx)(CoreBookingForm.Root, { formId: formId, serviceIds: serviceIds, additionalMetadata: additionalMetadata, fieldMap: fieldMap, children: (renderProps) => {
|
|
154
|
+
const { children, asChild, className, formId, serviceIds, additionalMetadata, namespace, fieldMap, rowGapClassname = 'gap-y-4', columnGapClassname = 'gap-x-2', loadErrorFallback, ...otherProps } = props;
|
|
155
|
+
return ((0, jsx_runtime_1.jsx)(BookingFormErrorBoundary, { fallback: loadErrorFallback, children: (0, jsx_runtime_1.jsx)(CoreBookingForm.Root, { formId: formId, serviceIds: serviceIds, additionalMetadata: additionalMetadata, namespace: namespace, fieldMap: fieldMap, children: (renderProps) => {
|
|
156
156
|
// If children is a render prop function, call it with the render props
|
|
157
157
|
if (typeof children === 'function') {
|
|
158
158
|
return children(renderProps);
|
|
@@ -44,6 +44,8 @@ interface BookingFormBaseProps {
|
|
|
44
44
|
serviceIds?: string[];
|
|
45
45
|
/** Optional additional metadata to pass to FormService */
|
|
46
46
|
additionalMetadata?: Record<string, string | string[]>;
|
|
47
|
+
/** Optional namespace override for the form. Defaults to the bookings namespace. */
|
|
48
|
+
namespace?: string;
|
|
47
49
|
/** Field map to override default booking field components */
|
|
48
50
|
fieldMap: FieldMap;
|
|
49
51
|
/** Render prop function that receives form data and actions */
|
|
@@ -129,13 +129,13 @@ const signals_1 = require("@wix/services-definitions/core-services/signals");
|
|
|
129
129
|
* ```
|
|
130
130
|
*/
|
|
131
131
|
function Root(props) {
|
|
132
|
-
const { serviceIds, additionalMetadata, fieldMap, children } = props;
|
|
132
|
+
const { serviceIds, additionalMetadata, namespace, fieldMap, children } = props;
|
|
133
133
|
// Create formRef to pass to Form.Root and BookingFormContent
|
|
134
134
|
const formRef = (0, react_1.useRef)(null);
|
|
135
135
|
const bookingFormServiceConfig = props.form
|
|
136
|
-
? { form: props.form }
|
|
136
|
+
? { form: props.form, ...(namespace !== undefined ? { namespace } : {}) }
|
|
137
137
|
: props.formId
|
|
138
|
-
? { formId: props.formId, additionalMetadata, serviceIds }
|
|
138
|
+
? { formId: props.formId, additionalMetadata, serviceIds, namespace }
|
|
139
139
|
: undefined;
|
|
140
140
|
// Use Form.Root to set up FormService, then nest WixServices for BookingFormService
|
|
141
141
|
// This allows BookingFormService to access FormService via getService internally
|
|
@@ -10,6 +10,8 @@ export interface BuildCheckoutParams {
|
|
|
10
10
|
bookingId: string;
|
|
11
11
|
contactDetails?: ContactDetails;
|
|
12
12
|
businessLocationId?: string;
|
|
13
|
+
/** Optional app ID override for the catalog reference. Defaults to BOOKING_APP_ID. */
|
|
14
|
+
appId?: string;
|
|
13
15
|
}
|
|
14
16
|
/**
|
|
15
17
|
* Builds a checkout request from the booking ID and contact details
|
|
@@ -19,7 +19,7 @@ const constants_js_1 = require("../../constants.js");
|
|
|
19
19
|
* @returns CreateCheckoutRequest ready to be sent to the API
|
|
20
20
|
*/
|
|
21
21
|
function buildCheckoutRequest(params) {
|
|
22
|
-
const { bookingId, contactDetails, businessLocationId } = params;
|
|
22
|
+
const { bookingId, contactDetails, businessLocationId, appId } = params;
|
|
23
23
|
// Build checkoutInfo incrementally for readability
|
|
24
24
|
const checkoutInfo = {};
|
|
25
25
|
// businessLocationId for multi-location support
|
|
@@ -56,7 +56,7 @@ function buildCheckoutRequest(params) {
|
|
|
56
56
|
quantity: 1,
|
|
57
57
|
catalogReference: {
|
|
58
58
|
catalogItemId: bookingId,
|
|
59
|
-
appId: constants_js_1.BOOKING_APP_ID,
|
|
59
|
+
appId: appId ?? constants_js_1.BOOKING_APP_ID,
|
|
60
60
|
},
|
|
61
61
|
},
|
|
62
62
|
],
|
|
@@ -36,6 +36,8 @@ export interface BookActionParams {
|
|
|
36
36
|
location: TimeSlotLocationType | null;
|
|
37
37
|
formSubmission: FormValues | null;
|
|
38
38
|
timezone?: string;
|
|
39
|
+
/** Optional app ID override for the catalog reference. Defaults to the bookings app ID. */
|
|
40
|
+
appId?: string;
|
|
39
41
|
}
|
|
40
42
|
/**
|
|
41
43
|
* Props passed to children of Book component
|
|
@@ -110,6 +110,8 @@ export interface BookingServiceConfig {
|
|
|
110
110
|
timezone?: string;
|
|
111
111
|
/** Optional initial form submission */
|
|
112
112
|
formSubmission?: FormValues | null;
|
|
113
|
+
/** Optional app ID override for the catalog reference. Defaults to the bookings app ID. */
|
|
114
|
+
appId?: string;
|
|
113
115
|
}
|
|
114
116
|
/**
|
|
115
117
|
* Implementation of BookingService
|
|
@@ -55,9 +55,13 @@ export type BookingFormServiceConfig = {
|
|
|
55
55
|
additionalMetadata?: Record<string, string | string[]>;
|
|
56
56
|
/** Optional list of service IDs to pass to FormService */
|
|
57
57
|
serviceIds?: string[];
|
|
58
|
+
/** Optional namespace override. Defaults to BOOKING_FORM_NAMESPACE. */
|
|
59
|
+
namespace?: string;
|
|
58
60
|
} | {
|
|
59
61
|
/** Pre-loaded form object (SSR/SSG) - must be from bookings namespace */
|
|
60
62
|
form: forms.Form;
|
|
63
|
+
/** Optional namespace override. Defaults to BOOKING_FORM_NAMESPACE. */
|
|
64
|
+
namespace?: string;
|
|
61
65
|
};
|
|
62
66
|
/**
|
|
63
67
|
* API interface for the BookingForm service.
|
|
@@ -61,15 +61,18 @@ exports.BookingFormServiceDefinition = (0, services_definitions_1.defineService)
|
|
|
61
61
|
// Validation Helpers
|
|
62
62
|
// ============================================================================
|
|
63
63
|
/**
|
|
64
|
-
* Validates that a form belongs to the
|
|
65
|
-
*
|
|
66
|
-
*
|
|
64
|
+
* Validates that a form belongs to the expected namespace.
|
|
65
|
+
* When a custom namespace is provided, validates against it; otherwise validates
|
|
66
|
+
* against BOOKING_FORM_NAMESPACE.
|
|
67
|
+
* @param form The form to validate
|
|
68
|
+
* @param expectedNamespace The expected namespace (defaults to BOOKING_FORM_NAMESPACE)
|
|
69
|
+
* @throws Error if the form namespace does not match the expected namespace
|
|
67
70
|
*/
|
|
68
|
-
function validateBookingFormNamespace(form) {
|
|
71
|
+
function validateBookingFormNamespace(form, expectedNamespace = exports.BOOKING_FORM_NAMESPACE) {
|
|
69
72
|
const formNamespace = form.namespace;
|
|
70
|
-
if (formNamespace && formNamespace !==
|
|
73
|
+
if (formNamespace && formNamespace !== expectedNamespace) {
|
|
71
74
|
throw new Error(`BookingFormService: Invalid form namespace. ` +
|
|
72
|
-
`Expected "${
|
|
75
|
+
`Expected "${expectedNamespace}", but received "${formNamespace}". ` +
|
|
73
76
|
`Ensure the form is a booking form.`);
|
|
74
77
|
}
|
|
75
78
|
}
|
|
@@ -78,7 +81,7 @@ function validateBookingFormConfig({ config, services, }) {
|
|
|
78
81
|
return;
|
|
79
82
|
}
|
|
80
83
|
if ((0, utils_js_1.hasForm)(config)) {
|
|
81
|
-
validateBookingFormNamespace(config.form);
|
|
84
|
+
validateBookingFormNamespace(config.form, config.namespace);
|
|
82
85
|
const servicesFormId = services.length > 1 ? DEFAULT_FORM_ID : services?.[0]?.form?._id;
|
|
83
86
|
if (servicesFormId !== config.form._id) {
|
|
84
87
|
throw new Error(`BookingFormService: Invalid form ID. ` +
|
|
@@ -236,7 +239,7 @@ exports.BookingFormService = services_definitions_1.implementService.withConfig(
|
|
|
236
239
|
? { form: config.form }
|
|
237
240
|
: {
|
|
238
241
|
formId: formIdValue,
|
|
239
|
-
namespace: exports.BOOKING_FORM_NAMESPACE,
|
|
242
|
+
namespace: config?.namespace ?? exports.BOOKING_FORM_NAMESPACE,
|
|
240
243
|
additionalMetadata: {
|
|
241
244
|
...config?.additionalMetadata,
|
|
242
245
|
serviceIds,
|
|
@@ -183,7 +183,7 @@ exports.ServiceListService = services_definitions_1.implementService.withConfig(
|
|
|
183
183
|
// Use effectiveFilterSignal.peek() to get the computed filter value
|
|
184
184
|
const effectiveFilter = effectiveFilterSignal.peek();
|
|
185
185
|
isLoadingSignal.set(true);
|
|
186
|
-
Promise.
|
|
186
|
+
Promise.allSettled([
|
|
187
187
|
(0, index_js_1.queryServices)({
|
|
188
188
|
appId: initialQueryOptions.appId,
|
|
189
189
|
filter: effectiveFilter,
|
|
@@ -195,15 +195,21 @@ exports.ServiceListService = services_definitions_1.implementService.withConfig(
|
|
|
195
195
|
}),
|
|
196
196
|
!hasInitialCategories ? (0, index_js_2.queryCategories)() : Promise.resolve(null),
|
|
197
197
|
])
|
|
198
|
-
.then(([
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
categoriesSignal.set(categoriesResult.categories);
|
|
198
|
+
.then(([servicesSettled, categoriesSettled]) => {
|
|
199
|
+
if (servicesSettled.status === 'fulfilled') {
|
|
200
|
+
servicesSignal.set(servicesSettled.value.services);
|
|
201
|
+
pagingMetadataSignal.set(servicesSettled.value.pagingMetadata);
|
|
203
202
|
}
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
203
|
+
else {
|
|
204
|
+
errorSignal.set(servicesSettled.reason instanceof Error
|
|
205
|
+
? servicesSettled.reason.message
|
|
206
|
+
: 'Unknown error');
|
|
207
|
+
}
|
|
208
|
+
if (categoriesSettled.status === 'fulfilled' &&
|
|
209
|
+
categoriesSettled.value) {
|
|
210
|
+
categoriesSignal.set(categoriesSettled.value.categories);
|
|
211
|
+
}
|
|
212
|
+
// If categories fail, silently keep empty categories — filter won't be shown
|
|
207
213
|
})
|
|
208
214
|
.finally(() => {
|
|
209
215
|
isLoadingSignal.set(false);
|
|
@@ -379,7 +385,7 @@ exports.ServiceListService = services_definitions_1.implementService.withConfig(
|
|
|
379
385
|
*/
|
|
380
386
|
async function loadServiceListServiceInitialData(options) {
|
|
381
387
|
try {
|
|
382
|
-
// Fetch services and categories in parallel
|
|
388
|
+
// Fetch services and categories in parallel; categories failure is non-fatal
|
|
383
389
|
const [servicesResult, categoriesResult] = await Promise.all([
|
|
384
390
|
(0, index_js_1.queryServices)({
|
|
385
391
|
appId: options.appId,
|
|
@@ -387,13 +393,13 @@ async function loadServiceListServiceInitialData(options) {
|
|
|
387
393
|
pagingMetadata: options.pagingMetadata,
|
|
388
394
|
sort: options.sort,
|
|
389
395
|
}),
|
|
390
|
-
(0, index_js_2.queryCategories)(),
|
|
396
|
+
(0, index_js_2.queryCategories)().catch(() => null),
|
|
391
397
|
]);
|
|
392
398
|
return {
|
|
393
399
|
type: 'success',
|
|
394
400
|
config: {
|
|
395
401
|
services: servicesResult.services,
|
|
396
|
-
categories: categoriesResult
|
|
402
|
+
categories: categoriesResult?.categories ?? [],
|
|
397
403
|
options: {
|
|
398
404
|
...options,
|
|
399
405
|
pagingMetadata: servicesResult.pagingMetadata,
|
|
@@ -21,6 +21,8 @@ export interface RootProps {
|
|
|
21
21
|
serviceIds?: string[];
|
|
22
22
|
/** Optional additional metadata to pass to FormService */
|
|
23
23
|
additionalMetadata?: Record<string, string | string[]>;
|
|
24
|
+
/** Optional namespace override for the form. Defaults to the bookings namespace. */
|
|
25
|
+
namespace?: string;
|
|
24
26
|
/** Field map to override default booking field components */
|
|
25
27
|
fieldMap: FieldMap;
|
|
26
28
|
/**
|
|
@@ -112,8 +112,8 @@ export const TestIds = {
|
|
|
112
112
|
* ```
|
|
113
113
|
*/
|
|
114
114
|
export const Root = React.forwardRef((props, ref) => {
|
|
115
|
-
const { children, asChild, className, formId, serviceIds, additionalMetadata, fieldMap, rowGapClassname = 'gap-y-4', columnGapClassname = 'gap-x-2', loadErrorFallback, ...otherProps } = props;
|
|
116
|
-
return (_jsx(BookingFormErrorBoundary, { fallback: loadErrorFallback, children: _jsx(CoreBookingForm.Root, { formId: formId, serviceIds: serviceIds, additionalMetadata: additionalMetadata, fieldMap: fieldMap, children: (renderProps) => {
|
|
115
|
+
const { children, asChild, className, formId, serviceIds, additionalMetadata, namespace, fieldMap, rowGapClassname = 'gap-y-4', columnGapClassname = 'gap-x-2', loadErrorFallback, ...otherProps } = props;
|
|
116
|
+
return (_jsx(BookingFormErrorBoundary, { fallback: loadErrorFallback, children: _jsx(CoreBookingForm.Root, { formId: formId, serviceIds: serviceIds, additionalMetadata: additionalMetadata, namespace: namespace, fieldMap: fieldMap, children: (renderProps) => {
|
|
117
117
|
// If children is a render prop function, call it with the render props
|
|
118
118
|
if (typeof children === 'function') {
|
|
119
119
|
return children(renderProps);
|
|
@@ -44,6 +44,8 @@ interface BookingFormBaseProps {
|
|
|
44
44
|
serviceIds?: string[];
|
|
45
45
|
/** Optional additional metadata to pass to FormService */
|
|
46
46
|
additionalMetadata?: Record<string, string | string[]>;
|
|
47
|
+
/** Optional namespace override for the form. Defaults to the bookings namespace. */
|
|
48
|
+
namespace?: string;
|
|
47
49
|
/** Field map to override default booking field components */
|
|
48
50
|
fieldMap: FieldMap;
|
|
49
51
|
/** Render prop function that receives form data and actions */
|
|
@@ -90,13 +90,13 @@ import { SignalsServiceDefinition } from '@wix/services-definitions/core-service
|
|
|
90
90
|
* ```
|
|
91
91
|
*/
|
|
92
92
|
export function Root(props) {
|
|
93
|
-
const { serviceIds, additionalMetadata, fieldMap, children } = props;
|
|
93
|
+
const { serviceIds, additionalMetadata, namespace, fieldMap, children } = props;
|
|
94
94
|
// Create formRef to pass to Form.Root and BookingFormContent
|
|
95
95
|
const formRef = useRef(null);
|
|
96
96
|
const bookingFormServiceConfig = props.form
|
|
97
|
-
? { form: props.form }
|
|
97
|
+
? { form: props.form, ...(namespace !== undefined ? { namespace } : {}) }
|
|
98
98
|
: props.formId
|
|
99
|
-
? { formId: props.formId, additionalMetadata, serviceIds }
|
|
99
|
+
? { formId: props.formId, additionalMetadata, serviceIds, namespace }
|
|
100
100
|
: undefined;
|
|
101
101
|
// Use Form.Root to set up FormService, then nest WixServices for BookingFormService
|
|
102
102
|
// This allows BookingFormService to access FormService via getService internally
|
|
@@ -10,6 +10,8 @@ export interface BuildCheckoutParams {
|
|
|
10
10
|
bookingId: string;
|
|
11
11
|
contactDetails?: ContactDetails;
|
|
12
12
|
businessLocationId?: string;
|
|
13
|
+
/** Optional app ID override for the catalog reference. Defaults to BOOKING_APP_ID. */
|
|
14
|
+
appId?: string;
|
|
13
15
|
}
|
|
14
16
|
/**
|
|
15
17
|
* Builds a checkout request from the booking ID and contact details
|
|
@@ -16,7 +16,7 @@ import { BOOKING_APP_ID } from '../../constants.js';
|
|
|
16
16
|
* @returns CreateCheckoutRequest ready to be sent to the API
|
|
17
17
|
*/
|
|
18
18
|
export function buildCheckoutRequest(params) {
|
|
19
|
-
const { bookingId, contactDetails, businessLocationId } = params;
|
|
19
|
+
const { bookingId, contactDetails, businessLocationId, appId } = params;
|
|
20
20
|
// Build checkoutInfo incrementally for readability
|
|
21
21
|
const checkoutInfo = {};
|
|
22
22
|
// businessLocationId for multi-location support
|
|
@@ -53,7 +53,7 @@ export function buildCheckoutRequest(params) {
|
|
|
53
53
|
quantity: 1,
|
|
54
54
|
catalogReference: {
|
|
55
55
|
catalogItemId: bookingId,
|
|
56
|
-
appId: BOOKING_APP_ID,
|
|
56
|
+
appId: appId ?? BOOKING_APP_ID,
|
|
57
57
|
},
|
|
58
58
|
},
|
|
59
59
|
],
|
|
@@ -36,6 +36,8 @@ export interface BookActionParams {
|
|
|
36
36
|
location: TimeSlotLocationType | null;
|
|
37
37
|
formSubmission: FormValues | null;
|
|
38
38
|
timezone?: string;
|
|
39
|
+
/** Optional app ID override for the catalog reference. Defaults to the bookings app ID. */
|
|
40
|
+
appId?: string;
|
|
39
41
|
}
|
|
40
42
|
/**
|
|
41
43
|
* Props passed to children of Book component
|
|
@@ -110,6 +110,8 @@ export interface BookingServiceConfig {
|
|
|
110
110
|
timezone?: string;
|
|
111
111
|
/** Optional initial form submission */
|
|
112
112
|
formSubmission?: FormValues | null;
|
|
113
|
+
/** Optional app ID override for the catalog reference. Defaults to the bookings app ID. */
|
|
114
|
+
appId?: string;
|
|
113
115
|
}
|
|
114
116
|
/**
|
|
115
117
|
* Implementation of BookingService
|
|
@@ -55,9 +55,13 @@ export type BookingFormServiceConfig = {
|
|
|
55
55
|
additionalMetadata?: Record<string, string | string[]>;
|
|
56
56
|
/** Optional list of service IDs to pass to FormService */
|
|
57
57
|
serviceIds?: string[];
|
|
58
|
+
/** Optional namespace override. Defaults to BOOKING_FORM_NAMESPACE. */
|
|
59
|
+
namespace?: string;
|
|
58
60
|
} | {
|
|
59
61
|
/** Pre-loaded form object (SSR/SSG) - must be from bookings namespace */
|
|
60
62
|
form: forms.Form;
|
|
63
|
+
/** Optional namespace override. Defaults to BOOKING_FORM_NAMESPACE. */
|
|
64
|
+
namespace?: string;
|
|
61
65
|
};
|
|
62
66
|
/**
|
|
63
67
|
* API interface for the BookingForm service.
|
|
@@ -53,15 +53,18 @@ export const BookingFormServiceDefinition = defineService('bookingForm');
|
|
|
53
53
|
// Validation Helpers
|
|
54
54
|
// ============================================================================
|
|
55
55
|
/**
|
|
56
|
-
* Validates that a form belongs to the
|
|
57
|
-
*
|
|
58
|
-
*
|
|
56
|
+
* Validates that a form belongs to the expected namespace.
|
|
57
|
+
* When a custom namespace is provided, validates against it; otherwise validates
|
|
58
|
+
* against BOOKING_FORM_NAMESPACE.
|
|
59
|
+
* @param form The form to validate
|
|
60
|
+
* @param expectedNamespace The expected namespace (defaults to BOOKING_FORM_NAMESPACE)
|
|
61
|
+
* @throws Error if the form namespace does not match the expected namespace
|
|
59
62
|
*/
|
|
60
|
-
function validateBookingFormNamespace(form) {
|
|
63
|
+
function validateBookingFormNamespace(form, expectedNamespace = BOOKING_FORM_NAMESPACE) {
|
|
61
64
|
const formNamespace = form.namespace;
|
|
62
|
-
if (formNamespace && formNamespace !==
|
|
65
|
+
if (formNamespace && formNamespace !== expectedNamespace) {
|
|
63
66
|
throw new Error(`BookingFormService: Invalid form namespace. ` +
|
|
64
|
-
`Expected "${
|
|
67
|
+
`Expected "${expectedNamespace}", but received "${formNamespace}". ` +
|
|
65
68
|
`Ensure the form is a booking form.`);
|
|
66
69
|
}
|
|
67
70
|
}
|
|
@@ -70,7 +73,7 @@ function validateBookingFormConfig({ config, services, }) {
|
|
|
70
73
|
return;
|
|
71
74
|
}
|
|
72
75
|
if (hasForm(config)) {
|
|
73
|
-
validateBookingFormNamespace(config.form);
|
|
76
|
+
validateBookingFormNamespace(config.form, config.namespace);
|
|
74
77
|
const servicesFormId = services.length > 1 ? DEFAULT_FORM_ID : services?.[0]?.form?._id;
|
|
75
78
|
if (servicesFormId !== config.form._id) {
|
|
76
79
|
throw new Error(`BookingFormService: Invalid form ID. ` +
|
|
@@ -228,7 +231,7 @@ export const BookingFormService = implementService.withConfig()(BookingFormServi
|
|
|
228
231
|
? { form: config.form }
|
|
229
232
|
: {
|
|
230
233
|
formId: formIdValue,
|
|
231
|
-
namespace: BOOKING_FORM_NAMESPACE,
|
|
234
|
+
namespace: config?.namespace ?? BOOKING_FORM_NAMESPACE,
|
|
232
235
|
additionalMetadata: {
|
|
233
236
|
...config?.additionalMetadata,
|
|
234
237
|
serviceIds,
|
|
@@ -179,7 +179,7 @@ export const ServiceListService = implementService.withConfig()(ServiceListServi
|
|
|
179
179
|
// Use effectiveFilterSignal.peek() to get the computed filter value
|
|
180
180
|
const effectiveFilter = effectiveFilterSignal.peek();
|
|
181
181
|
isLoadingSignal.set(true);
|
|
182
|
-
Promise.
|
|
182
|
+
Promise.allSettled([
|
|
183
183
|
queryServices({
|
|
184
184
|
appId: initialQueryOptions.appId,
|
|
185
185
|
filter: effectiveFilter,
|
|
@@ -191,15 +191,21 @@ export const ServiceListService = implementService.withConfig()(ServiceListServi
|
|
|
191
191
|
}),
|
|
192
192
|
!hasInitialCategories ? queryCategories() : Promise.resolve(null),
|
|
193
193
|
])
|
|
194
|
-
.then(([
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
categoriesSignal.set(categoriesResult.categories);
|
|
194
|
+
.then(([servicesSettled, categoriesSettled]) => {
|
|
195
|
+
if (servicesSettled.status === 'fulfilled') {
|
|
196
|
+
servicesSignal.set(servicesSettled.value.services);
|
|
197
|
+
pagingMetadataSignal.set(servicesSettled.value.pagingMetadata);
|
|
199
198
|
}
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
199
|
+
else {
|
|
200
|
+
errorSignal.set(servicesSettled.reason instanceof Error
|
|
201
|
+
? servicesSettled.reason.message
|
|
202
|
+
: 'Unknown error');
|
|
203
|
+
}
|
|
204
|
+
if (categoriesSettled.status === 'fulfilled' &&
|
|
205
|
+
categoriesSettled.value) {
|
|
206
|
+
categoriesSignal.set(categoriesSettled.value.categories);
|
|
207
|
+
}
|
|
208
|
+
// If categories fail, silently keep empty categories — filter won't be shown
|
|
203
209
|
})
|
|
204
210
|
.finally(() => {
|
|
205
211
|
isLoadingSignal.set(false);
|
|
@@ -375,7 +381,7 @@ export const ServiceListService = implementService.withConfig()(ServiceListServi
|
|
|
375
381
|
*/
|
|
376
382
|
export async function loadServiceListServiceInitialData(options) {
|
|
377
383
|
try {
|
|
378
|
-
// Fetch services and categories in parallel
|
|
384
|
+
// Fetch services and categories in parallel; categories failure is non-fatal
|
|
379
385
|
const [servicesResult, categoriesResult] = await Promise.all([
|
|
380
386
|
queryServices({
|
|
381
387
|
appId: options.appId,
|
|
@@ -383,13 +389,13 @@ export async function loadServiceListServiceInitialData(options) {
|
|
|
383
389
|
pagingMetadata: options.pagingMetadata,
|
|
384
390
|
sort: options.sort,
|
|
385
391
|
}),
|
|
386
|
-
queryCategories(),
|
|
392
|
+
queryCategories().catch(() => null),
|
|
387
393
|
]);
|
|
388
394
|
return {
|
|
389
395
|
type: 'success',
|
|
390
396
|
config: {
|
|
391
397
|
services: servicesResult.services,
|
|
392
|
-
categories: categoriesResult
|
|
398
|
+
categories: categoriesResult?.categories ?? [],
|
|
393
399
|
options: {
|
|
394
400
|
...options,
|
|
395
401
|
pagingMetadata: servicesResult.pagingMetadata,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@wix/headless-bookings",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.117",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"scripts": {
|
|
@@ -73,5 +73,5 @@
|
|
|
73
73
|
"groupId": "com.wixpress.headless-components"
|
|
74
74
|
}
|
|
75
75
|
},
|
|
76
|
-
"falconPackageHash": "
|
|
76
|
+
"falconPackageHash": "f3af7c27f3ef8bd8bdc06d522c39551763e5bf65fd9fe6891ba25425"
|
|
77
77
|
}
|