Storybook中使用react-router-dom的Link组件报错:无法解构null的basename属性
解决Storybook中StyledLink组件的Context报错问题
问题原因
StyledLink基于react-router-dom的Link封装,而Link依赖react-router提供的Router上下文。在Storybook环境中单独渲染该组件时,没有像主应用那样用BrowserRouter(或其他Router组件)包裹,导致上下文为null,触发解构basename的错误。
解决方案
1. 在单个Story中包裹Router组件
直接在StyledLink的Story代码里,用BrowserRouter或MemoryRouter(更适合测试场景)包裹组件:
import { BrowserRouter } from 'react-router-dom'; import StyledLink from './StyledLink'; export default { title: 'Components/StyledLink', component: StyledLink, decorators: [ (Story) => ( <BrowserRouter> <Story /> </BrowserRouter> ), ], }; export const Default = () => <StyledLink to="/">Home</StyledLink>;
2. 全局添加Router装饰器(推荐)
如果多个组件都依赖router上下文,可在.storybook/preview.js中添加全局装饰器,避免每个Story重复编写包裹逻辑:
import { BrowserRouter } from 'react-router-dom'; export const decorators = [ (Story) => ( <BrowserRouter> <Story /> </BrowserRouter> ), ];
3. 为StyledLink添加降级处理(可选)
如果希望组件在无Router上下文时也能正常渲染,可以给StyledLink添加兜底逻辑,降级为普通a标签:
import { Link } from 'react-router-dom'; import styled from 'styled-components'; import { useContext } from 'react'; import { RouterContext } from 'react-router-dom'; const StyledLinkElement = styled(Link)` /* 你的自定义样式 */ `; const StyledLink = ({ to, children, ...props }) => { const routerContext = useContext(RouterContext); if (!routerContext) { return <a href={to} {...props}>{children}</a>; } return <StyledLinkElement to={to} {...props}>{children}</StyledLinkElement>; }; export default StyledLink;
内容的提问来源于stack exchange,提问作者Marcos Eduardo Santos Henke
相关产品推荐
相关产品推荐

