Torii session does not persist after refresh

833 views Asked by At

Currently, my Ember-cli application logs out after refresh. I have altered my code a lot to try to get it to work, but none helped. If necessary, I will try to implement authentication with another provider.

I have a route for application, which is just the logout and a route for login, which deals with login, because the client wants to style it.

My config/environment.js file looks like this:

firebase: 'https://<my-website-here>.firebaseio.com/',
    torii: {
      sessionServiceName: 'session'
    },

app/adapters/application.js:

import Ember from 'ember';
import FirebaseAdapter from 'emberfire/adapters/firebase';

const { inject } = Ember;

export default FirebaseAdapter.extend({
  firebase: inject.service(),
});

app/torii-adapters/application.js:

import Ember from 'ember';
import ToriiFirebaseAdapter from 'emberfire/torii-adapters/firebase';

export default ToriiFirebaseAdapter.extend({
  firebase: Ember.inject.service()
});

app/routes/application.js:

import Ember from 'ember';

export default Ember.Route.extend({
 actions: {
   logout: function() {
       this.get('session').close().then(function() {
           this.transitionTo('application');
       }.bind(this));
   }
  }
});

app/routes/login.js:

import Ember from 'ember';

export default Ember.Route.extend({
  actions: {
    login: function() {
      var controller = this.get('controller');
      var email = controller.get('userEmail');
      var password = controller.get('userPassword');
        this.get('session').open('firebase', {
             provider: 'password',
             email: email,
             password: password
        }).then(function() {
            this.transitionTo('dashboard');
        }.bind(this));
    }
  }
});

Yeah, currently, login and logout works just fine, but I cannot refresh the page in the middle of the session, or else it logs out me automatically.

Thanks to anyone in advance.

2

There are 2 answers

1
Alisdair McDiarmid On BEST ANSWER

Torii does not persist your authentication session for you. You need to implement this yourself in the open, fetch, and close hooks of your adapter.

The easiest way to do this is with the localStorage API.

Fetch

In the fetch hook, you need to pull your session data out of localStorage. If there's nothing there, either throw an exception or return a promise which will reject.

Open

Your adapter needs to resolve with the session data, but should also store it in localStorage for later sessions.

Close

Clear the localStorage key for your session data and return a promise which will resolve.

Example

Here's the application adapter from one of my applications, which uses the Slack API with Torii. The open hook is likely different from what you need for Firebase, but hopefully this gives you something to work with.

export default Ember.Object.extend({
  storage: Ember.inject.service(),

  fetch() {
    let token = this.get('storage.token');

    if (Ember.isEmpty(token)) {
      throw new Error('No token in storage');
    }

    return Ember.RSVP.resolve({ token });
  },

  open(authentication) {
    return new Ember.RSVP.Promise((resolve, reject) => {
      Ember.$.ajax({
        type: 'POST',
        url: '/api/tokens',
        data: authentication,
        dataType: 'json',
        success: Ember.run.bind(null, resolve),
        failure: Ember.run.bind(null, reject)
      });
    }).then(data => {
      let token = data.accessToken;

      this.set('storage.token', token);

      return { token };
    });
  },

  close() {
    this.set('storage.token', null);

    return Ember.RSVP.resolve();
  }
});

My storage service is a wrapper around the browser localStorage API.

0
dirkdirk On

Here's a much easier way.

app/routes/application.js:

import Ember from 'ember';

export default Ember.Route.extend({
  beforeModel: function() {
    return this.get('session').fetch().catch(function() {});
  },

  model() {
    if(this.get('session.isAuthenticated')) {
      return this.store.findAll('post');
    } else {
      this.transitionTo('login');
  }
});

The key is the beforeModel fetching the session.

I found this little nugget here: https://blog.isnorcreative.com/2016/07/30/ember-firebase.html