4

I have a simple Backbone.js app with User model with different roles and I use json-server to emulate some backend basics. I need to make a basic authentication -- i.e. I need my User to be able to login and save his session somewhere (for that he wouldn't need to sign in each time he refreshes his browser). I've got a db.json file where I already have some users:

{
    "users": [
        {
            "login": "admin",
            "password": "password",
            "role": "admin",
            "id": 1
        }
    ]
}

and here is my User model:

var User = Backbone.Model.extend({
    defaults: {
        login: "",
        password: "",
        role: ""
    },
    // Updated
    url: function () {
        return "http://localhost:3000/users?login=" + 
                   this.attributes.login + "&password=" + this.attributes.password;
    }
});

I don't get quite good how could I manage authentication (i.e. entering login and password in form and storing the user session without proper backend). I thought about making a token field in my User model and filling in in each time user signs in and saving it in cookies, but I don't get how could I do that either way. I would be very grateful if someone could help me with this task.

ADDDED This is my login function in my view:

signIn: function () {
    var login = $('#js-login').val();
    var password = $('#js-password').val();

    if (login && password) {
        var currentUser = new User({
            login: login,
            password: password
        });
        currentUser.fetch({
            success: function () {
                console.log(currentUser.toJSON());
            },
            error: function (err) {
                console.log(err);
            }
        });
    }
}

But instead of finding a user from my json-server it just creates a new user with all empty attributes except of values of #js-login and #js-password input fields

ADDED I guess I should find my users by the query in url above in my collection, but I don't actually get how I would manage that

Repo with my project

AlexNikolaev94
  • 1,169
  • 2
  • 16
  • 40

2 Answers2

2

This is simplified flow for your app:

  • Each time user open your website, check his cookies.

    • If cookies contain user info (saved username, password), check match with the info in your DB. If matched, go to home page. Otherwise, clear cookies, go to login page

    • If cookies not contain user info, go to login page

  • In login page, after user success logged in, save user info to cookies for next time check.

You can use some mechanism to encode user info (tokens, encryption...) to secure info stored in cookies/sessions. But store authentication DB in client is really weak security point. Sample code below:

Model:

var User = Backbone.Model.extend({
    url: function () {
        return "users?login" + this.attributes.login + "&password=" + this.attributes.password;
    },

    isAdmin: function () {
        return (this.get("role") == "admin");
    }
});

In your view:

// Load username password from cookie (just simple example)
var username = $.cookie("username"),
    password = $.cookie("password");

if (username && password) {
    var userModel = new User({
        login: username,
        password: password
    });
    userModel.fetch({
        success: function () {
            if (userModel.isAdmin) {
                // e.g. go to admin page
            } else {
                // e.g. go to normal user page
            }

            // Save to cookie/session here
        },
        error: function () {
            // Go to login page
        }
    });
} else {
    // Go to login page
}

About cookie, you can refer How do I set/unset cookie with jQuery?

About getting username/password input form, you can just use simple jquery selector (very easy to google for it, e.g. https://www.formget.com/jquery-login-form/)

Community
  • 1
  • 1
Akivamu
  • 550
  • 5
  • 17
  • Thank you! That looks like exactly something what I need. But I don't very get how I will get user's login and password from my login form, find this user and store his credentials in cookies. Could you please explain that a little bit more? – AlexNikolaev94 Oct 15 '16 at 10:14
  • 1
    I updated answer. Btw, your question in comment is very popular, better search google for example. – Akivamu Oct 15 '16 at 15:17
  • I tried your variant, it seems to create a new user instead of getting one of already existent :( it just creates a new user with empty properties except login and password which I enter to input fields instead of finding one with these credentials – AlexNikolaev94 Oct 15 '16 at 16:27
  • Inside `success` callback of userModel.fetch(), put this line to debug if data received from server is correct: `console.log(userModel.toJSON());` http://backbonejs.org/#Model-toJSON – Akivamu Oct 17 '16 at 06:04
  • the response is a new empty `User` model, the only properties which it has are `login` and `password` that I've entered in my input fields – AlexNikolaev94 Oct 17 '16 at 06:24
  • Check to make sure you can get valid response from json-server. What is response of `users?login=admin&password=password`? Try with your browser. – Akivamu Oct 17 '16 at 06:48
  • `GET /users?login=admin&password=password 200 6.522 ms - 335` this is my response from json-server, and in browser it `console.log`'s `User` model that I've told about above. – AlexNikolaev94 Oct 17 '16 at 06:55
  • If your normal 'GET' can't not return valid response, so URL could be wrong. I don't use json-server lib, can't tell exactly what 's wrong. But you should make sure the URL is correct in normal 'GET' before bring it to your app. By normal 'GET', I mean HTTP get, or you can type url into address bar of any browser. What about `/users/1` response? – Akivamu Oct 17 '16 at 07:21
  • `/users/1` response is correct and returns the proper model. I guess I should find a user by his `id` before logging in, according to credentials I enter, but I can't exactly manage how – AlexNikolaev94 Oct 17 '16 at 07:32
  • That's weird, lib's docs stated that supported: https://github.com/typicode/json-server#filter. Try to change success callback in model fetch() like this `success: function (data) { console.log(data); }` I think json-server responses as ARRAY, not object – Akivamu Oct 17 '16 at 07:45
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/125881/discussion-between-huy-luu-and-alexnikolaev94). – Akivamu Oct 17 '16 at 07:48
0

Here you can refer to this plugin that uses mostly the jquery functions as mentioned in the documentation here

I would not be going into much detail as the documentaion is quite clear. This refers to the authentication with the jquery

Now IF you want to authenticate the user using backbone.js

if the route came back with {loggedIn: false} the backbone router would send the user to the login/register pages only. But if it came back with a users profile information then it would obviously mean he had a session.

wire up $.ajax to respond to 401 (Unauthorized) status codes.

Also to mention as stated in this stackoverflow thread

Hope it may be able to help you a bit.

Here is the step by step guide to authenticate with backbone.js

Community
  • 1
  • 1
Pritish Vaidya
  • 21,561
  • 3
  • 58
  • 76