SurfCustomCalabash 0.2.0 → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +11 -0
  3. data/README.md +68 -4
  4. data/SurfCustomCalabash.gemspec +3 -3
  5. data/bin/SurfCustomCalabash +54 -0
  6. data/bin/surf-calabash-console.rb +62 -0
  7. data/bin/surf-calabash-gen.rb +17 -0
  8. data/bin/surf-calabash-helpers.rb +34 -0
  9. data/lib/SurfCustomCalabash/CommonMethods.rb +3 -3
  10. data/lib/SurfCustomCalabash/DroidMethods.rb +2 -1
  11. data/lib/SurfCustomCalabash/IosMethods.rb +2 -2
  12. data/lib/SurfCustomCalabash/version.rb +1 -1
  13. data/sources/Backdoors list b/data/sources/Backdoors → list +0 -0
  14. data/sources/Gemfile +27 -0
  15. data/sources/Scripts/and.sh +5 -0
  16. data/sources/Scripts/ca.sh +5 -0
  17. data/sources/Scripts/ci.sh +5 -0
  18. data/sources/Scripts/data +7 -0
  19. data/sources/Scripts/fa.sh +6 -0
  20. data/sources/Scripts/fi.sh +5 -0
  21. data/sources/Scripts/get_apk.rb +68 -0
  22. data/sources/Scripts/get_scenarios.rb +193 -0
  23. data/sources/Scripts/import_scenarios.rb +172 -0
  24. data/sources/Scripts/ios.sh +5 -0
  25. data/sources/Scripts/parallel_android_smoke.sh +4 -0
  26. data/sources/Scripts/parallel_android_test.sh +4 -0
  27. data/sources/Scripts/ra.sh +12 -0
  28. data/sources/Scripts/ri.sh +9 -0
  29. data/sources/Scripts/smoke_and.sh +5 -0
  30. data/sources/Scripts/smoke_ios.sh +5 -0
  31. data/sources/Scripts/ta.sh +5 -0
  32. data/sources/Scripts/ti.sh +5 -0
  33. data/sources/Scripts/to_exec.sh +19 -0
  34. data/sources/Scripts/update.sh +24 -0
  35. data/sources/Scripts/update_exec.rb +96 -0
  36. data/sources/TestFolder/small.gif +0 -0
  37. data/sources/ci/JenkinsfileUiTestAndroid.groovy +22 -0
  38. data/sources/ci/JenkinsfileUiTestIos.groovy +23 -0
  39. data/sources/config/cucumber.yml +24 -0
  40. data/sources/features/android/pages/standard/DroidCommon.rb +33 -0
  41. data/sources/features/android/pages/standard/Init_android.rb +8 -0
  42. data/sources/features/android/pages/test.rb +43 -0
  43. data/sources/features/android/support/app_life_cycle_hooks.rb +147 -0
  44. data/sources/features/android/support/log_hooks_and.rb +40 -0
  45. data/sources/features/android/support/video_hooks_and.rb +110 -0
  46. data/sources/features/ios/pages/standard/Init_ios.rb +5 -0
  47. data/sources/features/ios/pages/standard/IosCommon.rb +30 -0
  48. data/sources/features/ios/pages/test.rb +37 -0
  49. data/sources/features/ios/support/01_launch.rb +194 -0
  50. data/sources/features/ios/support/log_hooks_ios.rb +40 -0
  51. data/sources/features/ios/support/video_hooks_ios.rb +58 -0
  52. data/sources/features/net/net.rb +28 -0
  53. data/sources/features/net/screentest_api.rb +186 -0
  54. data/sources/features/scenarios/eng.feature +8 -0
  55. data/sources/features/scenarios/rus.feature +8 -0
  56. data/sources/features/step_definitions/test.rb +43 -0
  57. data/sources/features/support/credentials.rb +11 -0
  58. data/sources/features/support/env.rb +8 -0
  59. data/sources/features/support/hooks.rb +21 -0
  60. data/sources/features/support/localization.rb +8 -0
  61. data/sources/find_id.rb +95 -0
  62. data/sources/group_steps.rb +39 -0
  63. data/sources/irbrcs/android/irbrc +105 -0
  64. data/sources/irbrcs/ios/irbrc +132 -0
  65. data/sources/start.sh +134 -0
  66. metadata +63 -6
  67. data/bin/console +0 -14
  68. data/bin/setup +0 -8
