升级到 Umi4 后,有同事和我反映,之前的一些组件不能用了,获取不到 props ,props 是空对象。
Umi4 在代码层做了修改,将 react-router@5 升级到 react-router@6,所以路由相关的一些 api 存在着使用上的差异。
props 默认为空对象,以下属性都不能直接从 props 中取出:
![]()
需要采用下面的方式:
children
import { Outlet } from 'umi';
<Outlet />;主要在全局 layout 中需要修改:
如 layouts/index.tsx:
import React from 'react';
+ import { Outlet } from 'umi';
export default function Layout(props) {
return (
<div>
- { props.children }
+ <Outlet />
</div>
);
}使用了 React.cloneElement 方式渲染的路由组件改造,示例
import React from 'react';
+ import { Outlet } from 'umi';
export default function RouteComponent(props) {
return (
<div>
- { React.cloneElement(props.children, { someProp: 'p1' }) }
+ <Outlet context={{ someProp: 'p1' }} />
</div>
);
}组件改成从 useOutletContext 取值
import React from 'react';
+ import { useOutletContext } from 'umi';
- export function Comp(props){
+ export function Comp() {
+ const props = useOutletContext();
return props.someProp;
}history
+ import { history } from 'umi';
export default function Page(props) {
return (
<div onClick={()=>{
- props.history.push('list');
+ history.push('list');
}}>
</div>
);
}location
建议组件或 hooks 里用 useLocation 取,其他地方就用 window.location 获取。
export default function Page(props) {
+ const { location } = window;
return (
<div>
- { props.location }
+ { location }
</div>
);
}或者
+ import { useLocation } from 'umi';
export default function Page(props) {
+ let location = useLocation();
return (
<div>
- { props.location }
+ { location }
</div>
);
}match
+ import { useMatch } from 'umi';
export default function Page(props) {
+ const match = useMatch({ path: 'list/search/:type' });
return (
<div>
- { props.match }
+ { match }
</div>
);
}需要注意 match 数据的差异:
// match v5
isExact: true
params: {}
path: "/users/abc"
url: "/users/abc"
// match v6
params:{ }
pathname: "/list/search/articles"
pathnameBase: "/list/search/articles"
pattern: {path: 'list/search/:type'}更多改动和 api 变更,可参考 react-router@6
未经允许不得转载:前端资源网 - w3h5 » Umi4获取不到props,默认为空对象
前端资源网 - w3h5