React onClick doesn't stop browser from setting anchor tag

Viewed 1658

I'm a React newbie and ran into a problem with paging controls using link tags. My basic paging control renders as something like this:

<a href="#page2">Next</a>

The JSX definition that renders it looks like this:

<a href={"#page"+(this.props.pageIndex+1)} onClick={this.handleClick}>
  {this.props.name}
</a>

The problem is that when you click on the Next link to go to Page 2, the browser ends up showing #page3 in the URL bar, even though the code properly renders page 2. (The code does nothing to modify the URL.) Tracing following the JavaScript in the debugger, I see that window.location.href stays at #page1, then jumps to #page3.

I believe what is happening is that React is intercepting the click event, and re-renders the page properly, then the browser's default link handling fires after the Next link has changed to point to #page3 instead of #page2.

Is my analysis correct? If so, what is the proper way to make this work so the browser shows #page2 in the URL bar?

EDIT: Here is the simplified code in context:

class RecordList extends React.Component {
  changePage(pageIndex) {
    console.log("change page selected: "+pageIndex);
    this.props.changePage(pageIndex);
    return false;
  }

  render() {
    ...
    nextLink = (<PagingLink name=" Next> "pageIndex={this.props.pageIndex+1} handleClick={() => 
    this.changePage(this.props.pageIndex+1)}/>)

    return (
      ...
      <div className="paging-control">
        <span>Page {this.props.pageIndex+1}</span>
          {nextLink}
        </div>
    );
  }  
}

class PagingLink extends React.Component {
  constructor(props) {
    super(props);
    this.handleClick = this.handleClick.bind(this);
  }
  handleClick() {
    this.props.handleClick(this.props.pageIndex)
  }
  render() {
    return (
        <span className="pageLink">
        <a href={"#page"+(this.props.pageIndex+1)} onClick={this.handleClick}>
          {this.props.name}
        </a>
        </span>
    );
  }
}

class App extends Component {
  constructor() {
    super();
    this.state = {
      pageSize: 20,
      pageIndex: 0,
      ...
    };
  }

  componentDidMount() {
    var pageIndex = this.state.pageIndex;
    if (window.location.hash.indexOf("#page") === 0) {
      pageIndex = Number(window.location.hash.substring(5))-1;
      this.setState((prevState) => {
          return { pageIndex: pageIndex };
        }, () => {
        this.fetchRecords(pageIndex);
      });
    }
    else {
      this.fetchRecords(pageIndex);
    }
  }

  fetchRecords(pageIndex) {
    ...
  }

 changePage(pageIndex) {
   console.log("change page selected: "+pageIndex);
   this.setState({pageIndex: pageIndex});
   this.fetchRecords(pageIndex);
 }

render() {
  var content = (
      <RecordList
        records={this.state.records}
        pageSize={this.state.pageSize}
        pageIndex={this.state.pageIndex}
        changePage={(pageIndex) => this.changePage(pageIndex)}
        />
    )
  return (
    <div className="App">
      ...
      {content}
    </div>
  );
}
2 Answers
Related