fix(core): expose catched editor load error (#5133)

This commit is contained in:
Joooye_34
2023-11-29 20:31:35 +08:00
committed by GitHub
parent 908c4e1a6f
commit a226eb8d5f
3 changed files with 21 additions and 30 deletions
@@ -96,11 +96,18 @@ export class NoPageRootError extends Error {
} }
} }
/**
* TODO: Defined async cache to support suspense, instead of reflect symbol to provider persistent error cache.
*/
const PAGE_LOAD_KEY = Symbol('PAGE_LOAD');
const PAGE_ROOT_KEY = Symbol('PAGE_ROOT'); const PAGE_ROOT_KEY = Symbol('PAGE_ROOT');
function usePageRoot(page: Page) { function usePageRoot(page: Page) {
if (!page.loaded) { let load$ = Reflect.get(page, PAGE_LOAD_KEY);
use(page.load()); if (!load$) {
load$ = page.load();
Reflect.set(page, PAGE_LOAD_KEY, load$);
} }
use(load$);
if (!page.root) { if (!page.root) {
let root$: Promise<void> | undefined = Reflect.get(page, PAGE_ROOT_KEY); let root$: Promise<void> | undefined = Reflect.get(page, PAGE_ROOT_KEY);
@@ -1,17 +1,25 @@
import { useAFFiNEI18N } from '@affine/i18n/hooks'; import { useAFFiNEI18N } from '@affine/i18n/hooks';
import type { FC } from 'react'; import { type FC, useCallback } from 'react';
import { ErrorDetail } from '../error-basic/error-detail'; import { ErrorDetail } from '../error-basic/error-detail';
import type { FallbackProps } from '../error-basic/fallback-creator'; import type { FallbackProps } from '../error-basic/fallback-creator';
/**
* TODO: Support reload and retry two reset actions in page error and area error.
*/
export const AnyErrorFallback: FC<FallbackProps> = props => { export const AnyErrorFallback: FC<FallbackProps> = props => {
const { error, resetError } = props; const { error } = props;
const t = useAFFiNEI18N(); const t = useAFFiNEI18N();
const reloadPage = useCallback(() => {
document.location.reload();
}, []);
return ( return (
<ErrorDetail <ErrorDetail
title={t['com.affine.error.unexpected-error.title']()} title={t['com.affine.error.unexpected-error.title']()}
resetError={resetError} resetError={reloadPage}
buttonText={t['com.affine.error.reload']()}
description={error.message ?? error.toString()} description={error.message ?? error.toString()}
/> />
); );
@@ -110,7 +110,6 @@ export const DetailPage = (): ReactElement => {
const currentSyncEngineStatus = useCurrentSyncEngineStatus(); const currentSyncEngineStatus = useCurrentSyncEngineStatus();
const currentPageId = useAtomValue(currentPageIdAtom); const currentPageId = useAtomValue(currentPageIdAtom);
const [page, setPage] = useState<Page | null>(null); const [page, setPage] = useState<Page | null>(null);
const [pageLoaded, setPageLoaded] = useState<boolean>(false);
// load page by current page id // load page by current page id
useEffect(() => { useEffect(() => {
@@ -155,30 +154,7 @@ export const DetailPage = (): ReactElement => {
return; return;
}, [currentSyncEngineStatus, navigate, page]); }, [currentSyncEngineStatus, navigate, page]);
// wait for page to be loaded if (!currentPageId || !page) {
useEffect(() => {
if (page) {
if (!page.isEmpty) {
setPageLoaded(true);
} else {
setPageLoaded(false);
// call waitForLoaded to trigger load
page
.load(() => {})
.catch(() => {
// do nothing
});
return page.slots.ready.on(() => {
setPageLoaded(true);
}).dispose;
}
} else {
setPageLoaded(false);
}
return;
}, [page]);
if (!currentPageId || !page || !pageLoaded) {
return <PageDetailSkeleton key="current-page-is-null" />; return <PageDetailSkeleton key="current-page-is-null" />;
} }