Persisting the Login

In notebook:
Building Modern Web Apps
Created at:
2016-01-23
Updated:
2016-06-12
Tags:
JavaScript DOM libraries React Ampersand
We have to store the session info

​LocalStorage​ is the perfect place to store this.

Create a model for the user

  1. Creates a models directory
  2. names the first model me.js (it's the user model)
  // **** models/me.js ****
import Model from 'ampersand-model'

export default Model.extend({
    // props: we get from the server
    // and we want to persist back to the server
    // e.g. user profile info
    props: {
       id: 'number',
       login: 'string',
       avatar_url: 'string'
    },
    // session: things we want to keep
    // but not save as permanent data 
    // to the server (e.g. the token)
    session: {
        token: 'string'
    }
})
In Backbone you don't have to predefine properties of the model. In Ampersand you do.
Everything you want to persist in the model you have to explicitly define as a property.
The ​props​ model
It's just the data we will get from github.

Create the model

Above we just defined the model. Now we'll create one.
He'll do it in app.js 
  // **** app.js ****
import ...
// ++++ 1. import the Me model
import Me from './models/me'

window.app = app

app.extend({
    init () {
        // ++++ 2. create a new Me model
        this.me = new Me()
        this.router = new Router();
        this.router.history.start();
    }
})

app.init();
We can take advantage that these are observable models.
So in router.js we can just assign the token
  // **** router.js ****
import ...
// ++++ 1. import app
import app from 'ampersand-app'

export default Router.extend({
    ...
    routes: { ...  },
    public () { ... },
    repos () { ... },

    login () { ... },
    
    
    authCallback (query) {
        query = qs.parse(query)
        console.log(query);
        // ++++ 2. do the ajax request for the token
        xhr({
            url: 'https;//the-heroku-labelr-service-url' + query.code,
            json: true
        }, (err, req, body) => {
            console.log(body)
            // ++++ 2. assign to the me model
            // notice that we're not using
            // app.me.session.token but
            // just app.me.token
            app.me.token = body.token
        })
    }
})
We still have to modify the model so that it persists.
We add an initialise method to the me model.
  // **** models/me.js ****
import ...

export default Model.extend({
    // ++++ 1. add initialize
    // it will once when you create (instantiate)
    // a new model
    initialize () {
        // the case that we already have a token
        // (this.token and not this.session.token)
        this.token = window.localStorage.token;
        // ++++ 2. if the token changes
        // change event is part of ampersand model
        this.on('change:token', this.onTokenChange)
    },
    
    props: {...},
    
    session: {
        token: 'string'
    },
    
    // ++++ 3. define the onTokenChange handler
    onTokenChange () {
        window.localStorage.token = this.token
        // every time the token changes
        // it will automatically written to localstorage
    }
    
})
In some way React is a layer of protection against cross site scripting attack, since it sanitises the DOM manipulation.