So you’ve built yourself an app, cool! But now you want to add user accounts! Neato! But alas! Your records are going to need to be linked to each user, otherwise everybody with an account can view every bodies information. No bueno. We are going to need to separate that asap.
Thankfully there’s a gem for that! Because I’m going to regale you with a story about how I built my own user auth system and how they all work…
The User Authentication System
When I first started coding web apps this was incredibly confusing to me. This was not lessened by the fact that I was coding in Java with the Spring framework… Screw you java. I was missing a few key lessons and had to fumble my way through it, but the basic essence is;
register user with email and password →
check in user database for a matching email →
if email unique validate password →
if password valid then encrypt password →
store email and password in user database →
create getters and setters to repeat this while still providing security.
A common method is that when visiting a website, the server assigns you a ‘Session’ and on login you put in the email and the service checks the database and looks for a matching email, then encrypts the entered password and compares it against the record. If everything checks out, the session is authenticated and is assigned some semi-permanent variable. Sometimes it stores your login info and rechecks it after every action, sometimes its stored in cookies. Magic!
With Java I literally had to create the database, every registration table, program in my own getters, setters, checks, encryption, etc. It was exhausting.
Ruby on Rails has a gem for that. Of Course.
Let’s Devise A Way To Do It
Devise is the super popular, ready to go out of the box, fully loaded gem that allows you to set up a user registration system in minutes, rather than days. Check them out HERE
They give you modular options allowing you to chose whether you want to track new user registration, offer password resets, lock accounts, send confirmation emails, etc. Just really great stuff guys.
Installation is super easy and super customizable;
# gemfile.rbgem 'devise'
rails g devise:install
Perfect. Devise is set up. There are some extra config options you can set up like the mailer, recoverable or confirmation options, etc. But that's bonus reading.
Next we need to create a new model, one specifically for devise, probably something that can store lots of information about the person signing in and logging in… Something probably called a User;
rails generate devise User
This creates a new model in your program, specifically for devise, that is created when a new User registers for your site! Simple! But we are going to destroy that Model and make a newer, better one.
Customise Your Devise Model
rails d devise User
rails g devise User username:string account_id:string role:string active:boolean paid_to:date
Just like creating any other model we can pass in a bunch of column names and types and get a little customisation with our devise models. In this one I want to add a custom account id, a role (ie. admin, employee, user, etc.) and more. These are not devise specific, but that's how you can add your own data to a devise model.
After its all in there and your happy;
And you should have a User model that looks something like this;
class User < ApplicationRecord
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable, :trackable and :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :validatable
The commented out lines are all options that aren’t being used and the ones below are options that are on by default. There is nothing to worry about here if you are going for the base install, but for more info check out the Devise Git.
Logging In And Out
This bit is easy, Devise has it right on their Git;
<%if user_signed_in? %>
<%=link_to('Logout', destroy_user_session_path, method: :delete) %>
<%=link_to('Login', new_user_session_path) %>
Just put that into your nav bar list, or anywhere you want really, and it’ll direct the user to the appropriate page.
And There you have it! Stay tuned for another post on linking the user with their created content!