[RUBY] [For beginners] Test devise user registration with RSpec

Introduction

I introduced devise, but I can't write the first test ...! I didn't have all the information about how to write it, so I tried to summarize it myself. For beginners who have started making their own apps.

Ruby '2.6.6' Rails '5.2.4'

1. Edit Gemfile

Gemfile


group :development, :test do
・
・
  gem "rspec-rails"
  gem "factory_bot_rails"
end

To the Gemfile

Terminal


bundle install

Terminal



bundle install 
Fetching gem metadata from https://rubygems.org/............. 
Fetching gem metadata from https://rubygems.org/. 
・
・
Using duktape 2.3.0.0 
Fetching factory_bot 6.1.0 
Installing factory_bot 6.1.0 
Fetching factory_bot_rails 6.1.0 
Installing factory_bot_rails 6.1.0 
Using jbuilder 2.10.0
・
・
Using web-console 3.7.0 
Bundle complete! 22 Gemfile dependencies, 95 gems now installed. 
Use `bundle info [gemname]` to see where a bundled gem is installed.

Download RSpec

Terminal


$ bundle exec rails generate rspec:install

2. .rspec settings

Write the following in .rspec.

rspec


--require spec_helper
--format documentation #Add here

The above description may or may not be present, but with or without it, the display at the time of test execution changes so much.

None

$ ...............................

Yes $ User $ #create $ is valid $ is invalid without email $ is invalid without password


 Source: How to log in to devise in rspec test environment [rails]
https://qiita.com/Kohei_Kishimoto0214/items/e29e509b12a6eb484a42

### I haven't written anything, but I'll give it a try

 The command to test is
`bundle exec rspec`
 Alternatively, it can be specified individually


