Skip to content

Commit

Permalink
Move plan request builder to its own file and add tests
Browse files Browse the repository at this point in the history
  • Loading branch information
fbeaudoincoveo committed Feb 27, 2025
1 parent d91729d commit 46d70ce
Show file tree
Hide file tree
Showing 4 changed files with 151 additions and 27 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
import {QuerySuggestRequest} from '../../../api/commerce/search/query-suggest/query-suggest-request.js';
import {
defaultNodeJSNavigatorContextProvider,
NavigatorContext,
} from '../../../app/navigatorContextProvider.js';
import {buildMockBaseCommerceAPIRequest} from '../../../test/mock-commerce-api-request.js';
import {buildBaseCommerceAPIRequest} from '../common/base-commerce-api-request-builder.js';
import {getConfigurationInitialState} from '../configuration/configuration-state.js';
import {getCartInitialState} from '../context/cart/cart-state.js';
import {getContextInitialState} from '../context/context-state.js';
import {getCommerceQueryInitialState} from '../query/query-state.js';
import {
buildPlanRequest,
StateNeededForPlanCommerceAPIRequest,
} from './plan-request-builder.js';

vi.mock('../common/base-commerce-api-request-builder.js');

describe('#buildPlanRequest', () => {
let state: StateNeededForPlanCommerceAPIRequest;
let navigatorContext: NavigatorContext;
let request: QuerySuggestRequest;

const baseRequest = buildMockBaseCommerceAPIRequest();

const setState = (
configuration?: Partial<StateNeededForPlanCommerceAPIRequest>
) => {
state = {
configuration: getConfigurationInitialState(),
cart: getCartInitialState(),
commerceContext: getContextInitialState(),
commerceQuery: getCommerceQueryInitialState(),
...configuration,
};
};

const setNavigatorContext = (configuration?: Partial<NavigatorContext>) => {
navigatorContext = {
...defaultNodeJSNavigatorContextProvider(),
...configuration,
};
};
beforeEach(() => {
vi.resetAllMocks();
vi.mocked(buildBaseCommerceAPIRequest).mockReturnValue(baseRequest);
setState();
setNavigatorContext();
});

it('sets base properties, except #context.capture, to the value returned by #buildBaseCommerceAPIRequest(#state, #navigatorContext)', () => {
const {query, page, perPage, ...restOfPlanRequest} = buildPlanRequest(
state,
navigatorContext
);

const {capture: planRequestCapture, ...restOfPlanRequestContext} =
restOfPlanRequest.context;
const basePropertiesWithoutCapture = {
...restOfPlanRequest,
context: {...restOfPlanRequestContext},
};

const {capture: baseRequestCapture, ...restOfBaseRequestContext} =
baseRequest.context;
const baseRequestWithoutCapture = {
...baseRequest,
context: {...restOfBaseRequestContext},
};

expect(buildBaseCommerceAPIRequest).toHaveBeenCalledWith(
state,
navigatorContext
);
expect(basePropertiesWithoutCapture).toEqual(baseRequestWithoutCapture);
});

it('sets #context.capture to false', () => {
const {context} = buildPlanRequest(state, navigatorContext);

expect(context.capture).toBe(false);
});

it('sets #page to 0', () => {
const {page} = buildPlanRequest(state, navigatorContext);

expect(page).toBe(0);
});

it('sets #perPage to 1', () => {
const {perPage} = buildPlanRequest(state, navigatorContext);

expect(perPage).toBe(0);
});

it('sets #query to #state.commerceQuery.query', () => {
const query = 'some-query';
setState({
commerceQuery: {
query,
},
});
request = buildPlanRequest(state, navigatorContext);

expect(request.query).toBe(query);
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
import {
PageParam,
PerPageParam,
QueryParam,
} from '../../../api/commerce/commerce-api-params.js';
import {BaseCommerceAPIRequest} from '../../../api/commerce/common/request.js';
import {NavigatorContext} from '../../../app/navigatorContextProvider.js';
import {CommerceQuerySection} from '../../../state/state-sections.js';
import {
buildBaseCommerceAPIRequest,
StateNeededForBaseCommerceAPIRequest,
} from '../common/base-commerce-api-request-builder.js';

export type StateNeededForPlanCommerceAPIRequest =
StateNeededForBaseCommerceAPIRequest & CommerceQuerySection;

export type CommercePlanRequest = BaseCommerceAPIRequest &
QueryParam &
PageParam &
PerPageParam;

export const buildPlanRequest = (
state: StateNeededForPlanCommerceAPIRequest,
navigatorContext: NavigatorContext
): CommercePlanRequest => {
const baseRequest = buildBaseCommerceAPIRequest(state, navigatorContext);
return {
...baseRequest,
context: {
...baseRequest.context,
capture: false,
},
page: 0,
perPage: 1,
query: state.commerceQuery.query,
};
};
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,11 @@ import {AsyncThunkAction, PayloadAction} from '@reduxjs/toolkit';
import {AsyncThunkCommerceOptions} from '../../../api/commerce/commerce-api-client.js';
import {CommerceEngine} from '../../../app/commerce-engine/commerce-engine.js';
import {standaloneSearchBoxSetReducer as standaloneSearchBoxSet} from '../../standalone-search-box-set/standalone-search-box-set-slice.js';
import {StateNeededForPlanCommerceAPIRequest} from './plan-request-builder.js';
import {
FetchRedirectUrlPayload,
RegisterStandaloneSearchBoxPayload,
ResetStandaloneSearchBoxPayload,
StateNeededForRedirect,
fetchRedirectUrl,
registerStandaloneSearchBox,
resetStandaloneSearchBox,
Expand Down Expand Up @@ -37,7 +37,7 @@ export interface StandaloneSearchBoxSetActionCreators {
): AsyncThunkAction<
string,
FetchRedirectUrlPayload,
AsyncThunkCommerceOptions<StateNeededForRedirect>
AsyncThunkCommerceOptions<StateNeededForPlanCommerceAPIRequest>
>;

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,25 +4,15 @@ import {
AsyncThunkCommerceOptions,
isErrorResponse,
} from '../../../api/commerce/commerce-api-client.js';
import {CommerceSearchRequest} from '../../../api/commerce/search/request.js';
import {isRedirectTrigger} from '../../../api/common/trigger.js';
import {NavigatorContext} from '../../../app/navigatorContextProvider.js';
import {
CartSection,
CommerceContextSection,
CommerceQuerySection,
CommerceConfigurationSection,
} from '../../../state/state-sections.js';
import {
requiredNonEmptyString,
validatePayload,
} from '../../../utils/validate-payload.js';
import {buildPaginatedCommerceAPIRequest} from '../common/paginated-commerce-api-request-builder.js';

export type StateNeededForRedirect = CommerceConfigurationSection &
CommerceContextSection &
CommerceQuerySection &
CartSection;
import {
buildPlanRequest,
StateNeededForPlanCommerceAPIRequest,
} from './plan-request-builder.js';

export interface FetchRedirectUrlPayload {
/**
Expand All @@ -36,7 +26,7 @@ export interface FetchRedirectUrlPayload {
export const fetchRedirectUrl = createAsyncThunk<
string,
FetchRedirectUrlPayload,
AsyncThunkCommerceOptions<StateNeededForRedirect>
AsyncThunkCommerceOptions<StateNeededForPlanCommerceAPIRequest>
>(
'commerce/standaloneSearchBox/fetchRedirect',
async (
Expand Down Expand Up @@ -119,13 +109,3 @@ export const resetStandaloneSearchBox = createAction(
id: requiredNonEmptyString,
})
);

export const buildPlanRequest = (
state: StateNeededForRedirect,
navigatorContext: NavigatorContext
): CommerceSearchRequest => {
return {
query: state.commerceQuery.query,
...buildPaginatedCommerceAPIRequest(state, navigatorContext),
};
};

0 comments on commit 46d70ce

Please sign in to comment.