What are some tips and tricks for setting up CI with a React Native project, including how integration testing, probably with Appium.
Tips
- Accessibility labels are your friends and critically needed for image/icon buttons.
- You might have to use xpath if there’s no accessibility label. The appium inspector is particularly useful for this.
- The ruby console is also great for testing out the command to get appium objects. You can use
binding.pry
in your tests.
Setup
- Install appium per the instructions at appium.io.
- Add appium files to your react-native project, per the below example.
/test/appium/spec_helper.rb
require 'rspec'
require 'appium_lib'
SPEC_ROOT = File.expand_path(File.dirname(__FILE__))
Dir[File.expand_path('support/**/*.rb', SPEC_ROOT)].each { |f| require f }
app_path = '../../ios/build/Build/Products/Debug-iphonesimulator/SpylightApp.app'
RSpec.configure do |config|
config.include ::Screenshot
config.include ::Helpers
config.before(:suite) do
driver_caps = {
platformName: 'iOS',
versionNumber: '9.3',
deviceName: 'iPhone 6s',
newCommandTimeout: 9999,
app: app_path
}
Appium::Driver.new(caps: driver_caps).start_driver
Appium.promote_appium_methods RSpec::Core::ExampleGroup
end
config.after(:suite) do
$driver.driver_quit
end
end
/test/appium/Gemfile
source 'https://www.rubygems.org'
gem 'appium_lib', '~> 6.0.0'
gem 'rspec'
/tests/appium/features/login_spec.rb
require './spec_helper'
describe 'Login' do
it 'User logs in' do
find('Log in').click
find_by_accessibility_label('Email').click
textfields[0].type 'somebody@email.com'
textfields[1].type 'wrongpass'
find_by_accessibility_label('FORWARD').click
alert = driver.switch_to.alert
expect(alert.text).to include('Invalid username or password. Please try again.')
alert_accept
textfields[1].type 'password'
find_by_accessibility_label('FORWARD').click
# some_reference_on_next_screen is a helper in /test/appium/support to find some screen object
expect(some_reference_on_next_screen).not_to be_nil
end
end
/test/appium/support/screenshot.rb
Example of the kind of file you can put in the /test/appium/support
directory, from github.
require 'fileutils'
module Screenshot
module_function
## Usage:
# capture_screenshot => #{screenshot_dir}/img_1.png
# capture_screenshot(prefix: 'foo') => #{screenshot_dir}/foo_img_2.png
def capture_screenshot(prefix: nil)
img_name = "img_#{screenshot_count}.png"
img_name = "#{prefix}_#{img_name}" unless prefix.nil?
img_path = File.join(screenshot_dir, img_name)
begin
$driver.driver.save_screenshot(img_path)
@@screenshot_count += 1
rescue => e
$stderr.puts "saving screenshot failed #{e.message}"
end
img_path
end
def screenshot_count
@@screenshot_count ||= 1
end
def screenshot_dir
@@screenshot_dir ||= File.join(Bundler.root, 'screenshots', Time.now.strftime('%Y%m%d-%H%M%S')).tap do |dirname|
FileUtils.mkdir_p dirname
end
end