@@ -0,0 +1,24 @@
1
+ #!/usr/bin/env bash
2
+
3
+ echo "введите название фича файла с обновленными тестами из папки features/scenarios/name.feature в формате <name>"
4
+ echo "enter feature file name with updated tests from dir features/scenarios/name.feature in format <name>"
5
+
6
+ read path
7
+
8
+ index=0
9
+ while read line; do
10
+ array[$index]="$line"
11
+ index=$(($index+1))
12
+ done < ./Scripts/data
13
+
14
+ first_string="${array[0]}"
15
+ username=${first_string/login /}
16
+
17
+ second_string="${array[1]}"
18
+ password=${second_string/jira_pass /}
19
+
20
+ third_string="${array[2]}"
21
+ code=${third_string/project_key /}
22
+
23
+
24
+ curl -H "Content-Type: multipart/form-data" -u $username:$password -F "file=@features/scenarios/$path.feature" https://jira.surfstudio.ru/rest/raven/1.0/import/feature?projectKey=$code
@@ -0,0 +1,96 @@
1
+ require 'rest-client'
2
+ require 'json'
3
+ require 'base64'
4
+
5
+
6
+ class Execution
7
+
8
+ # path - path to dir with autotests, пример - /Users/user_name/autotests/project-test/
9
+ def initialize(path)
10
+
11
+ # hash with data from file scripts/data
12
+ @all_data = get_all_data
13
+
14
+ # login in jira
15
+ @login = @all_data['login']
16
+
17
+ # pass in jira
18
+ @password = @all_data['jira_pass']
19
+
20
+ # project key
21
+ @key = @all_data['project_key']
22
+
23
+ # path to dir with autotests
24
+ @path = path
25
+
26
+ @auth = 'Basic ' + Base64.encode64( "#{@login}:#{@password}" ).chomp
27
+ end
28
+
29
+ attr_accessor :path
30
+
31
+ # read user data from file
32
+ def get_all_data
33
+ Hash[*File.read("#{@path}scripts/data").split(/[, \n]+/)]
34
+ end
35
+
36
+ def get_test_execution(test_exec)
37
+
38
+ key_arr = []
39
+
40
+ for i in 1..2
41
+ url = "https://jira.surfstudio.ru/rest/raven/1.0/api/testexec/#{test_exec}/test?page=#{i}"
42
+
43
+ response = RestClient.get url, {:Authorization => @auth}
44
+ # Kernel.puts(response)
45
+ parse_response = JSON.parse(response.body)
46
+
47
+ # Kernel.puts(parse_response)
48
+
49
+ parse_response.each do |keys|
50
+ key_arr << keys['key']
51
+ end
52
+ end
53
+
54
+ Kernel.puts(key_arr.sort)
55
+
56
+ $test_keys = key_arr.sort
57
+ end
58
+
59
+
60
+ def delete_test_from_execution(test_exec)
61
+
62
+ p "Start Delete"
63
+ # begin
64
+ url = "https://jira.surfstudio.ru/rest/raven/1.0/api/testexec/#{test_exec}/test"
65
+ response = RestClient.post url, {:remove => $test_keys}.to_json,
66
+ {:Authorization => @auth,
67
+ content_type: :json,
68
+ accept: :json}
69
+ end
70
+
71
+ def add_test_to_execution(test_exec)
72
+
73
+ p "Start Update"
74
+
75
+ url = "https://jira.surfstudio.ru/rest/raven/1.0/api/testexec/#{test_exec}/test"
76
+ response = RestClient.post url, {:add => $test_keys}.to_json,
77
+ {:Authorization => @auth,
78
+ content_type: :json,
79
+ accept: :json}
80
+
81
+ end
82
+
83
+ def update_test_execution(test_exec)
84
+ get_test_execution(test_exec)
85
+ begin
86
+ delete_test_from_execution(test_exec)
87
+ rescue
88
+ p "Timeout error"
89
+ p "Retrying Attempt"
90
+ delete_test_from_execution(test_exec)
91
+ end
92
+
93
+ add_test_to_execution(test_exec)
94
+ end
95
+
96
+ end
@@ -0,0 +1,22 @@
1
+ @Library('surf-lib@version-3.0.0-SNAPSHOT') // https://bitbucket.org/surfstudio/jenkins-pipeline-lib/
2
+ import ru.surfstudio.ci.pipeline.ui_test.UiTestPipelineAndroid
3
+
4
+ //init
5
+ def pipeline = new UiTestPipelineAndroid(this)
6
+ pipeline.init()
7
+
8
+ //configuration
9
+ pipeline.sourceRepoUrl = "TODO add repo source code app"
10
+ pipeline.jiraProjectKey = "TODO add key project in jira"
11
+ pipeline.testBranch = "master" // branch with tests
12
+ pipeline.defaultTaskKey = "TODO add key test execution in jira" //task for run periodically
13
+ pipeline.projectForBuild = “TODO add name project for build in jenkins”
14
+
15
+
16
+ //customization
17
+ pipeline.cronTimeTrigger = "00 02 * * *"
18
+ pipeline.notificationEnabled = false
19
+ pipeline.buildGradleTask = "clean assembleQa"
20
+
21
+ //run
22
+ pipeline.run()
@@ -0,0 +1,23 @@
1
+ @Library('surf-lib@version-3.0.0-SNAPSHOT') // https://bitbucket.org/surfstudio/jenkins-pipeline-lib/
2
+ import ru.surfstudio.ci.pipeline.ui_test.UiTestPipelineiOS
3
+
4
+ //init
5
+ def pipeline = new UiTestPipelineiOS(this)
6
+ pipeline.init()
7
+
8
+ //configuration
9
+ pipeline.sourceRepoUrl = "TODO add repo source code app"
10
+ pipeline.jiraProjectKey = "TODO add key project in jira"
11
+ pipeline.testBranch = "master" // branch with tests
12
+ pipeline.defaultTaskKey = "TODO add key test execution in jira" //task for run periodically
13
+ pipeline.testDeviceName = "iPhone 11"
14
+ pipeline.testOSVersion = "com.apple.CoreSimulator.SimRuntime.iOS-13-3"
15
+ pipeline.testiOSSDK = "iphonesimulator13.2"
16
+ pipeline.projectForBuild = "test"
17
+
18
+ //customization
19
+ pipeline.cronTimeTrigger = "01 04 * * *"
20
+ pipeline.notificationEnabled = false
21
+
22
+ //run
23
+ pipeline.run()
@@ -0,0 +1,24 @@
1
+ # config/cucumber.yml
2
+ ##YAML Template
3
+
4
+ android: PLATFORM=android -r features/support -r features/android/support -r features/android -r features/step_definitions -r features/android/pages -r features/android/pages/standard
5
+ ios: PLATFORM=ios -r features/support -r features/ios/support -r features/step_definitions -r features/ios/pages
6
+ <%
7
+ date = Time.now.strftime('%d_%m-%H:%M:%S')
8
+ default_report = "./output_#{date}_.html"
9
+ default_json = "./output_#{date}.json"
10
+ default_allure = "./output_#{date}.html"
11
+ default_rerun = "./rerun_#{date}.txt"
12
+ %>
13
+
14
+ common: NO_STOP='1'
15
+ rerun_out: -f rerun -o ./reports/<%= default_rerun %>
16
+ html_report: -f html -o ./reports/<%= default_report %>
17
+ json_report: -f json -o ./reports/<%= ENV['DEVICE_INFO']%>.json
18
+ json_xray: -f json -o ./reports/<%= ENV['DEVICE_INFO']%>_<%= ENV['ADB_DEVICE_ARG']%>.json
19
+
20
+
21
+ run: -p common -p rerun_out -p html_report -p json_report -p allure_report -p json_xray
22
+
23
+
24
+
@@ -0,0 +1,33 @@
1
+ require 'calabash-android'
2
+ require 'SurfCustomCalabash/DroidMethods'
3
+
4
+ class DroidCommon
5
+
6
+ # system methods
7
+ def initialize(driver)
8
+ @driver = driver
9
+ end
10
+
11
+ def method_missing (sym, *args, &block)
12
+ @driver.send sym, *args, &block
13
+ end
14
+
15
+ def self.element(name, &block)
16
+ define_method(name.to_s, &block)
17
+ end
18
+
19
+ class << self
20
+ alias :value :element
21
+ alias :action :element
22
+ alias :trait :element
23
+ end
24
+
25
+ # custom methods
26
+ def go_back
27
+ sleep(1.5)
28
+ press_back_button
29
+ sleep(1)
30
+ end
31
+
32
+ end
33
+
@@ -0,0 +1,8 @@
1
+ require_relative 'DroidCommon'
2
+
3
+ def init_android
4
+ $test = Test.new(self)
5
+ # write here creating new class instances like example above this line
6
+ end
7
+
8
+
@@ -0,0 +1,43 @@
1
+ require_relative 'standard/DroidCommon.rb'
2
+ # all screens your application screens should be like this. Inheritance from DroidCommon is essential!
3
+
4
+ class Test < DroidCommon
5
+ def initialize(driver)
6
+
7
+ @driver = driver
8
+
9
+ ##### elements on the screen #######
10
+
11
+ # elements locators and their x-platform nickname should be like that
12
+
13
+ @trait = "* id:'feed_rv'"
14
+
15
+ @auth_field = "* id:'auth_fld'"
16
+
17
+ @main_ok_button = "* id:'feed_vote_tutorial_go_btn'"
18
+
19
+ end
20
+
21
+ # all elements above should have getter for mention them from step definitions
22
+ attr_reader *Test.new(self).instance_variables.map {|s| s[1..-1]}
23
+
24
+ # another way to describe elements
25
+
26
+ def tape
27
+ "* id:'feed_rv'"
28
+ end
29
+
30
+ #### methods ###########
31
+
32
+ def authorize(data)
33
+ tap_on(@auth_field)
34
+ wait_for_keyboard
35
+ enter_text(data)
36
+ end
37
+
38
+ def test
39
+ tap_on(@main_ok_button)
40
+ end
41
+
42
+ end
43
+
@@ -0,0 +1,147 @@
1
+ require 'calabash-android/operations'
2
+ require 'calabash-android/management/app_installation'
3
+ require 'calabash-android/cucumber'
4
+ require 'cucumber'
5
+ require 'json'
6
+ require_relative '../../../features/net/screentest_api'
7
+ require 'fileutils'
8
+
9
+ Before do |scenario|
10
+
11
+ ENV['SCREENSHOT_PATH'] = './reports/'
12
+
13
+ @scenario_name = scenario.name
14
+
15
+ @start_record = true
16
+ @start_log = true
17
+
18
+ scenario_tags = scenario.source_tag_names
19
+
20
+ reinstall_apps if scenario_tags.include?('@reinstall')
21
+
22
+ clear_app_data if scenario_tags.include?('@clear')
23
+
24
+ skip_this_scenario('Сценарий только для iOS') if scenario_tags.include?('@skip')
25
+
26
+ if scenario_tags.include?('@screentest')
27
+ clear_file_with_stack_trace
28
+ create_feature(@scenario_name)
29
+ end
30
+
31
+ @start_record = true if scenario_tags.include?('@record')
32
+
33
+ start_test_server_in_background
34
+
35
+ @video_capture = nil
36
+
37
+ # start video record
38
+ if @start_record
39
+ @video_capture = AndroidVideoCapture.new
40
+ @video_capture.start_capture
41
+ @need_convert = false
42
+ # set video quality: low, medium, high
43
+ @video_capture.quality = "low"
44
+ end
45
+
46
+ @write_log = nil
47
+
48
+ # start write logs
49
+ if @start_log
50
+ @write_log = AndroidLogs.new
51
+ @write_log.start_log
52
+ end
53
+ end
54
+
55
+ def file_name(ext)
56
+ "android_#{Time.now.strftime('%d_%m-%H:%M:%S')}.#{ext}"
57
+ end
58
+
59
+ def create_folder
60
+ model = %x(adb devices -l | awk 'NR==2{print $5}')
61
+ model.slice! "model:"
62
+
63
+ @path = "#{ENV['SCREENSHOT_PATH']}#{@scenario_name}_#{model}_#{Time.now.strftime('%d_%m-%H:%M:%S')}/"
64
+ # Dir.mkdir(@path) unless File.directory?(@path)
65
+ FileUtils.mkdir_p @path
66
+ end
67
+
68
+ def convert
69
+ convert_file = "video_#{file_name('mp4')}"
70
+ @video_capture.convert_video(@video_capture.video_file, convert_file)
71
+ delete_file(@video_capture.video_file)
72
+ @video_capture.video_file = convert_file
73
+ end
74
+
75
+ def embed_video
76
+ unless @video_capture.nil?
77
+ @video_capture.acquire_capture
78
+ if File.exist?(@video_capture.video_file)
79
+ convert if @need_convert
80
+ embed(@video_capture.video_file, 'video/mp4', "video #{@video_capture.video_file}")
81
+ FileUtils.mv(@video_capture.video_file, @path)
82
+ @video_capture.video_file = @path + @video_capture.video_file
83
+ end
84
+ end
85
+ end
86
+
87
+ def delete_file(file_name)
88
+ if File.exist?(file_name)
89
+ File.delete(file_name)
90
+ end
91
+ end
92
+
93
+ def embed_logs
94
+ unless @write_log.nil?
95
+ if File.exist?(@write_log.log_file)
96
+ embed(@write_log.log_file, 'log/txt', "log #{@write_log.log_file}")
97
+ FileUtils.mv(@write_log.log_file, @path)
98
+ end
99
+ end
100
+ end
101
+
102
+ After do |scenario|
103
+
104
+ @video_capture.stop_capture unless @video_capture.nil?
105
+
106
+ @write_log.stop_log unless @write_log.nil?
107
+
108
+ scenario_tags = scenario.source_tag_names
109
+
110
+ if scenario_tags.include?('@record') && scenario.passed?
111
+ create_folder
112
+ embed_video
113
+ elsif scenario.passed?
114
+ @video_capture.dispose_capture unless @video_capture.nil?
115
+ delete_file(@write_log.log_file) unless @write_log.nil?
116
+ delete_file(@video_capture.video_file) unless @video_capture.nil?
117
+ end
118
+
119
+ if scenario.failed?
120
+
121
+ create_folder
122
+
123
+ mark_feature_as_not_finished if scenario.source_tag_names.include?('@screentest')
124
+
125
+ pretty = JSON.pretty_generate(query("*"))
126
+ parsed = JSON.parse(pretty)
127
+
128
+ for i in 0..query("*").count-1
129
+ id = parsed[i]['id'].to_s
130
+ text = parsed[i]['text'].to_s
131
+ if id != ''
132
+ File.open("#{@path}id_#{file_name('txt')}", 'a', crlf_newline: true) { |f| f.puts(id.encode(crlf_newline: true))}
133
+ end
134
+ if text != ''
135
+ File.open("#{@path}text_#{file_name('txt')}", 'a', crlf_newline: true) { |f| f.puts(text.encode(crlf_newline: true))}
136
+ end
137
+ end
138
+
139
+ screenshot(prefix: @path, name: "#{file_name('png')}")
140
+ embed_video
141
+ embed_logs
142
+ end
143
+
144
+ send_video(@video_capture.video_file) if scenario.source_tag_names.include?('@record')
145
+ shutdown_test_server
146
+
147
+ end
@@ -0,0 +1,40 @@
1
+ require 'open3'
2
+ require 'timeout'
3
+ require 'process'
4
+ require 'calabash-android/operations'
5
+ require 'calabash-android/env'
6
+
7
+ def adb_command
8
+ "\"#{Calabash::Android::Dependencies.adb_path}\""
9
+ end
10
+
11
+ class AndroidLogs
12
+
13
+ def initialize
14
+ @log_file = "#{ENV['SCREENSHOT_PATH']}log_#{Time.now.strftime('%d_%m-%H:%M:%S')}.txt"
15
+ end
16
+
17
+ attr_reader :log_file
18
+
19
+ def start_log
20
+ package = package_name('L.apk')
21
+ pid_app = %x{adb shell ps | grep #{package} | tr -s [:space:] ' ' | cut -d' ' -f2}
22
+ @logcat = Open3.popen2e("adb logcat | grep #{pid_app}")
23
+ @pid = @logcat[2].pid
24
+ end
25
+
26
+ def stop_log
27
+ %x{ps | grep logcat | grep -v grep | cut -d' ' -f1 | awk '{print $1}' | xargs kill -2}
28
+
29
+ begin
30
+ Timeout.timeout(30) { File.open(@log_file, 'w') { |f| f << @logcat[1].readlines.join("\n") } }
31
+ rescue Timeout::Error
32
+ Kernel.puts("Error write log file")
33
+ @logcat[0].close
34
+ @logcat[1].close
35
+ end
36
+
37
+ @logcat[0].close
38
+ @logcat[1].close
39
+ end
40
+ end