diff --git a/apps/web/src/hooks/use-load-public-workspace.ts b/apps/web/src/hooks/use-load-public-workspace.ts new file mode 100644 index 0000000000..2f5cf35fc8 --- /dev/null +++ b/apps/web/src/hooks/use-load-public-workspace.ts @@ -0,0 +1,35 @@ +import { getDataCenter, WorkspaceUnit } from '@affine/datacenter'; +import { useRouter } from 'next/router'; +import { useEffect, useState } from 'react'; + +export function useLoadPublicWorkspace(workspaceId: string) { + const router = useRouter(); + const [workspace, setWorkspace] = useState(); + const [status, setStatus] = useState<'loading' | 'error' | 'success'>( + 'loading' + ); + + useEffect(() => { + setStatus('loading'); + + const init = async () => { + const dataCenter = await getDataCenter(); + + dataCenter + .loadPublicWorkspace(workspaceId) + .then(data => { + setWorkspace(data); + setStatus('success'); + }) + .catch(() => { + // if (!cancel) { + // router.push('/404'); + // } + setStatus('error'); + }); + }; + init(); + }, [router, workspaceId]); + + return { status, workspace }; +} diff --git a/apps/web/src/hooks/use-public-workspace.ts b/apps/web/src/hooks/use-public-workspace.ts deleted file mode 100644 index 79cd5f3714..0000000000 --- a/apps/web/src/hooks/use-public-workspace.ts +++ /dev/null @@ -1,31 +0,0 @@ -import { useAppState } from '@/providers/app-state-provider'; -import { WorkspaceUnit } from '@affine/datacenter'; -import { useRouter } from 'next/router'; -import { useEffect, useState } from 'react'; - -export function usePublicWorkspace(workspaceId: string) { - const { dataCenter } = useAppState(); - const router = useRouter(); - const [workspace, setWorkspace] = useState(); - - useEffect(() => { - let cancel = false; - dataCenter - .loadPublicWorkspace(workspaceId) - .then(data => { - if (!cancel) { - setWorkspace(data); - } - }) - .catch(() => { - if (!cancel) { - router.push('/404'); - } - }); - return () => { - cancel = true; - }; - }, [router, workspaceId, dataCenter]); - - return workspace; -} diff --git a/apps/web/src/pages/_app.tsx b/apps/web/src/pages/_app.tsx index da52f88833..acf7f05ace 100644 --- a/apps/web/src/pages/_app.tsx +++ b/apps/web/src/pages/_app.tsx @@ -39,9 +39,16 @@ type AppPropsWithLayout = AppProps & { Component: NextPageWithLayout; }; +// Page list which do not rely on app state +const NoNeedAppStatePageList = [ + '/404', + '/public-workspace/[workspaceId]', + '/public-workspace/[workspaceId]/[pageId]', +]; const App = ({ Component, pageProps }: AppPropsWithLayout) => { const getLayout = Component.getLayout || (page => page); const { i18n } = useTranslation(); + const router = useRouter(); React.useEffect(() => { document.documentElement.lang = i18n.language; @@ -68,7 +75,11 @@ const App = ({ Component, pageProps }: AppPropsWithLayout) => { , ]} > - {getLayout()} + {NoNeedAppStatePageList.includes(router.route) ? ( + getLayout() + ) : ( + {getLayout()} + )} ); @@ -84,11 +95,6 @@ const AppDefender = ({ children }: PropsWithChildren) => { } }, [router]); - // if you visit /404, you will see the children directly - if (router.route === '/404') { - return
{children}
; - } - return
{synced ? children : }
; }; diff --git a/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx b/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx index 73127dddd1..355fab3e1e 100644 --- a/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx +++ b/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx @@ -10,7 +10,7 @@ import NextLink from 'next/link'; import { PaperIcon, SearchIcon } from '@blocksuite/icons'; import { WorkspaceUnitAvatar } from '@/components/workspace-avatar'; import { useModal } from '@/store/globalModal'; -import { usePublicWorkspace } from '@/hooks/use-public-workspace'; +import { useLoadPublicWorkspace } from '@/hooks/use-load-public-workspace'; import { useTranslation } from '@affine/i18n'; const DynamicBlocksuite = dynamic(() => import('@/components/editor'), { @@ -20,8 +20,9 @@ const DynamicBlocksuite = dynamic(() => import('@/components/editor'), { const Page: NextPageWithLayout = () => { const router = useRouter(); const { workspaceId, pageId } = router.query as Record; - const workspaceUnit = usePublicWorkspace(workspaceId); - const [loaded, setLoaded] = useState(false); + const { status, workspace: workspaceUnit } = + useLoadPublicWorkspace(workspaceId); + const [editorLoaded, setEditorLoaded] = useState(false); const { triggerQuickSearchModal } = useModal(); const { t } = useTranslation(); @@ -43,48 +44,58 @@ const Page: NextPageWithLayout = () => { } }, [workspace, router, pageId]); - return ( - <> - {!loaded && } - - - - - - {workspaceName} - - - - {pageTitle ? pageTitle : t('Untitled')} - - - { - triggerQuickSearchModal(); - }} - > - - - + useEffect(() => { + if (status === 'error') { + router.push('/404'); + } + }, [router, status]); - {workspace && page && ( - { - editor.readonly = true; - setLoaded(true); - }} - /> - )} - - + if (status === 'loading' || !editorLoaded) { + return ; + } + + if (status === 'error') { + return null; + } + return ( + + + + + + {workspaceName} + + + + {pageTitle ? pageTitle : t('Untitled')} + + + { + triggerQuickSearchModal(); + }} + > + + + + + {workspace && page && ( + { + editor.readonly = true; + setEditorLoaded(true); + }} + /> + )} + ); }; diff --git a/apps/web/src/pages/public-workspace/[workspaceId]/index.tsx b/apps/web/src/pages/public-workspace/[workspaceId]/index.tsx index 9691a9968b..f0e229adc4 100644 --- a/apps/web/src/pages/public-workspace/[workspaceId]/index.tsx +++ b/apps/web/src/pages/public-workspace/[workspaceId]/index.tsx @@ -1,30 +1,47 @@ import { PageList } from '@/components/page-list'; import { WorkspaceUnitAvatar } from '@/components/workspace-avatar'; -import { usePublicWorkspace } from '@/hooks/use-public-workspace'; +import { useLoadPublicWorkspace } from '@/hooks/use-load-public-workspace'; import { PageMeta } from '@/providers/app-state-provider'; import { useModal } from '@/store/globalModal'; import { Breadcrumbs } from '@affine/component'; import { SearchIcon } from '@blocksuite/icons'; import { useRouter } from 'next/router'; -import { ReactElement, useMemo } from 'react'; +import { ReactElement, useMemo, useEffect } from 'react'; import { NavContainer, PageContainer, SearchButton, StyledBreadcrumbs, } from './[pageId]'; +import { PageLoading } from '@/components/loading'; const All = () => { const router = useRouter(); const { triggerQuickSearchModal } = useModal(); - const workspaceUnit = usePublicWorkspace(router.query.workspaceId as string); + const { status, workspace } = useLoadPublicWorkspace( + router.query.workspaceId as string + ); const pageList = useMemo(() => { - return (workspaceUnit?.blocksuiteWorkspace?.meta.pageMetas ?? - []) as PageMeta[]; - }, [workspaceUnit]); + return (workspace?.blocksuiteWorkspace?.meta.pageMetas ?? []) as PageMeta[]; + }, [workspace]); + + const workspaceName = workspace?.blocksuiteWorkspace?.meta.name; + + useEffect(() => { + if (status === 'error') { + router.push('/404'); + } + }, [router, status]); + + if (status === 'loading') { + return ; + } + + if (status === 'error') { + return null; + } - const workspaceName = workspaceUnit?.blocksuiteWorkspace?.meta.name; return ( @@ -35,7 +52,7 @@ const All = () => { {workspaceName}