Back to Repositories

Testing Devise Authentication Integration Workflow in heartcombo/devise

This integration test suite demonstrates authentication workflow testing in a Rails application using Devise and Minitest. It sets up a minimal Rails environment with Devise authentication and validates user login functionality through integration testing.

Test Coverage Overview

The test suite covers essential Devise authentication flows in a Rails application environment.

  • User authentication validation
  • Session management testing
  • Route protection verification
  • Warden integration testing

Implementation Analysis

The implementation uses Minitest’s integration testing framework with Rack::Test for HTTP request simulation. The approach leverages Warden test helpers for authentication state management, demonstrating proper separation of concerns between authentication logic and application functionality.

  • Rack::Test methods for request handling
  • Warden test mode configuration
  • Rails integration test patterns

Technical Details

  • Minitest testing framework
  • SQLite in-memory database
  • Devise 4.0 authentication
  • Rails 4.2 application setup
  • Warden middleware configuration
  • ActiveRecord migrations

Best Practices Demonstrated

The test implementation showcases several testing best practices for Rails authentication workflows.

  • Isolated test environment setup
  • Proper middleware configuration
  • Helper method inclusion
  • Clean database state management
  • Explicit authentication state handling

heartcombo/devise

guides/bug_report_templates/integration_test.rb

            
# frozen_string_literal: true

begin
  require 'bundler/inline'
rescue LoadError => e
  $stderr.puts 'Bundler version 1.10 or later is required. Please update your Bundler'
  raise e
end

gemfile(true) do
  source 'https://rubygems.org'
  # Activate the gem you are reporting the issue against.
  gem 'rails', '~> 4.2.0'
  gem 'devise', '~> 4.0'
  gem 'sqlite3'
  gem 'byebug'
end

require 'rack/test'
require 'action_controller/railtie'
require 'active_record'
require 'devise/rails/routes'
require 'devise/rails/warden_compat'

ActiveRecord::Base.establish_connection( adapter: :sqlite3, database:  ':memory:')

class DeviseCreateUsers < ActiveRecord::Migration
  def change
    create_table(:users) do |t|
      t.string :email,              null: false
      t.string :encrypted_password, null: true
      t.timestamps null: false
    end

  end
end

Devise.setup do |config|
  require 'devise/orm/active_record'
  config.secret_key = 'secret_key_base'
end

class TestApp < Rails::Application
  config.root = File.dirname(__FILE__)
  config.session_store :cookie_store, key: 'cookie_store_key'
  secrets.secret_token    = 'secret_token'
  secrets.secret_key_base = 'secret_key_base'
  config.eager_load = false

  config.middleware.use Warden::Manager do |config|
    Devise.warden_config = config
  end

  config.logger = Logger.new($stdout)
  Rails.logger  = config.logger

end

Rails.application.initialize!

DeviseCreateUsers.migrate(:up)

class User < ActiveRecord::Base
  devise :database_authenticatable
end

Rails.application.routes.draw do
  devise_for :users

  get '/' => 'test#index'
end

class ApplicationController < ActionController::Base
end

class TestController < ApplicationController
  include Rails.application.routes.url_helpers

  before_action :authenticate_user!

  def index
    render plain: 'Home'
  end
end

require 'minitest/autorun'

class BugTest < ActionDispatch::IntegrationTest
  include Rack::Test::Methods
  include Warden::Test::Helpers

  def test_returns_success
    Warden.test_mode!

    login_as User.create!(email: '[email protected]', password: 'test123456', password_confirmation: 'test123456')

    get '/'
    assert last_response.ok?
  end

  private

  def app
    Rails.application
  end
end