简体   繁体   中英

React Idle Timer with BrowserRouter

I'm attempting to use the React Idle Timer to go to a lock screen after 15 minutes.

The problem I am having is redirecting the page. I am using electron with react and the react BrowserRouter. Because of this I can't use window.location.assign('/clock'); (or similar window.location) method to redirect the page. Typically in my components I use:

this.props.history.push("/clock");

This works within the components that are within the Switch of the BrowserRouter. However, I need the React Idle Timer to be at the top level and when I use props.history.push inside the onIdle function I get the message:

Uncaught TypeError: Cannot read property 'push' of undefined

 class AppRouter extends Component { constructor(props) { super(props); this.idleTimer = null; this.onAction = this._onAction.bind(this); this.onActive = this._onActive.bind(this); this.onIdle = this._onIdle.bind(this); } _onAction(e) { console.log("user did something", e); } _onActive(e) { console.log("user is active", e); console.log("time remaining", this.idleTimer.getRemainingTime()); } _onIdle(e) { console.log("user is idle", e); console.log("last active", this.idleTimer.getLastActiveTime()); //need to push to /clock after 15 minutes //window.location.assign('/clock'); -- WORKS in browser, but not with Electron // this.props.history.push("/clock"); -- gives Uncaught TypeError: Cannot read property 'push' of undefined //can't place <IdleTimer inside BrowserRouter because it only allows 1 thing within. } render() { return ( <div> <IdleTimer ref={ref => { this.idleTimer = ref; }} element={document} onActive={this.onActive} onIdle={this.onIdle} onAction={this.onAction} debounce={250} timeout={1000 * 60 * 0.1} /> <BrowserRouter> <div> <Switch> <Route path="/institution" component={Institution} /> <Route path="/location" component={Location} /> <Route path="/timezone" component={TimeZone} /> <Route path="/clock" component={Clock} /> <Route path="/" component={PreflightCheck} /> </Switch> </div> </BrowserRouter> </div> ); } } ReactDOM.render(<AppRouter />, document.getElementById("root"));

What is the correct way to redirect to a component at the top level outside of the BrowserRouter tags?

I have also tried this:

import { createHashHistory } from 'history'
export const history = createHashHistory()

and then calling history.push('/clock');

That only seems to append /clock to the current page that I am on and I get this message:

Hash history cannot PUSH the same path; a new entry will not be added to the history stack

Create history (you can use npm install history):

import { createBrowserHistory } from "history";
const history = createBrowserHistory();

Then place the idle timer within Router. BrowserRouter does not seem to work with history like Router does in this situation.

<Router history={history}>
      <div>

  <IdleTimer
          ref={ref => {
            this.idleTimer = ref;
          }}
          element={document}
          onActive={this.onActive}
          onIdle={() =>  this.checkplayerstatus(history)}
          onAction={this.onAction}
          debounce={250}
          timeout={1000 * 60 * 15}
        />
        <Switch>
          <Route path="/institution" component={Institution} />
          <Route path="/location" component={Location} />
          <Route path="/timezone" component={TimeZone} />
          <Route path="/clock" component={Clock} />
          <Route path="/" component={PreflightCheck} />
        </Switch>
      </div>
    </>

And then in the onIdle function you can do this: "whatevervariableyoupassashistoryfromonidle".push("/clock").

   If you are using tsx means ,
      _onIdle=(e)=> {
          window.location.href = "/your_location";
       }
    or if you are using js means,
      _onIdle=(e)=> {
          window.location = "/your_location";
       }

<IdleTimer
          ref={ref => {
            this.idleTimer = ref;
          }}
          element={document}
          onActive={this.onActive}
          onIdle={() =>  this.checkplayerstatus(history)}
          onAction={this.onAction}
          debounce={250}
          timeout={1000 * 60 * 15}  // 15 minutes
        />

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM