Javascript 盖茨比混合应用程序-在使用“createPage”中的模板构建的页面上存在子路由问题`
编辑: 我忘了提到我的网站包含了大约25k个用这个模板构建的页面。Derek Nguyen的答案适用于页面数量较少的小型网站,但如果按比例放大,则Javascript 盖茨比混合应用程序-在使用“createPage”中的模板构建的页面上存在子路由问题`,javascript,reactjs,routing,gatsby,reach-router,Javascript,Reactjs,Routing,Gatsby,Reach Router,编辑: 我忘了提到我的网站包含了大约25k个用这个模板构建的页面。Derek Nguyen的答案适用于页面数量较少的小型网站,但如果按比例放大,则matchPath数据将存储在JS中,从而导致庞大的捆绑包大小。(对我来说大约是3.1mb!) 挑战 我需要使用createPage创建一个页面,其中包含一个子路由系统,其中默认路由构建为静态HTML,但任何其他路由都是仅客户端路由 问题 我在createPage方法中有一个用于静态HTML生成的模板组件,但在pages/目录中也有一个用于为仅客户端路
matchPath
数据将存储在JS中,从而导致庞大的捆绑包大小。(对我来说大约是3.1mb!)
挑战
我需要使用createPage
创建一个页面,其中包含一个子路由系统,其中默认路由构建为静态HTML,但任何其他路由都是仅客户端路由
问题
我在createPage
方法中有一个用于静态HTML生成的模板组件,但在pages/
目录中也有一个用于为仅客户端路由分配匹配路径的组件
在最新版本的Gatsby上,模板组件呈现默认路由,但“页面”组件仅呈现客户端路由,导致在我只希望呈现子路由时重新呈现整页,因为父路由中存在需要持久化的数据
在我看来,用两个路由器连接两个组件是错误的,但我想不出任何其他方法来实现我想要实现的目标
以下是我的路由设置示例:
用于创建页面的模板
<Router>
<ContainerComponent
path={urlFromGraphQL}
>
<DefaultRoute
default
/>
</ContainerComponent>
</Router>
我也复制了这种行为。确保转到以查看正确的输出
我已经在github中创建了一个关于此问题的解决方案,但尚未得到答复。问题
看起来您混合了静态生成页面和动态页面,即在test.js
中匹配test/:param1/:param2
时,您都在/test/foo/bar
处生成页面
静态生成的页面比动态页面具有更高的特异性,因此盖茨比认为test/foo/bar
&test/foo/bar/second route
是两个不同的页面,而不是来自同一静态页面的两个动态路径
潜在解决方案
在这种情况下,您需要做的是为动态路由创建/test
和/test/foo/bar
根页面。这样,像/test/one/two
这样的随机匹配将是/test
的动态路径;而/test/foo/bar/second route
将是/test/foo/bar
的动态路径
由于您已经通过编程方式创建了/test/foo/bar
,因此将其作为动态页面的根目录并不重要:
//gatsby-node.js
exports.createPages=异步({actions})=>{
const{createPage}=actions
const pathFromGraphQL=“/test/foo/bar”
创建页面({
组件:path.resolve(`./src/templates/template.js`),
背景:{
url:pathFromGraphQL,
},
路径:pathFromGraphQL,
+匹配路径:`${pathFromGraphQL}/*`,
})
}
现在的问题是“template.js”不再完全是一个模板,它必须包含特定于test/foo/bar
的组件和路由。根据您的要求,这可能是一个表演的障碍,也可能是某种规避
我对你的叉子做了一点编辑来证明这一点;除了上面的代码更改之外,代码从pages/test.js
移动到templates/template.js
&我为pages/test.js
添加了一个虚拟组件,以表明它仍然可以处理其他动态路由:
此外,如果您决定这样做,请注意这一点。谢谢!我忘了提到,在我的例子中,我们根据这些模板生成了25k页。我在createPage
选项中直接提供了一个matchPath
,你说得对,它工作得很好。唯一的问题是,自gatsbyv2.9.0以来,包含matchPath
数据的数组被捆绑到JS中。这导致了一个巨大的JS包,用于有大量页面的站点。我最初创建了一个关于这一点,这导致了一个我目前已打开!哇,是的,这对你没有帮助:/我会关注这个问题,看看是否有其他解决方案
<Router>
<ContainerComponent
path="/some-route/:slug/:id"
>
<DefaultRoute
default
/>
<SecondTabRoute
path="second-tab-route"
/>
<ThirdTabRoute
path="third-tab-route"
/>
</ContainerComponent>
</Router>