Next.js Link跳转仅URL变更 未渲染对应目标页面问题
Next.js + Chakra UI 路由跳转URL更新但页面不渲染修复
问题场景
- 技术栈:Next.js Pages Router、Chakra UI
- 异常表现:点击
next/link生成的跳转链接后,浏览器地址栏URL正确变更为目标路径,但页面始终停留在当前页,不渲染目标路由内容 - 涉及核心代码:
原_app.js代码
import Layout, { ScrollBarStyle } from '../components/layouts/main' import theme from '../lib/theme.js' import Font from '../components/fonts' const Website = ({ Component, pageProps, router}) => { const getLayout = Component.getLayout return getLayout ? ( getLayout( <ChakraProvider theme = {theme}> <Font/> <ScrollBarStyle/> <Component {...pageProps} /> </ChakraProvider>) ) : ( <ChakraProvider theme = {theme}> <Font/> <ScrollBarStyle/> <Layout router={router}> <Component {...pageProps} /> </Layout> </ChakraProvider> ) } export default Website
原跳转代码
<NextLink href = '/marketplace' passHref as = '/marketplace'> <a> <SiMarketo color = 'lightgrey' size = "27px"/> </a> </NextLink>
问题根因
- 代码中使用了
ChakraProvider但未从@chakra-ui/react导入该组件,会导致Chakra上下文状态异常,阻断路由更新的渲染流程 - 自定义
getLayout布局逻辑未绑定路由维度的唯一标识,React在diff组件树时无法识别路由切换动作,直接复用当前页的组件实例,导致内容不更新 - 跳转代码中冗余声明了和
href取值一致的as属性,极端场景下会干扰Next.js路由匹配逻辑
修复步骤
- 在
_app.js顶部补全缺失的ChakraProvider导入:
import { ChakraProvider } from '@chakra-ui/react'
- 给两个渲染分支的最外层
ChakraProvider绑定key={router.asPath},强制路由变化时重新挂载组件树,修复后的完整_app.js代码如下:
import { ChakraProvider } from '@chakra-ui/react' import Layout, { ScrollBarStyle } from '../components/layouts/main' import theme from '../lib/theme.js' import Font from '../components/fonts' const Website = ({ Component, pageProps, router}) => { const getLayout = Component.getLayout return getLayout ? ( getLayout( <ChakraProvider key={router.asPath} theme={theme}> <Font/> <ScrollBarStyle/> <Component {...pageProps} /> </ChakraProvider> ) ) : ( <ChakraProvider key={router.asPath} theme={theme}> <Font/> <ScrollBarStyle/> <Layout router={router}> <Component {...pageProps} /> </Layout> </ChakraProvider> ) } export default Website
- 简化跳转代码,移除冗余的
as属性,注意确保NextLink是从next/link正确导入的:
import Link from 'next/link' // 其余业务导入省略 <Link href='/marketplace' passHref> <a> <SiMarketo color='lightgrey' size="27px"/> </a> </Link>
- 校验所有自定义
getLayout的页面,确保方法正确接收并渲染传入的page参数,错误写法会导致页面内容被吞,正确示例:
// pages/marketplace.js 示例 const Marketplace = () => { return <div>市场页内容</div> } // 自定义布局必须把传入的page参数渲染出来 Marketplace.getLayout = (page) => { return <div className="custom-market-layout">{page}</div> } export default Marketplace
校验提示:如果以上步骤操作完仍有异常,可以检查Layout组件是否正确透传children属性,未透传也会导致子页面内容无法渲染。
内容的提问来源于stack exchange,提问作者myself_rana.raj
相关产品推荐
相关产品推荐