#### **`Terminal`**
```ruby

bundle exec rspec
No examples found.


Finished in 0.00101 seconds (files took 3.71 seconds to load)
0 examples, 0 failures

I haven't described what to check yet, but it is displayed ...! !! !!

3. Set Factory_bot

Add the following description to the config part in rails_helper.rb.

spec/rails_helper.rb


RSpec.configure do |config|
    config.includeFactoryBot::Syntax::Methods
end

I think it will look like this.

spec/rails_helper.rb


RSpec.configure do |config|
  # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
  config.fixture_path = "#{::Rails.root}/spec/fixtures"
  config.include FactoryBot::Syntax::Methods
  config.use_transactional_fixtures = true
  config.infer_spec_type_from_file_location!
  config.filter_rails_from_backtrace!
end

4. Rails_helper settings

Next, the following sentence is commented out in /spec/rails_helper.rb, so please uncomment it. You can now load the spec / support / file.

/spec/rails_helper.rb


Dir[Rails.root.join('spec/support/**/*.rb')].each{|f|requiref}

/spec/rails_helper.rb


# This file is copied to spec/ when you run 'rails generate rspec:install'
require 'spec_helper'
ENV['RAILS_ENV'] ||= 'test'
require File.expand_path('../config/environment', __dir__)
# Prevent database truncation if the environment is production
abort("The Rails environment is running in production mode!") if Rails.env.production?
require 'rspec/rails'
# Add additional requires below this line. Rails is not loaded until this point!

# Requires supporting ruby files with custom matchers and macros, etc, in
# spec/support/ and its subdirectories. Files matching `spec/**/*_spec.rb` are
# run as spec files by default. This means that files in spec/support that end
# in _spec.rb will both be required and run as specs, causing the specs to be
# run twice. It is recommended that you do not name files matching this glob to
# end with _spec.rb. You can configure this pattern with the --pattern
# option on the command line or in ~/.rspec, .rspec or `.rspec-local`.
#
# The following line is provided for convenience purposes. It has the downside
# of increasing the boot-up time by auto-requiring all files in the support
# directory. Alternatively, in the individual `*_spec.rb` files, manually
# require only the support files necessary.
#
 Dir[Rails.root.join('spec', 'support', '**', '*.rb')].sort.each { |f| require f }Uncommented here

# Checks for pending migrations and applies them before tests are run.
# If you are not using ActiveRecord, you can remove these lines.
begin
  ActiveRecord::Migration.maintain_test_schema!
rescue ActiveRecord::PendingMigrationError => e
  puts e.to_s.strip
  exit 1
end
RSpec.configure do |config|
  # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
  config.fixture_path = "#{::Rails.root}/spec/fixtures"
  config.include FactoryBot::Syntax::Methods
  

  # If you're not using ActiveRecord, or you'd prefer not to run each of your
  # examples within a transaction, remove the following line or assign false
  # instead of true.
  config.use_transactional_fixtures = true

  # You can uncomment this line to turn off ActiveRecord support entirely.
  # config.use_active_record = false

  # RSpec Rails can automatically mix in different behaviours to your tests
  # based on their file location, for example enabling you to call `get` and
  # `post` in specs under `spec/controllers`.
  #
  # You can disable this behaviour by removing the line below, and instead
  # explicitly tag your specs with their type, e.g.:
  #
  #     RSpec.describe UsersController, type: :controller do
  #       # ...
  #     end
  #
  # The different available types are documented in the features, such as in
  # https://relishapp.com/rspec/rspec-rails/docs
  config.infer_spec_type_from_file_location!

  # Filter lines from Rails gems in backtraces.
  config.filter_rails_from_backtrace!
  # arbitrary gems may also be filtered via:
  # config.filter_gems_from_backtrace("gem name")
end

5. Preparation of test data

Create a new folder & file spec \ factories \ user.rb

This time, Faker is not included, so enter the data manually. There is also a way to assign serial numbers, but this time we will use the simplest method.

Since the devise initial setting has no name, only the following three elements are required. If you have added the name column, please add the name item to spec \ factories \ user.rb as well.

spec\factories\user.rb


FactoryBot.define do
  factory :user do
    email                 {"[email protected]"}
    password              {"111111"}
    password_confirmation {"111111"}
  end
end

6. Create controller_macros

Create spec / support / controller_macros.rb and add the official content below.

Official: How To: Test controllers with Rails (and RSpec) https://github.com/heartcombo/devise/wiki/How-To:-Test-controllers-with-Rails-(and-RSpec)

spec/support/controller_macros.rb


module ControllerMacros
  def login_admin
    before(:each) do
      @request.env["devise.mapping"] = Devise.mappings[:admin]
      sign_in FactoryBot.create(:admin) # Using factory bot as an example
    end
  end

  def login_user
    before(:each) do
      @request.env["devise.mapping"] = Devise.mappings[:user]
      user = FactoryBot.create(:user)
      user.confirm! # or set a confirmed_at inside the factory. Only necessary if you are using the "confirmable" module
      sign_in user
    end
  end
end

7. Load devise and controller_macros in rails_helper

Write the following outside RSpec.configure of rails_helper and load devise and macros.

spec/rails_helper.rb


require'devise'
requireFile.expand_path("spec/support/controller_macros.rb")

Write the following in RSpec.configure to enable devise's test_helper and macros in the controller.

spec/rails_helper.rb


RSpec.configure do |config|
・
・
 config.include Devise::Test::ControllerHelpers, type: :controller
  config.include Devise::Test::IntegrationHelpers, type: :request
  config.extend ControllerMacros, :type => :controller
・
・

When added, it looks like this.

spec\rails_helper.rb



 # This file is copied to spec/ when you run 'rails generate rspec:install'
require 'spec_helper'
ENV['RAILS_ENV'] ||= 'test'
require File.expand_path('../config/environment', __dir__)
abort("The Rails environment is running in production mode!") if Rails.env.production?
require 'rspec/rails'
require 'devise'
require File.expand_path("spec/support/controller_macros.rb")
require_relative 'support/controller_macros'

 Dir[Rails.root.join('spec', 'support', '**', '*.rb')].sort.each { |f| require f }


begin
  ActiveRecord::Migration.maintain_test_schema!
rescue ActiveRecord::PendingMigrationError => e
  puts e.to_s.strip
  exit 1
end
RSpec.configure do |config|
  # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
  config.fixture_path = "#{::Rails.root}/spec/fixtures"
  config.include FactoryBot::Syntax::Methods
  config.include Devise::Test::ControllerHelpers, type: :controller
  config.include Devise::Test::IntegrationHelpers, type: :request
  config.extend ControllerMacros, :type => :controller

 
  config.infer_spec_type_from_file_location!
  config.filter_rails_from_backtrace!

end

8. In user_spec.rb, create user and log in.

The created user is stored in let and can be used like an instance variable. Then let that user log in to devise using the login_user method.

Test the validation of the model. Please set validation in advance.

require 'rails_helper'

RSpec.describe User, type: :model do describe 'user registration' do it "name, email, password and password_You can register if confirmation exists" do user = build(:user) expect(user).to be_valid # user.valid?Pass if is true end

end


Source: [Test using Rspec (1) (Unit test: Validation test)] (https://misukeblog.com/rspec/) Source: [Test using Rspec (2) (Integration test)] (https://misukeblog.com/rspec2/)

After writing

Terminal


bundle exec rspec

Go out

Should be! !! !! !! This completes! !!

Terminal


$ bundle exec rspec
 
User
name, email, password and password_You can register if confirmation exists
 
Finished in 0.5297 seconds (files took 9.34 seconds to load)
1 example, 0 failures

9. I'm addicted to

pattern 1

Terminal



& rails g rspec:model user
    conflict  spec/models/user_spec.rb
Overwrite C:/Users/deeep/techpitgram/spec/models/user_spec.rb? (enter "h"
for help) [Ynaqdhm]
                                        force  spec/models/user_spec.rb   for help) [Ynaqdhm]
$ bundle 


Migrations are pending. To resolve this issue, run:
 
        bin/rails db:migrate RAILS_ENV=test
No examples found.

In such a case, as instructed

Terminal


$ rails db:migrate RAILS_ENV=test

let's do it

Pattern 2

If you get an error like this, it's an old gem in your gemfile.

Terminal



$ bundle exec rspec
2020-09-02 22:36:39 WARN Selenium [DEPRECATION] Selenium::WebDriver::Chrom
e#driver_path= is deprecated. Use Selenium::WebDriver::Chrome::Service#dri
ver_path= instead.
 
An error occurred while loading ./spec/models/user_spec.rb.
Failure/Error: require File.expand_path('../config/environment', __dir__)
 
Selenium::WebDriver::Error::WebDriverError:
per-2.1.1/bin/chromedriver-helper"
# ./config/application.rb:7:in `<top (required)>'

