fix(core): Ensure resource sets an error (#58855)

Before this commit, a resource with a previous value wouldn't set the error state correctly.
This commit fixes this. A resource will set its status to error even when there was a previous valid value.

PR Close #58855
This commit is contained in:
Matthieu Riegler 2024-11-24 20:18:45 +01:00 committed by Jessica Janiuk
parent beec8969ee
commit 08b9452f01
2 changed files with 37 additions and 1 deletions

View file

@ -115,8 +115,9 @@ abstract class BaseWritableResource<T> implements WritableResource<T> {
* Put the resource into the error state.
*/
protected setErrorState(err: unknown): void {
this.status.set(ResourceStatus.Error);
this.value.set(undefined);
// The previous line will set the status to `Local`, so we need to update it.
this.status.set(ResourceStatus.Error);
this.error.set(err);
}

View file

@ -128,10 +128,45 @@ describe('resource', () => {
expect(echoResource.status()).toBe(ResourceStatus.Error);
expect(echoResource.isLoading()).toBeFalse();
expect(echoResource.hasValue()).toBeFalse();
expect(echoResource.value()).toEqual(undefined);
expect(echoResource.error()).toBe('Something went wrong....');
});
it('should expose errors on reload', async () => {
const backend = new MockEchoBackend();
const counter = signal(0);
const echoResource = resource({
request: () => ({counter: counter()}),
loader: (params) => {
if (params.request.counter % 2 === 0) {
return Promise.resolve('ok');
} else {
throw new Error('KO');
}
},
injector: TestBed.inject(Injector),
});
TestBed.flushEffects();
await backend.flush();
expect(echoResource.status()).toBe(ResourceStatus.Resolved);
expect(echoResource.isLoading()).toBeFalse();
expect(echoResource.hasValue()).toBeTrue();
expect(echoResource.value()).toEqual('ok');
expect(echoResource.error()).toBe(undefined);
counter.update((value) => value + 1);
TestBed.flushEffects();
expect(echoResource.status()).toBe(ResourceStatus.Error);
expect(echoResource.isLoading()).toBeFalse();
expect(echoResource.hasValue()).toBeFalse();
expect(echoResource.value()).toEqual(undefined);
expect(echoResource.error()).toEqual(Error('KO'));
});
it('should _not_ load if the request resolves to undefined', () => {
const counter = signal(0);
const backend = new MockEchoBackend();