Skip to content

Commit

Permalink
fix: useLoader fallback (#516)
Browse files Browse the repository at this point in the history
* fix: useLoader fallback

* docs: changeset

Co-authored-by: Belinda Cao <[email protected]>
  • Loading branch information
2 people authored and targeral committed Jun 10, 2022
1 parent 78c569e commit ae5a9db
Show file tree
Hide file tree
Showing 4 changed files with 72 additions and 11 deletions.
5 changes: 5 additions & 0 deletions .changeset/famous-ways-matter.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@modern-js/runtime-core": patch
---

fix(runtime): useLoader fallback logic
8 changes: 2 additions & 6 deletions packages/runtime/src/compatible.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -123,15 +123,11 @@ export const bootstrap: BootStrap = async (
(res: any, key) => {
const loaderData = loadersData[key];

if (
loaderData.loading !== false ||
loaderData.error ||
typeof loaderData.data === 'undefined'
) {
if (loaderData.loading !== false) {
return res;
}

res[key] = loaderData.data;
res[key] = loaderData;
return res;
},
{},
Expand Down
13 changes: 8 additions & 5 deletions packages/runtime/src/loader/loaderManager.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ const createGetId = () => {
}

// WARNING: id should be unique after serialize.
// In some cases, such as 0/'0' would generate the same id.
const id = JSON.stringify(objectId);

invariant(id, 'params should be not null value');
Expand All @@ -42,14 +41,18 @@ export type LoaderResult = {

const createLoader = (
id: string,
initialData: any,
initialData: LoaderResult = {
loading: false,
reloading: false,
data: undefined,
error: undefined,
},
loaderFn: () => Promise<any>,
skip = false,
) => {
let promise: Promise<any> | null;
let status: LoaderStatus = LoaderStatus.idle;
let data: any = initialData;
let error: any;
let { data, error } = initialData;
let hasLoaded = false;

const handlers = new Set<
Expand Down Expand Up @@ -80,7 +83,7 @@ const createLoader = (
})
// eslint-disable-next-line promise/prefer-await-to-then
.catch(e => {
error = e;
error = e instanceof Error ? `${e.message}` : e;
data = null;
status = LoaderStatus.rejected;
notify();
Expand Down
57 changes: 57 additions & 0 deletions packages/runtime/tests/loaderManager.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
import { createLoaderManager } from '../src/loader/loaderManager';

describe('loaderManager', () => {
test('basic usage', async () => {
const initialData = {
loading: false,
reloading: false,
data: 'hello world',
error: null,
};

const loaderManager = createLoaderManager({
[JSON.stringify('1')]: initialData,
});

const { add, get, awaitPendingLoaders } = loaderManager;

add(() => Promise.resolve('hello modern'), { params: '1' });
add(() => Promise.resolve('hello modern2'), { params: '2', initialData });
add(() => Promise.reject(new Error('error occurs')), {
params: '3',
initialData,
});

const loader1 = get(JSON.stringify('1'));
const loader2 = get(JSON.stringify('2'));
const loader3 = get(JSON.stringify('3'));

expect(loader1?.result).toEqual(initialData);
expect(loader2?.result).toEqual(initialData);

loader1?.load();
loader2?.load();
loader3?.load();

const result = await awaitPendingLoaders();

expect(result[JSON.stringify('1')]).toEqual({
loading: false,
reloading: false,
data: 'hello modern',
error: null,
});
expect(result[JSON.stringify('2')]).toEqual({
loading: false,
reloading: false,
data: 'hello modern2',
error: null,
});
expect(result[JSON.stringify('3')]).toEqual({
loading: false,
reloading: false,
data: null,
error: 'error occurs',
});
});
});

0 comments on commit ae5a9db

Please sign in to comment.