Rails 8 comes with a built-in authentication generator. However, it doesn’t yet come with registrations. Here’s how to add them.
Rails auth generator
To generate authentication scaffold, run:
$ rails generate authentication
This will create User
and Session
models as well as sign-in forms. But there is little to do without registrations.
Registrations
To add registrations, we’ll add a new RegistrationsController
, route, and view.
The registration controller can look like this:
# app/controllers/registrations_controller.rbclassRegistrationsController<ApplicationController# Include Authentication module unless it's already in ApplicationControllerincludeAuthenticationallow_unauthenticated_accessrate_limitto: 10,within: 3.minutes,only: :create,with: ->{redirect_tonew_registration_url,alert: "Try again later."}defnew@user=User.newenddefcreate@user=User.new(safe_params)if@user.savestart_new_session_for@userredirect_toafter_authentication_url,notice: "Welcome!"elseflash[:alert]="Email or password confirmation invalid."render:new,status: :unprocessable_entityendendprivatedefsafe_paramsparams.require(:user).permit(:email_address,:password,:password_confirmation)endend
The code is surprisingly simple. We rely on the generator’s Authentication
module and start_new_session_for
method to sign people in. And we rely on has_secure_password
to do the right thing when providing users with password
and password_confirmation
.
Note that it doesn’t come with any constrains for passwords or email address, but we can add them:
# app/models/user.rbclassUservalidates:email_address,presence: truevalidates:password,length: {minimum: 10},if: ->{new_record?||changes[:password_digest]}validates:password,confirmation: true,if: ->{new_record?||changes[:password_digest]}validates:password_confirmation,presence: true,if: ->{new_record?||changes[:password_digest]}end
Then let’s add the view:
<!--app/views/registrations/new.html.erb--><%= tag.div(flash[:alert], style: "color:red") if flash[:alert] %>
<%=tag.div(flash[:notice],style: "color:green")ifflash[:notice]%><%= form_for @user, url: registrations_path do |form| %>
<%=form.label:email_address,"Email:"%><%= form.email_field :email_address, autofocus: true %>
<%=form.label:email,"Password:"%><%= form.password_field :password, required: true %>
<%=form.label:email,"Confirmation:"%><%= form.password_field :password_confirmation, required: true %>
<%=form.submit"Register"%><% end %>
Finally, let’s add the route:
Rails.application.routes.drawdoresource:sessionresources:passwords,param: :token# add thisresources:registrations,except: [:index,:show,:destroy]end
And that’s it! You can now register as a new user.