Stateless component React router

故事扮演 提交于 2019-12-23 09:57:57

问题


I am new to React and Redux, I am actually creating a code of myself but I got stuck with a router kind of thing inside stateless component.

So, Actually I need to route to a component by using this.props.history.push('/somepath'). This is not happening inside a stateless component.

My Stateless component is

import React from "react"; // eslint-disable-line no-unused-vars
import "bootstrap/dist/css/bootstrap.min.css";
import "./header.css";

const Header = () => ({

    handleAuthor() {
        this.props.history('/somepath')// this is not working
    },

    render(){
        return (
            <div className = "header">
                <h1 onClick = {this.handleAuthor.bind(this)}>{this.props.headerText}</h1>
            </div>
        );
    } 
});

export default Header;

I am calling this inside another stateless component like mainlayout

import React from "react"; // eslint-disable-line no-unused-vars
import Header from "../header/Header"; // eslint-disable-line no-unused-vars
import Footer from "../footer/Footer"; // eslint-disable-line no-unused-vars
import "./mainLayout.css";

const MainLayout = props => ({
    render() {
        return (
            <div className="App">
                <Header headerText = "RK Boilerplate"/>
                <div className = "mainLayout">
                    <main>{props.children}</main>
                </div>
                <Footer />
            </div>
        );
    }
});

export default MainLayout;

My main file index.js looks like this

import React from "react"; // eslint-disable-line no-unused-vars
import ReactDOM from "react-dom"; // eslint-disable-line no-unused-vars
import { matchRoutes, renderRoutes } from "react-router-config"; // eslint-disable-line no-unused-vars
import { Router } from "react-router-dom"; // eslint-disable-line no-unused-vars
import { Switch } from "react-router"; // eslint-disable-line no-unused-vars
import { Provider } from "react-redux"; // eslint-disable-line no-unused-vars
import store from "./store"; // eslint-disable-line no-unused-vars
import routes from "./routes"; // eslint-disable-line no-unused-vars
import MainLayout from "./components/mainLayout/MainLayout"; // eslint-disable-line no-unused-vars

import createHistory from "history/createBrowserHistory";
let history = createHistory();
const App =  document.getElementById("app");

export default App;

ReactDOM.render(
    <Provider store={store}>
        <MainLayout>
            <Router history= {history}>
                <Switch>
                    {renderRoutes(routes)}
                </Switch>
            </Router>
        </MainLayout>                 
    </Provider>, 
    App);

SO what i need is I have to route from the header to another component where this component and path is given in a router file

router.js

import Home from "../containers/Home";
import About from "../containers/About";
import CreateUser from "../containers/CreateUser";

import Layout from "../containers/Layout";

const routes = [
    { path: "/",
        exact: true,
        component: Layout
    },
    { path: "/home",
        exact: true,
        component: Home
    },
    {
        path:"/About",
        exact: true,
        component: About
    },
    {
        path:"/createUser",
        exact: true,
        component: CreateUser
    }
];

export default routes;

I got an error like push of undefined , when i tried to route from header. Am I missing something is there any change that i should do here.

Thanks in advance.


回答1:


You can directly import the history object and push from that. For example try below code.

import React from "react"; // eslint-disable-line no-unused-vars
import "bootstrap/dist/css/bootstrap.min.css";
import "./header.css";
import history from "/your/history/path" //try this

const Header = () => ({

    handleAuthor() {
        history.push('/somepath')// change to this
    },

    render(){
        return (
            <div className = "header">
                <h1 onClick = {this.handleAuthor.bind(this)}>{this.props.headerText}</h1>
            </div>
        );
    } 
});

export default Header;

Create browser history like below and use it every where by importing.

import createBrowserHistory from 'history/createBrowserHistory';

export default createBrowserHistory({});



回答2:


In 2019, React Router v4 has now added the useHistory hook for stateless / functional components:

https://reacttraining.com/react-router/web/api/Hooks/usehistory

From the docs:

import { useHistory } from "react-router-dom";

function HomeButton() {
  let history = useHistory();

  function handleClick() {
    history.push("/home");
  }

  return (
    <button type="button" onClick={handleClick}>
      Go home
    </button>
  );
}



回答3:


Hope this doesn't come in too late. I successfully could redirect from a stateful component but I wanted to convert my component to a stateless component since the only thing that made it stateful was the redirect bit. I'm fairly new to react and most of the resources out there were not as clear. This is how I went about it.

import React from "react"; // eslint-disable-line no-unused-vars
import "bootstrap/dist/css/bootstrap.min.css";
import "./header.css";

const Header = (props) => {
    return (
        <div className = "header">
            <h1 onClick = {props.history.push('/some-path')}>{props.headerText}</h1>
        </div>
    );
} 

export default Header;



回答4:


It worked for me by using withRouter, (plus ignoring typescript warning):

import { withRouter } from 'react-router-dom';

...

type Props = { myProp: boolean };

// @ts-ignore
export const MyComponent: FC<Props> = withRouter(({ myProp, history }) => {

...

})


来源:https://stackoverflow.com/questions/50895607/stateless-component-react-router

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!