0
votes

I don't know why but chrome renders blank page after completion of first it block.

create_account_spec.rb :

require 'feature_helper'
require 'rails_helper'

describe 'Create users' , :chrome do
    let(:company)  { build(:company, :auto_company) }
    let(:financer) { build(:account, :auto_financer) }
    let(:code_1)   { build(:account, :auto_code_1) }
    let(:user)     { build(:account, :auto_user) }

    before :all do
      visit '/'
      company = build(:company, :auto_company)

      GUI.login_as :auto_admin

    # Create Company
    find('#employer_model_screen a').send_keys :enter
    fill_in 'name',           with: company.name
    fill_in 'code_1',         with: company.code1
    fill_in 'code_2',         with: company.code2
    fill_in 'code_3',         with: company.code3
    fill_in 'code_4',         with: company.code4
    select  'Ukraine',        from: 'country_code'
    fill_in 'master_counter', with: company.master_counter
    fill_in 'storage',        with: company.storage
    find('input[value="CREATE"]').send_keys :enter

    GUI.sign_out
  end

  describe 'Check company created', :chrome do
    before :all do
      GUI.login_as :auto_admin
      find('#employer_model_screen a').send_keys :enter
    end

    after :all do
      GUI.sign_out
      visit '/'
    end
    it { expect(first('td.name').text).to eq company.name }
    it { expect(first('td.workflow-type').text).to  eq company.workflow_type }
    it { expect(first('td.code-1').text).to         eq company.code1 }
    it { expect(first('td.code-2').text).to         eq company.code2 }
    it { expect(first('td.code-3').text).to         eq company.code3 }
    it { expect(first('td.code-4').text).to         eq company.code4 }
    it { expect(first('td.country-code').text).to   eq company.country_code }
    it { expect(first('td.business-model').text).to eq 'R1' }
    it { expect(first('td.master-counter').text).to eq company.master_counter.to_s }
    it { expect(first('td.storage').text).to        eq company.storage.to_s }
  end

  context 'financer account' do
    describe 'create financer account', :chrome do
      include_examples 'login as', :auto_admin

      it 'fill financer fields' do
        find('#employer_model_screen a').send_keys :enter
        find('a', text: company.name).send_keys :enter
        fill_in 'emp_id',      with: financer.employee_id
        fill_in 'first_name',  with: financer.first_name
        fill_in 'last_name',   with: financer.last_name
        fill_in 'designation', with: financer.designation
        fill_in 'department',  with: financer.department
        fill_in 'email',       with: financer.email
        find('#create_code2').send_keys :enter
      end

      it { expect(first('td.emp_id').text).to      eq financer.employee_id }
      it { expect(first('td.name').text).to        eq financer.first_name + ' ' + financer.last_name }
      it { expect(first('td.designation').text).to eq financer.designation }
      it { expect(first('td.department').text).to  eq financer.department }
      it { expect(first('td.code_type').text).to   eq 'financer' }
      it { expect(first('td.email').text).to       eq financer.email }
      it { expect(first('td.status').text).to      eq financer.status }
      it { expect(first('.btn-primary').text).to eq 'ACTIVATE' }

      include_examples 'sign out'
    end

    describe 'sign up as financer account', :chrome do
      include_examples 'sign up as', :auto_financer, code: :code2
      include_examples 'check sign up successfully'
      include_examples 'check welcome message'
      include_examples 'sign out'
    end

    describe 'login as financer', :chrome do
      it 'fill email' do
        fill_in 'email', with: financer.email
        sleep(0.5)
      end

      include_examples 'check plan', disabled: :individual, checked: :company

      it 'fill password & Go' do
        fill_in 'password', with: financer.password
        find('[value=Go]').send_keys :enter
      end
      include_examples 'check sign in successfully'
      include_examples 'check navigation items', 'Home', 'Submit', 'Storage (0)',
                       'My Claims', 'Employees\' Claim (0)', 'Sign Out',
                       'Employee Accounts', 'Expense Setup', 'Reports'
      include_examples 'sign out'
    end
  end

  context 'code_1 account' do
    describe 'create code_1 account', :chrome do
      include_examples 'login as', :auto_financer
      it 'fill code_1 fields' do
        find('#employee_accounts_screen a').send_keys :enter
        fill_in 'emp_id',      with: code_1.employee_id
        fill_in 'first_name',  with: code_1.first_name
        fill_in 'last_name',   with: code_1.last_name
        fill_in 'designation', with: code_1.designation
        fill_in 'department',  with: code_1.department
        fill_in 'email',       with: code_1.email
        find('select option[value=User]').select_option
        find('input[value="CREATE"]').send_keys :enter
      end

      # [Question] User are created in the middle of table list (at second position - little weird)
      # I have automated it for 1-st position (like when creating financer account)
      # If it is correct behavior I will change logic
      it { expect(all('td.role')[1].text).to           eq 'User' }
      it { expect(all('td.emp_id')[1].text).to         eq code_1.employee_id }
      it { expect(all('td.name')[1].text).to           eq code_1.first_name + ' ' + code_1.last_name }
      it { expect(all('td.designation')[1].text).to    eq code_1.designation }
      it { expect(all('td.department')[1].text).to     eq code_1.department }
      it { expect(all('td.email')[1].text).to          eq code_1.email }

      include_examples 'sign out'
    end

    describe 'sign up as code_1 account', :chrome do
      include_examples 'sign up as', :auto_code_1, code: :code1
      include_examples 'check sign up successfully'
      include_examples 'check welcome message'
      include_examples 'sign out'
    end

    describe 'login as code_1', :chrome do
      it 'fill email' do
        fill_in 'email', with: code_1.email
        sleep(0.5)
      end

      include_examples 'check plan', disabled: :individual, checked: :company

      it 'fill password & Go' do
        fill_in 'password', with: code_1.password
        find('[value=Go]').send_keys :enter
      end
      include_examples 'check sign in successfully'
      include_examples 'check navigation items', 'Home', 'Submit', 'Storage (0)',
                       'My Claims', 'Employees\' Claim (0)', 'Sign Out'
      include_examples 'sign out'
    end
  end

  context 'user account' do
    describe 'sign up as user account ', :chrome do
      include_examples 'sign up as', :auto_user
      include_examples 'check sign up successfully'
      include_examples 'check welcome message'
      include_examples 'sign out'
    end

    describe 'login as user', :chrome do
      it 'fill email' do
        fill_in 'email', with: user.email
        sleep(0.5)
      end

      include_examples 'check plan', disabled: :company, checked: :individual

      it 'fill password & Go' do
        fill_in 'password', with: user.password
        find('[value=Go]').send_keys :enter
      end
      include_examples 'check sign in successfully'
      include_examples 'check navigation items', 'Home', 'Submit',
                       'Storage (0)', 'My Claims', 'Sign Out'
      include_examples 'sign out'
    end
  end

  context 'duplicate user' do
    describe 'sign up as duplicate user', :chrome do
      include_examples 'sign up as', :auto_user
      include_examples 'check review errors message'
      it 'check warning message ' do
        expect(find('.user-form')).to be_visible
      end
    end
  end
