Skip to content

Commit 3a44977

Browse files
Merge branch 'feature/1cc_merge' into dannyphan2000.W-21000338.bopis-auto-populate-blling-address
2 parents d36e3df + c292a78 commit 3a44977

File tree

2 files changed

+184
-1
lines changed

2 files changed

+184
-1
lines changed

packages/template-retail-react-app/app/pages/checkout-one-click/index.test.js

Lines changed: 183 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,38 @@ const WrappedCheckout = () => {
111111
}
112112

113113
describe('Checkout One Click', () => {
114+
// Helper to create a BOPIS-only basket (single pickup shipment, no delivery)
115+
const createBopisOnlyBasket = () => {
116+
const basket = JSON.parse(JSON.stringify(scapiBasketWithItem))
117+
basket.productItems = [
118+
{
119+
itemId: 'item-pickup-1',
120+
productId: '701643070725M',
121+
quantity: 1,
122+
price: 19.18,
123+
shipmentId: 'pickup1',
124+
inventoryId: 'inventory_m_store_store1'
125+
}
126+
]
127+
basket.shipments = [
128+
{
129+
shipmentId: 'pickup1',
130+
c_fromStoreId: 'store1',
131+
shippingMethod: {id: 'PICKUP', c_storePickupEnabled: true},
132+
shippingAddress: {
133+
firstName: 'Store 1',
134+
lastName: 'Pickup',
135+
address1: '1 Market St',
136+
city: 'San Francisco',
137+
postalCode: '94105',
138+
stateCode: 'CA',
139+
countryCode: 'US'
140+
}
141+
}
142+
]
143+
return basket
144+
}
145+
114146
// Set up and clean up
115147
beforeEach(() => {
116148
global.server.use(
@@ -356,6 +388,157 @@ describe('Checkout One Click', () => {
356388
})
357389
})
358390

391+
// BOPIS-only checkout tests
392+
describe('BOPIS-only checkout', () => {
393+
test('can checkout BOPIS-only order as guest shopper', async () => {
394+
// Mock authorizePasswordlessLogin to fail with 404 (unregistered user)
395+
mockUseAuthHelper.mockRejectedValueOnce({
396+
response: {status: 404}
397+
})
398+
399+
const bopisOnlyBasket = createBopisOnlyBasket()
400+
global.server.use(
401+
rest.get('*/baskets', (req, res, ctx) => {
402+
return res(
403+
ctx.json({
404+
baskets: [bopisOnlyBasket],
405+
total: 1
406+
})
407+
)
408+
})
409+
)
410+
411+
window.history.pushState({}, 'Checkout', createPathWithDefaults('/checkout'))
412+
const {user} = renderWithProviders(<WrappedCheckout history={history} />, {
413+
wrapperProps: {
414+
isGuest: true,
415+
siteAlias: 'uk',
416+
appConfig: mockConfig.app
417+
}
418+
})
419+
420+
// Wait for contact info step
421+
await screen.findByText(/contact info/i)
422+
423+
// Fill email and phone number
424+
const emailInput = await screen.findByLabelText(/email/i)
425+
await user.type(emailInput, 'bopisguest@test.com')
426+
await user.tab()
427+
const phoneInput = screen.queryByLabelText(/phone/i)
428+
if (phoneInput) {
429+
await user.type(phoneInput, '5551234567')
430+
}
431+
432+
// Wait for continue button and click
433+
const continueBtn = await screen.findByText(/continue to shipping address/i)
434+
await user.click(continueBtn)
435+
436+
// Verify we skip directly to payment
437+
await waitFor(
438+
() => {
439+
const paymentStep = screen.queryByTestId('sf-toggle-card-step-4')
440+
const paymentHeading = screen.queryByRole('heading', {name: /payment/i})
441+
expect(paymentStep || paymentHeading).toBeTruthy()
442+
},
443+
{timeout: 5000}
444+
)
445+
})
446+
447+
test('can checkout BOPIS-only order as registered shopper', async () => {
448+
const bopisOnlyBasket = createBopisOnlyBasket()
449+
global.server.use(
450+
rest.get('*/baskets', (req, res, ctx) => {
451+
return res(
452+
ctx.json({
453+
baskets: [bopisOnlyBasket],
454+
total: 1
455+
})
456+
)
457+
})
458+
)
459+
460+
window.history.pushState({}, 'Checkout', createPathWithDefaults('/checkout'))
461+
renderWithProviders(<WrappedCheckout history={history} />, {
462+
wrapperProps: {
463+
bypassAuth: true,
464+
isGuest: false,
465+
siteAlias: 'uk',
466+
locale: {id: 'en-GB'},
467+
appConfig: mockConfig.app
468+
}
469+
})
470+
471+
// Wait for checkout to load - registered user should have email displayed
472+
await waitFor(() => {
473+
expect(screen.getByText('customer@test.com')).toBeInTheDocument()
474+
})
475+
476+
// For BOPIS-only, we should see payment step
477+
await waitFor(
478+
() => {
479+
const paymentStep = screen.queryByTestId('sf-toggle-card-step-4')
480+
const paymentHeading = screen.queryByRole('heading', {name: /payment/i})
481+
expect(paymentStep || paymentHeading).toBeTruthy()
482+
},
483+
{timeout: 5000}
484+
)
485+
})
486+
487+
test('BOPIS-only guest shopper editing contact info continues to payment, not pickup address', async () => {
488+
mockUseAuthHelper.mockRejectedValueOnce({
489+
response: {status: 404}
490+
})
491+
492+
const bopisOnlyBasket = createBopisOnlyBasket()
493+
global.server.use(
494+
rest.get('*/baskets', (req, res, ctx) => {
495+
return res(
496+
ctx.json({
497+
baskets: [bopisOnlyBasket],
498+
total: 1
499+
})
500+
)
501+
})
502+
)
503+
504+
window.history.pushState({}, 'Checkout', createPathWithDefaults('/checkout'))
505+
const {user} = renderWithProviders(<WrappedCheckout history={history} />, {
506+
wrapperProps: {
507+
isGuest: true,
508+
siteAlias: 'uk',
509+
appConfig: mockConfig.app
510+
}
511+
})
512+
513+
// Wait for contact info step
514+
await screen.findByText(/contact info/i)
515+
516+
// Fill email and phone
517+
const emailInput = await screen.findByLabelText(/email/i)
518+
await user.type(emailInput, 'bopisguest@test.com')
519+
await user.tab()
520+
521+
const phoneInput = screen.queryByLabelText(/phone/i)
522+
if (phoneInput) {
523+
await user.type(phoneInput, '5551234567')
524+
}
525+
526+
// Wait for continue button and click
527+
const continueBtn = await screen.findByText(/continue to shipping address/i)
528+
await user.click(continueBtn)
529+
530+
// Verify we continue to payment
531+
await waitFor(
532+
() => {
533+
const paymentStep = screen.queryByTestId('sf-toggle-card-step-4')
534+
const paymentHeading = screen.queryByRole('heading', {name: /payment/i})
535+
expect(paymentStep || paymentHeading).toBeTruthy()
536+
},
537+
{timeout: 5000}
538+
)
539+
})
540+
})
541+
359542
afterEach(() => {
360543
jest.resetModules()
361544
jest.clearAllMocks()

packages/template-retail-react-app/app/pages/checkout-one-click/util/checkout-context.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,7 @@ export const CheckoutProvider = ({children}) => {
102102
)
103103
const hasDeliveryShipments = shipmentsWithItems.some((s) => !isPickupShipment(s))
104104
// Skip to appropriate next step; when mixed, go to SHIPPING_ADDRESS
105-
setStep(hasDeliveryShipments ? STEPS.SHIPPING_ADDRESS : STEPS.PICKUP_ADDRESS)
105+
setStep(hasDeliveryShipments ? STEPS.SHIPPING_ADDRESS : STEPS.PAYMENT)
106106
} else {
107107
setStep(step + 1)
108108
}

0 commit comments

Comments
 (0)