diff --git a/apps/website/docs/api/operators/apply_barrier.md b/apps/website/docs/api/operators/apply_barrier.md index 8335623d9..1a19c6744 100644 --- a/apps/website/docs/api/operators/apply_barrier.md +++ b/apps/website/docs/api/operators/apply_barrier.md @@ -4,28 +4,31 @@ Applies the [_Barrier_](/api/primitives/barrier) to the [_Query_](/api/primitive ## Formulae -### `applyBarrier(operation, { barrier })` +### `applyBarrier(operation, config)` ```ts import { applyBarrier } from '@farfetched/core'; -applyBarrier(operation, { barrier }); +applyBarrier(operation, config); ``` -#### Arguments +Operation could be a [_Query_](/api/primitives/query) or a [_Mutation_](/api/primitives/mutation) to apply the [_Barrier_](/api/primitives/barrier) to. -- `operation` - [_Query_](/api/primitives/query) or [_Mutation_](/api/primitives/mutation) to apply the [_Barrier_](/api/primitives/barrier) to -- `barrier` - [_Barrier_](/api/primitives/barrier) to apply +Config fields: -### `applyBarrier(operations, { barrier })` +- `barrier` - [_Barrier_](/api/primitives/barrier) to apply. +- `suppressIntermediateFailures?` - _boolean_ whether to suppress intermediate failures or not, defaults to `false`. If `true`, then the operation will be marked as failed after the first fail. + +### `applyBarrier(operations, config)` ```ts import { applyBarrier } from '@farfetched/core'; -applyBarrier([operation1, operation2], { barrier }); +applyBarrier([operation1, operation2], config); ``` -#### Arguments +Operations is an array of [_Queries_](/api/primitives/query) or [_Mutations_](/api/primitives/mutation) to apply the [_Barrier_](/api/primitives/barrier) to. + +Config fields: -- `operations` - Array of [_Queries_](/api/primitives/query) or [_Mutations_](/api/primitives/mutation) to apply the [_Barrier_](/api/primitives/barrier) to -- `barrier` - [_Barrier_](/api/primitives/barrier) to apply +- same as [previous formula](/api/operators/apply_barrier#applybarrier-operation-config). diff --git a/packages/core/src/barrier_api/__tests__/apply_barrier.test.ts b/packages/core/src/barrier_api/__tests__/apply_barrier.test.ts index cc0cc2bef..b2b986e5b 100644 --- a/packages/core/src/barrier_api/__tests__/apply_barrier.test.ts +++ b/packages/core/src/barrier_api/__tests__/apply_barrier.test.ts @@ -132,4 +132,49 @@ describe('applyBarrier', () => { expect(performer).toBeCalledTimes(1); }); + + test.concurrent( + 'suppress intermediate failure on operation fail', + async () => { + const defer = createDefer(); + + const renewTokenFx = createEffect(() => defer.promise); + + const authBarrier = createBarrier({ + activateOn: { failure: isHttpErrorCode(401) }, + perform: [renewTokenFx], + }); + + const query = createQuery({ + handler: vi + .fn() + .mockRejectedValueOnce( + httpError({ status: 401, statusText: 'Nooo', response: null }) + ) + .mockResolvedValueOnce('OK'), + }); + + applyBarrier(query, { + barrier: authBarrier, + suppressIntermediateFailures: true, + }); + + const scope = fork(); + + const { listeners } = watchRemoteOperation(query, scope); + + allSettled(query.refresh, { scope }); + await setTimeout(1); + expect(scope.getState(authBarrier.$active)).toBeTruthy(); + + defer.resolve(null); + await allSettled(scope); + expect(scope.getState(authBarrier.$active)).toBeFalsy(); + expect(listeners.onFailure).toBeCalledTimes(0); + expect(listeners.onSuccess).toBeCalledTimes(1); + expect(listeners.onSuccess).toBeCalledWith( + expect.objectContaining({ result: 'OK' }) + ); + } + ); }); diff --git a/packages/core/src/barrier_api/apply_barrier.ts b/packages/core/src/barrier_api/apply_barrier.ts index bccaf59b3..a226a0ca8 100644 --- a/packages/core/src/barrier_api/apply_barrier.ts +++ b/packages/core/src/barrier_api/apply_barrier.ts @@ -8,10 +8,14 @@ import { type Barrier } from './type'; * * @param operation Query or Mutation to apply Barrier to * @param config.barrier Barrier to apply + * @param config.suppressIntermediateFailures Whether to suppress intermediate failures or not, defaults to `false` */ export function applyBarrier( operation: RemoteOperation, - { barrier }: { barrier: Barrier } + { + barrier, + suppressIntermediateFailures, + }: { barrier: Barrier; suppressIntermediateFailures?: boolean } ): void; /** @@ -19,17 +23,24 @@ export function applyBarrier( * * @param operations Query or Mutation to apply Barrier to * @param config.barrier Barrier to apply + * @param config.suppressIntermediateFailures Whether to suppress intermediate failures or not, defaults to `false` */ export function applyBarrier( operations: RemoteOperation[], - { barrier }: { barrier: Barrier } + { + barrier, + suppressIntermediateFailures, + }: { barrier: Barrier; suppressIntermediateFailures?: boolean } ): void; export function applyBarrier( operation: | RemoteOperation | RemoteOperation[], - { barrier }: { barrier: Barrier } + { + barrier, + suppressIntermediateFailures = false, + }: { barrier: Barrier; suppressIntermediateFailures?: boolean } ): void { if (Array.isArray(operation)) { for (const op of operation) {