withRouter' 不是从 'react-router-dom 导出的



在npm i——save react-router-dom和npm install——save with-router之后,我试着写

import {withRouter} from 'react-router';

但是我得到这个错误试图导入错误:' withouter '没有从'react-router'导出。


import React from 'react';
import PropTypes from 'prop-types';
import { Formik } from 'formik';
import {
Box,
Button,
Card,
CardContent,
CardHeader,
Divider,
} from '@material-ui/core';
import { connect } from 'react-redux';
import jsonGR from "src/assets/data/greek.json";
import jsonEN from "src/assets/data/english.json";
import { LAN_EN }  from 'src/actions/types';
import CloudUploadIcon from '@material-ui/icons/CloudUpload';
import AddIcon from '@material-ui/icons/Add';
import axios from 'axios';
import LinearProgress from '@material-ui/core/LinearProgress';
import Typography from '@material-ui/core/Typography';
import { withRouter } from 'react-router'
class ProfileDetails extends React.Component {
//code
}
};
ProfileDetails.propTypes = {
className: PropTypes.string
};
const mapStateToProps = state => {
return { loginsession: state.loginsession,
selectedlan: state.selectedlan };
};
export default withRouter(ProfileDetails);

文件包。它包含了我让npm安装到项目中的依赖项和所有必要的信息。我不知道问题出在哪里,我试了很多方法,但都不起作用

{
"name": "react-material-dashboard",
"author": "Apanay22",
"licence": "MIT",
"version": "1.0.0",
"private": false,
"scripts": {
"start": "react-scripts start http-server ",
"build": "react-scripts build",
"test": "react-scripts test",
"eject": "react-scripts eject"
},
"eslintConfig": {
"extends": "react-app"
},
"browserslist": {
"production": [
">0.2%",
"not dead",
"not op_mini all"
],
"development": [
"last 1 chrome version",
"last 1 firefox version",
"last 1 safari version"
]
},
"dependencies": {
"@material-ui/core": "^4.11.0",
"@material-ui/icons": "^4.9.1",
"@material-ui/lab": "^4.0.0-alpha.56",
"@material-ui/styles": "^4.10.0",
"axios": "^0.21.1",
"bcrypt": "^5.0.0",
"chart.js": "^2.9.3",
"clsx": "^1.1.1",
"compress.js": "^1.1.2",
"cors": "^2.8.5",
"csv-parse": "^4.15.1",
"express": "^4.17.1",
"formik": "^2.1.5",
"glob": "^7.1.6",
"gulp": "^4.0.2",
"history": "^5.0.0",
"lodash": "^4.17.19",
"material-ui-popup-state": "^1.7.1",
"moment": "^2.27.0",
"mui-datatables": "^3.7.6",
"nprogress": "^0.2.0",
"papaparse": "^5.3.0",
"prop-types": "^15.7.2",
"react": "^16.13.1",
"react-chartjs-2": "^2.10.0",
"react-csv-reader": "^3.2.1",
"react-dom": "^16.13.1",
"react-feather": "^2.0.8",
"react-helmet": "^6.1.0",
"react-hot-toast": "^1.0.2",
"react-image-file-resizer": "^0.4.2",
"react-navigation": "^4.4.4",
"react-perfect-scrollbar": "^1.5.8",
"react-redux": "^7.2.2",
"react-router": "^6.0.0-beta.0",
"react-router-dom": "^6.0.0-beta.0",
"react-scripts": "^3.4.1",
"react-toast-notifications": "^2.4.0",
"react-toastify": "^7.0.2",
"redux": "^4.0.5",
"redux-thunk": "^2.3.0",
"use-history": "^1.4.1",
"uuid": "^8.3.0",
"with-router": "^1.0.1",
"yup": "^0.29.3"
},
"devDependencies": {
"@types/react-router-dom": "^5.1.7",
"concurrently": "^5.3.0",
"eslint": "^6.8.0",
"eslint-config-airbnb": "^18.2.0",
"eslint-config-prettier": "^6.11.0",
"eslint-plugin-import": "^2.22.0",
"eslint-plugin-jsx-a11y": "^6.3.1",
"eslint-plugin-prettier": "^3.1.4",
"eslint-plugin-react": "^7.20.3",
"eslint-plugin-react-hooks": "^2.5.1",
"prettier": "^1.19.1"
},
"proxy": "http://localhost:9000"
}

我也有同样的问题。我通过将react-routerreact-router-dom降级到5.2.0版本来修复它。

只运行npm install react-router-dom@5.2.0npm install react-router@5.2.0。这将解决withRouter()的问题。

//你可以导入这个和这个函数

