Autenticação com Google em aplicações Rails: Omniauth e Devise

Escrito em 29 de Março de 2022 por Marcos Antonio Macedo Souza

Atualizado em 24 de Agosto de 2023

Hoje é muito comum vermos aplicações que oferecem a opção de login com sua conta Google ou de outros serviços famosos como Facebook, Twitter e outros. Essa autenticação é feita através do protocolo OAuth.

De forma resumida, esse protocolo permite que esses serviços compartilhem informações do usuário e registrem um token de segurança para ser usado em uma sessão da aplicação em que ele está fazendo login. 

Esse tipo de autenticação tem algumas vantagens, como usar dados já existentes sobre o usuário que são guardados nos bancos de dados desses serviços. Isso facilita o acesso do usuário, que não precisará criar um login preenchendo dados manualmente.

O quanto isso pode ser interessante dependerá do seu modelo de aplicação. Às vezes, a criação de um novo login pelo usuário pode ser a melhor opção para o uso de sua aplicação.

Caso você tenha interesse em adicionar uma autenticação com Google à sua aplicação Rails, vamos ver como fazer isso de forma fácil e rápida usando as gems Devise e Omniauth.

Partiremos do pressuposto de que sua aplicação já possui uma autenticação padrão com o Devise. Caso você não esteja usando essa gem e nunca tenha feito a implementação dela, basta seguir a documentação oficial da gem. É bem simples! 

 

Instalando as gems:

Primeiro vamos adicionar as gems necessárias para nossa autenticação, são elas:

  • OmniAuth-Google-OAuth2: Existem várias gems OmniAuth para autenticação com OAuth, essa é específica para autenticar com o Google, facilitando assim a implantação no projeto.
  • OmniAuth-Rails-Csrf-Protection: Cuidará da segurança dos tokens na comunicação entre a aplicação e a API da Google.

Adicione essas gems no seu Gemfile.

gem 'omniauth-google-oauth2'
gem 'omniauth-rails_csrf_protection'

 

Execute bundle install no terminal do seu projeto e vamos começar nossa implementação!

Primeiro configure o Devise para autenticar via OAuth. Adicione o seguinte código no arquivo de configurações do Devise (config/initializers/devise.rb).

 

config.omniauth :google_oauth2, "google_id", "google_secret ", {}

 

Substitua o “google_id” e “google_secret” por suas respectivas chaves da API de OAuth do Google. Caso não tenha feito essa configuração no painel Google antes, siga os primeiros tópicos da documentação da Google sobre a configuração da API. 

Adicione também as opções de OmniAuth (:omniauthable e omniauth_providers: [:google_oauth2]) em seu model User (models/user.rb) junto com as demais configurações do Devise:

 

class User < ApplicationRecord
  devise :database_authenticatable, :registerable,
        :recoverable, :rememberable, :validatable, :omniauthable, omniauth_providers: [:google_oauth2]
end

 

Uma vez configurado o Devise, vamos alterar as rotas para responder ao controller de callback que criaremos a seguir. Altere a linha de rotas do Devise para o seguinte:

 

Rails.application.routes.draw do
devise_for :users, controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }
end

 

Os códigos estão considerando que o model criado pelo Devise para gerenciar os usuários se chama “User”. Caso tenha criado com outro nome, mude sempre onde estiver User para o nome do seu model. Por exemplo, se seu model para usuários for Client o código ficaria:

 

Rails.application.routes.draw do
devise_for :clients, controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }
end

 

Em seguida crie o controller de callback no caminho que especificamos nas rotas (controllers/users/omniauth_callbacks_controller.rb) e adicione o seguinte código:

 

class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController
  def google_oauth2
    @user = User.from_omniauth(request.env['omniauth.auth'])

    if @user.persisted?
      flash[:notice] = I18n.t 'devise.omniauth_callbacks.success', kind: 'Google'
      sign_in_and_redirect @user, event: :authentication
    end
  end
end

 

Note que estamos usando o método .from_omniauth no model User para instanciar o usuário no código acima. Vamos adicionar esse método ao nosso model (models/user.rb):

 

def self.from_omniauth(access_token)
    data = access_token.info
    user = User.where(email: data['email']).first

    user ||= User.create(name: data['name'],
                        email: data['email'],
                        password: Devise.friendly_token[0, 20])
    user
end

 

Agora é só adicionar o link em sua tela de login (views/devise/sessions/new.html.erb) para acessar com a conta Google.

A rota é um POST para /users/auth/google_oauth2. Você pode criar o link usando o helper user_google_oauth2_omniauth_authorize_path, ficando assim.

 

<%= link_to "Sign in with Google", user_google_oauth2_omniauth_authorize_path, method: :post %>

 

E aqui está nossa tela de login!


Essa tela de login no diretório citado acima é a tela padrão do Devise. Se você não possui esses arquivos em seu projeto, provavelmente você não gerou as views do Devise como instrui a documentação do mesmo. Mas é bem simples: é só rodar o comando rails g devise:views no console do seu projeto. 

Posts relacionados