Correct pattern for memory storage of jwts in react graphQL

I’m following the Auth0-GraphQL blog post here and applying those patterns to my own code. I’m running into a problem where after I log in that I only get my jwt stored in memory after all the queries fire and the forceUpdate() doesn’t seem to be rerendering all the queries even if I set the query to ‘network-only’. I have read that Auth0 recommends that we only store tokens in memory, but all the official examples with react show storing tokens in local storage.

Has anyone had luck using class memory for storing their jwts?

class App extends React.Component {

  async componentDidMount() {
    window.jQuery = $;
    window.Tether = Tether;
    require('bootstrap');
    if (this.props.location.pathname === '/callback') return;
    try {
      await auth.silentAuth();
      console.log(auth.getAccessToken()) //this returns with the token
      this.forceUpdate(); //This fires but does not force rerun queries
    } catch (err) {
      if (err.error === 'login_required') return;
      console.log(err.error);
    }
  }

  render() {
    return (
      <div>
              <div>
                <BaseHelmet />
                <NavBar />
                <div className="container-fluid">
                  <Switch>
                    <Route exact path="/" component={HomePage} />
                    <GuardedRoute
                      path="/courses/:courseName/:sectionName/:lectureName"
                      component={LecturePage} />
      
                    <Route exact path="/callback" component={CallbackPage} />
                    <Route component={WhenNotFound} />
                  </Switch>
                </div>
                <Footer />
              </div>
      </div>
    );
  }
}

export default withRouter(App);


class Auth {
  constructor() {
    this.auth0 = new auth0.WebAuth({ ...PublicSettings.authSettings });
    this.authFlag = 'isLoggedIn';
    this.login = this.login.bind(this);
    this.logout = this.logout.bind(this);
    this.handleAuthentication = this.handleAuthentication.bind(this);
    this.isAuthenticated = this.isAuthenticated.bind(this);
  }

  login() {
    this.auth0.authorize();
  }

  getAccessToken() {
    return this.accessToken;
  }

  handleAuthentication() {
    return new Promise((resolve, reject) => {
      this.auth0.parseHash((err, authResult) => {
        if (err) return reject(err);
        if (!authResult || !authResult.accessToken) {
          return reject(err);
        }
        this.setSession(authResult);
        resolve();
      });
    });
  }

  setSession(authResult) {
    this.accessToken = authResult.accessToken;
    localStorage.setItem(this.authFlag, JSON.stringify(true));
  }

  logout() {
    localStorage.setItem(this.authFlag, JSON.stringify(false));
    this.auth0.logout({
      returnTo: homePage,
      clientID: PublicSettings.authSettings.clientID,
    });
  }

  silentAuth() {
    if (this.isAuthenticated()) {
      return new Promise((resolve, reject) => {
        this.auth0.checkSession({}, (err, authResult) => {
          if (err) {
            localStorage.removeItem(this.authFlag);
            return reject(err);
          }
          this.setSession(authResult);
          resolve();
        });
      });
    }
  }

  isAuthenticated() {
    return JSON.parse(localStorage.getItem(this.authFlag));
  }
}

const auth = new Auth();

export default auth;

Hey there!

Sorry for such delay in response! We’re doing our best in providing the best developer support experience out there, but sometimes the number of incoming questions is just too big for our bandwidth. Sorry for such inconvenience!

Do you still require further assistance from us?