# ./config/environment.rb:2:in `<top (required)>'
# ./spec/rails_helper.rb:4:in `require'
# ./spec/rails_helper.rb:4:in `<top (required)>'
# ./spec/models/user_spec.rb:1:in `require'
# ./spec/models/user_spec.rb:1:in `<top (required)>'
No examples found.
 
 
Finished in 0.00008 seconds (files took 7.23 seconds to load)
0 examples, 0 failures, 1 error occurred outside of examples

Reference: Rspec does not work Loading rails_helper https://teratail.com/questions/247938?link=qa_related_pc

Rewrite the Gemfile.

Gemfile



group :test do
  # Adds support for Capybara system testing and selenium driver
  gem 'capybara', '>= 2.15'
  gem 'selenium-webdriver'
  # Easy installation and use of chromedriver to run system tests with Chrome
  #gem 'chromedriver-helper'  #Delete this one sentence or comment out
  gem 'webdrivers', '~> 3.0' #Add this one line
  gem 'rspec-rails'
  gem "factory_bot_rails"
end
・
・

gem 'devise'

And

Terminal


bundle install

You should be able to do this!

Finally

I would be grateful if you could point out any mistakes.

Various references

[Procedure for installing Rspec and Factory_bot in Rails app] (https://qiita.com/Ushinji/items/522ed01c9c14b680222c)

[RSpec beginner devise authentication system test] (https://qiita.com/zongxiaojie/items/d488edd42ba3864859c7)

[How to log in to devise in rspec test environment [rails]] (https://qiita.com/Kohei_Kishimoto0214/items/e29e509b12a6eb484a42)

[Testing the controller with devise] (https://qiita.com/nysalor/items/ef3d658ff76bee165379)

[Notes on unit tests using RSpec @TECH CAMP # 11-note] (https://note.com/ruquia7/n/n00ff04fc9129)

[[Ruby on Rails] Unit test of model using rspec-note] (https://note.com/vixer93/n/n6ef6555d7a3e)

[About the error "bin / rails db: migrate RAILS_ENV = test" after migrate in Rails] (https://teratail.com/questions/178462)

Recommended Posts

[For beginners] Test devise user registration with RSpec
devise user registration
[Rails] Test with RSpec
Test Nokogiri with Rspec.
Test Active Strage with RSpec
(For beginners) [Rails] Install Devise
Test GraphQL resolver with rspec
Edit user information with Devise
Unit test code for a model using RSpec, which has a little peculiarity ~ User registration
How to test a private method with RSpec for yourself
Environment construction with Docker for beginners
Test with RSpec + Capybara + selenium + chromedriver
Copy and paste test with RSpec
Let's unit test with [rails] Rspec!
[RSpec on Rails] How to write test code for beginners by beginners
6 points to doubt when user registration is not possible with devise
[Rails] Unit test code for User model
[Ruby on Rails] View test with RSpec
Learn Java with "So What" [For beginners]
[Ruby on Rails] Controller test with RSpec
[Ruby on Rails] Model test with RSpec
[Workshop for beginners] Let's write an E2E test with Cloud9 + Docker Compose + Cypress!
[Swift / For beginners] Write smartly with type inference
[Java] How to test for null with JUnit
I want to test Action Cable with RSpec test
I rewrote the Rails tutorial test with RSpec
Use [Rails] devise Guest user function (for portfolio)
Rails beginners tried to get started with RSpec
[RSpec] I wrote a test for uploading a profile image.
Why you need an email address for user registration
[Must-see for beginners] Compile settings with IntellJ [Many images]
About products using crud processing and devise (for beginners)
RSpec unit test code creation procedure (login user creation Ver.)
Rails5 Rspec test error ArgumentError: Factory not registered: user
Introduction to RSpec 4. Create test data with Factory Bot