Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why `Failed to execute 'pushState' on 'History'` when using `Link` from react-router-dom?

I've seen similar posts but couldn't find an answer and in my case, I'm trying to pass an action from <App />:

  addExpense = (expense) => {
    console.log('Hello From AddExpenseForm');
  }

to /create route where I'm rendering <AddExpenseForm /> component

<Link to={{
  pathname: '/create',
  state: { addExpense: this.addExpense }
}}> Create Expense</Link>

The link is rendered but when I click on it I get an error in console:

Uncaught DOMException: Failed to execute 'pushState' on 'History': function (expense) {
      console.log('Hello From addExpense');
    } could not be cloned

Why is that and what's the workaround here?

My updated code:

Routes in Index.js:

const Routes = () => {
  return (
      <BrowserRouter>
        <Switch>
          <Route path="/" exact component={App} />
          <Route path="/create" exact component={AddExpenseForm}/>
          <Route path="/expense/:expenseId" name="routename" component={ExpenseDetails} />
          <Route component={NotFound} />
        </Switch>
      </BrowserRouter>
  )
}

App.js:

  addExpense = (expense = {}) => {
    console.log('Hello From AddExpenseForm');
  }

  goToNextPage = (addExpense) => {
    this.props.history.push({
      pathname: '/create',
      state: { addExpense: this.addExpense }
    });
  }

  render() {
    return (
      <div>
        <Header
        />
        <button onClick={this.goToNextPage}>Create</button>
        ...
like image 861
karolis2017 Avatar asked Oct 17 '17 22:10

karolis2017


People also ask

What is history PUSH IN react router?

history. push() is another approach where we make use of the history props React Router provides while rendering a component. In other words, this works when the component is being rendered by React Router, bypassing the component as a Component prop to a Route.

Why we use Browserrouter in react?

React Router is a standard library for routing in React. It enables the navigation among views of various components in a React Application, allows changing the browser URL, and keeps the UI in sync with the URL. Let us create a simple application to React to understand how the React Router works.

What does outlet do in react router dom?

The Layout component has <Outlet> and <Link> elements. The <Outlet> renders the current route selected. <Link> is used to set the URL and keep track of browsing history. Anytime we link to an internal path, we will use <Link> instead of <a href=""> .

What is indexroute in react router?

Index Route - A child route with no path that renders in the parent's outlet at the parent's URL. Layout Route - A parent route without a path, used exclusively for grouping child routes inside a specific layout.


2 Answers

In my case, it was caused by trying to route to a path with two "/" characters. I wrote this:

history.push(`${location.pathname}/somePath`);

... but if location.pathname is "/" that will try to go to "//somePath", causing the error,

like image 104
Nicholas Tower Avatar answered Sep 27 '22 20:09

Nicholas Tower


Firstly, add some default value to your addExpense function:

  addExpense = (expense = DEFAULT) => {
    console.log('Hello From addExpense');
  }

Then Use Link:

<Link to={`/ideas/${this.addExpense}`}>Create Expense​</Link>         

OR Try this (Better Approach):

  goToNextPage = (addExpense) => {
    this.props.history.push({
      pathname: '/create',
      state: { addExpense: addExpense }
    });
  }

In next (create) component use the passed on values like this:

this.props.location.state.addExpense();
like image 23
BlackBeard Avatar answered Sep 27 '22 20:09

BlackBeard