import {
useLocation,
useNavigate,
useParams
} from "react-router-dom";

function withRouter(Component) {
function ComponentWithRouterProp(props) {
let location = useLocation();
let navigate = useNavigate();
let params = useParams();
return (
<Component
{...props}
router={{ location, navigate, params }}
/>
);
}

return ComponentWithRouterProp;
}

从FAQ页面,你需要有React 16.8+才能使用钩子。我在17.0.2,似乎工作良好:

https://reactrouter.com/en/main/start/faq

import {
useLocation,
useNavigate,
useParams
} from "react-router-dom";
function withRouter(Component) {
function ComponentWithRouterProp(props) {
let location = useLocation();
let navigate = useNavigate();
let params = useParams();
return (
<Component
{...props}
router={{ location, navigate, params }}
/>
);
}
return ComponentWithRouterProp;
}

既然withouter从react-router v6中删除了,你就可以创建自己的函数了

import { useNavigate } from 'react-router';
export const withRouter = (Component) =>{
const Wrapper = (props) =>{
const history = useNavigate();
return <Component history={history} {...props}/>
} 
return Wrapper;
}

我看到你正在使用react-router-dom 6,它与版本5有很大的不同。你有两个选择,降级到版本5或尝试实现新版本这里是新的文档文档

对于那些更喜欢类组件而不是函数组件的人来说,react-route-dom v6的等效解决方案是:

import { useLocation } from "react-router-dom";
const withLocation = Component => props => {
const location = useLocation();

return <Component {...props} location={location} />;
};

export default withLocation( MyComponent)

同样适用于useNavigationuseParams

我当时没有在库中找到现成的包装器。

尝试安装旧版本,例如版本5。它在最新版本6上不起作用。我可以看到你在用这个

在我的情况下,当路由迁移到Reactv.18后发生变化时,React应用程序停止重新渲染

;现在我把react-router-dom留在v.5但是为了解决这个问题,在Route:

中移动了React Strict模式
<HashRouter>
<React.StrictMode>
<App />
</React.StrictMode>
</HashRouter>` 

使用react-router 6,删除withRouter

你可以按照官方网站的指南去做。

创建自己的文件" without .js">

假设你可以实际使用钩子(你在React 16.8+),你只需要一个包装器

import {
useLocation,
useNavigate,
useParams,
} from "react-router-dom";
function withRouter(Component) {
function ComponentWithRouterProp(props) {
let location = useLocation();
let navigate = useNavigate();
let params = useParams();
return (
<Component
{...props}
router={{ location, navigate, params }}
/>
);
}
return ComponentWithRouterProp;
}

如果您需要使用参数来获取数据,在ClassComponent中编写逻辑并根据它们呈现组件,那么为ClassComponentContainer创建包装器

import { useLocation, useParams } from 'react-router-dom';
import ClassComponentContainer from './ClassComponentContainer';
export default function ClassComponentWrap(props) {
const location = useLocation();
const params = useParams();
return <ClassComponentContainer location={location} params={params} />
}

之后使用ClassComponent中的params它在props

import React from 'react';
import { connect } from 'react-redux';
import axios from 'axios';
import PresentationComponent from './PresentationComponent';
class ClassComponent extends React.Component {
componentDidMount() {
let postID = this.props.params.postID;
axios.get(`https://jsonplaceholder.typicode.com/posts/${postID}`)
.then((response) => {console.log(response)})
}
render() {
return <PresentationComponent {...this.props} />
}
}
const mapStateToProps = (state) => {...}
const mapDispatchToProps = (dispatch) => {...}
const ClassComponentContainer = connect(mapStateToProps, mapDispatchToProps)(ClassComponent);
export default ClassComponentContainer;

并在Route元素属性

中使用ClassComponentWrap组件
import { BrowserRouter, Route, Routes } from "react-router-dom";
import ClassComponentWrap from './components/ClassComponentWrap';
export default function App(props) {
return (
<BrowserRouter>
<Routes>
<Route path="/posts/:postID?" element={<ClassComponentWrap />} />
</Routes>
</BrowserRouter>
);
}

除了这个问题

如果你想获得HTTP路由器传递的参数

使用useParams()代替(withouter and match.params.id)获取HTTP参数

import {useParams} from "react-router-dom";
const Student = (props) => {

return (
<>
<h1>Student Component: {useParams().id}</h1>
</>
)           
}
export default Student;

如果你想访问状态,可以尝试从react-redux使用useSelector

const  isAuthenticated = useSelector((state) => isAuthenticated(state));
import {withRouter} from 'react-router-dom';

相关内容

  • 没有找到相关文章

最新更新