end

feature_helper:

require 'capybara/rspec'
require 'capybara/poltergeist'

require './spec/support/helpers/feature_helper'
require './spec/support/shared_examples/sign_in_examples'
require './spec/support/shared_examples/sign_up_examples'
require './spec/support/shared_examples/main_page_examples'

# Configure Capybara
Capybara.register_driver :chrome do |app|
  Capybara::Selenium::Driver.new(app, :browser => :chrome)
end
Capybara.default_driver = :poltergeist
Capybara.javascript_driver = :poltergeist
Capybara.current_driver = :chrome
Capybara.app_host = 'http://0.0.0.0:3000/'
Capybara.exact = true

RSpec.configure do |config|
  config.expect_with :rspec do |expectations|
    expectations.include_chain_clauses_in_custom_matcher_descriptions = true
    config.include Capybara::DSL, :type => :request
  end

  config.mock_with :rspec do |mocks|
    mocks.verify_partial_doubles = true
  end
end

support/feature_helper.rb

require 'capybara/dsl'

module GUI
  extend Capybara::DSL

  class << self
    def login_as(user)
      binding.pry
      user = FactoryGirl.build(:account, user)
      find('a', text: 'Sign In').send_keys :enter
      fill_in 'email',    with: user.email
      fill_in 'password', with: user.password
      find('[value=Go]').send_keys :enter
    end

    def sign_out
      binding.pry
      find('a', text: 'Sign Out').send_keys :enter
    end
  end
end

Gemfile: group :development, :test do gem 'dotenv-rails' gem 'pry-rails' gem 'byebug' gem 'factory_girl_rails' gem 'rspec-rails' gem 'chromedriver-helper' end

group :test do
  gem 'capybara'
  gem 'selenium-webdriver'
  gem 'poltergeist'
  gem 'codeclimate-test-reporter', require: false
  gem 'database_cleaner'
  gem 'simplecov', require: false # Test Coverage analytics
  gem 'shoulda-matchers', '~> 3.1'
  gem 'webmock' # Mocking http request
  gem 'terminal-notifier-guard' # for OSX
  gem 'rspec-steps'
end

If I write all the expect in on it block it works fine.

Thanks in advance.

1

1 Answers

2
votes

The issue for this specific question is that your visit call is in the wrong place, but your bigger overall issue is that you're writing your feature tests like unit tests.

Every it block is a separate test, and assuming you're using the standard Capybara rspec integration one of the last things done is to visit about:blank. This will occur after your after :all block. Because of this the visit of the page you're testing should occur either in your before :all block or in the individual tests themselves. Additionally, since the DB is/should be reset between each test (it/scenario block) signing out isn't usually necessary.

before :all do
  visit '/' # Alternatively you could move this to your login_as method
  GUI.login_as :auto_admin
  find('#employer_model_screen a').send_keys :enter
end

# Not generally necessary for tests of the type you show
# after :all do
#   GUI.sign_out
#   visit '/'
# end

Now, the bigger issue is that you're testing a whole "feature" yet testing for a single visual element in each test. This means that to see if the company name is shown it has to create a company, create a user, have a browser visit a page, then login, then check the name. Next it wants to check country type so it has to again create a company, create a user, have a browser visit the same page, then login, then check the country type. If you continue writing your feature tests like that they're very quickly going to take hours if not days to run. If the purpose of your check is that all the company info is shown then it should be one it/scenario

it "shows the company info" do
  expect(page).to have_css('td.name'.text: company.name)
  expect(page).to have_css('td.workflow-type', text: company.workflow_type)
  ...
end

Note also the use of the capybara provided matchers, rather than .text with eq, which will make your tests a lot more stable once you start having ajax/asynchronous actions and page updates since it provide waiting/retrying behavior to the checks. (You should also stay away from all/first whenever possible since they have severe limitations on dynamic pages)