testcentricity 2.3.13 → 2.3.14

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 97150cfd69ebee4848af8b0d2d9cf37e5ca816aa
4
- data.tar.gz: 78104785082fbdc52d40793fc9bf1bb9199004c9
3
+ metadata.gz: 57c238014ed1bde365574c49dfd63c8e9716ea5e
4
+ data.tar.gz: a6bbe0079660a63178e943152ebac311c710f9f5
5
5
  SHA512:
6
- metadata.gz: 904ae29d561d67a8917ff72520ce10b9743d323edf934603dc744e6259280439c939dd6700a90229cbfba533276f25568681a3d02b30217c4655682ccb6489ff
7
- data.tar.gz: 080dec95c5a11b14bd53926ef039c3c412f70b65e11c5efe4382e9c65392b66b25077e309d0a3f4c1a078ffcc28017135e3c0879188bad28d56a0377f60b9d11
6
+ metadata.gz: 0f758a336d3f13a2257a7661160f2019725b98ec108146e9ec2b4c3ae540608721d246ac0b4c559f227234aae2238815b9a08f11ebeb2ac637fed6530e17222e
7
+ data.tar.gz: d06d2ffca2e97581347f713eefe91b5ed177ba350419c85f3b75dc549c04a507dd5da982db3f1e3800567df1adc42aa5d56f4112a921c5442f546e57147b6f9f
data/README.md CHANGED
@@ -28,6 +28,10 @@ hosted instances of Chrome, Firefox, Safari, and IE web browsers.
28
28
 
29
29
 
30
30
  ## What's New
31
+ ###Version 2.3.14
32
+
33
+ * Updated device profiles for iPhone 7 (iOS 10) with MS Edge browser.
34
+
31
35
  ###Version 2.3.13
32
36
 
33
37
  * Added `AppiumServer.start`, `AppiumServer.running?`, and `AppiumServer.stop` methods for starting and stopping the Appium Server prior to executing tests on
@@ -77,7 +77,7 @@
77
77
  :css_width: 375
78
78
  :css_height: 667
79
79
  :default_orientation: portrait
80
- :user_agent: "Mozilla/5.0 (iPhone; CPU iPhone OS 10_3_3 like Mac OS X) AppleWebKit/603.3.8 (KHTML, like Gecko) Version/10.0 EdgiOS/41.9.0.0 Mobile/14G60 Safari/603.3.8"
80
+ :user_agent: "Mozilla/5.0 (iPhone; CPU iPhone OS 10_3_3 like Mac OS X) AppleWebKit/603.3.8 (KHTML, like Gecko) Version/10.0 EdgiOS/41.10.1.0 Mobile/14G60 Safari/603.3.8"
81
81
  :iphone8:
82
82
  :name: "iPhone 8"
83
83
  :os: ios
@@ -52,6 +52,8 @@ require 'testcentricity/app_elements/label'
52
52
  require 'testcentricity/app_elements/switch'
53
53
  require 'testcentricity/app_elements/textfield'
54
54
  require 'testcentricity/app_elements/list'
55
+ require 'testcentricity/app_elements/image'
56
+ require 'testcentricity/app_elements/alert'
55
57
 
56
58
 
57
59
  module TestCentricity
@@ -80,6 +80,8 @@ module TestCentricity
80
80
  @running = true
81
81
  Appium.promote_appium_methods TestCentricity::ScreenObject
82
82
  Appium.promote_appium_methods TestCentricity::AppUIElement
83
+
84
+ Environ.screen_size = $driver.window_size
83
85
  end
84
86
 
85
87
  def self.quit_driver
@@ -134,6 +136,10 @@ module TestCentricity
134
136
  $driver.is_keyboard_shown
135
137
  end
136
138
 
139
+ def self.set_orientation(orientation)
140
+ $driver.rotation = orientation.downcase.to_sym
141
+ end
142
+
137
143
  def self.set_geolocation(latitude, longitude, altitude)
138
144
  $driver.set_location(latitude, longitude, altitude)
139
145
  end
@@ -149,6 +155,23 @@ module TestCentricity
149
155
  def self.available_contexts
150
156
  $driver.available_contexts
151
157
  end
158
+
159
+ def self.default_context
160
+ $driver.switch_to_default_context
161
+ end
162
+
163
+ def self.is_webview?
164
+ $driver.current_context.start_with?('WEBVIEW')
165
+ end
166
+
167
+ def self.is_native_app?
168
+ $driver.current_context.start_with?('NATIVE_APP')
169
+ end
170
+
171
+ def self.webview_context
172
+ contexts = available_contexts
173
+ set_context(contexts[1])
174
+ end
152
175
  end
153
176
  end
154
177
 
@@ -4,50 +4,112 @@ module TestCentricity
4
4
  class ScreenObject
5
5
  include Test::Unit::Assertions
6
6
 
7
- attr_reader :strategy, :locator
7
+ attr_reader :locator
8
8
 
9
9
  def initialize
10
- raise "Screen object #{self.class.name} does not have a page_locator trait defined" unless defined?(page_locator)
11
- @strategy = page_locator[0].to_sym
12
- @locator = page_locator[1]
10
+ raise "Screen object #{self.class.name} does not have a page_name trait defined" unless defined?(page_name)
11
+ @locator = page_locator if defined?(page_locator)
13
12
  end
14
13
 
15
14
  def self.trait(trait_name, &block)
16
15
  define_method(trait_name.to_s, &block)
17
16
  end
18
17
 
19
- def self.element(element_name, strategy, locator)
20
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppUIElement.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
18
+ def self.element(element_name, locator)
19
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppUIElement.new("#{element_name}", self, #{locator}, :page);end))
21
20
  end
22
21
 
23
- def self.button(element_name, strategy, locator)
24
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppButton.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
22
+ def self.elements(element_hash)
23
+ element_hash.each do |element_name, locator|
24
+ element(element_name, locator)
25
+ end
26
+ end
27
+
28
+ def self.button(element_name, locator)
29
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppButton.new("#{element_name}", self, #{locator}, :page);end))
25
30
  end
26
31
 
27
- def self.textfield(element_name, strategy, locator)
28
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppTextField.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
32
+ def self.buttons(element_hash)
33
+ element_hash.each do |element_name, locator|
34
+ button(element_name, locator)
35
+ end
29
36
  end
30
37
 
31
- def self.switch(element_name, strategy, locator)
32
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppSwitch.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
38
+ def self.textfield(element_name, locator)
39
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppTextField.new("#{element_name}", self, #{locator}, :page);end))
33
40
  end
34
41
 
35
- def self.checkbox(element_name, strategy, locator)
36
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppCheckBox.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
42
+ def self.textfields(element_hash)
43
+ element_hash.each do |element_name, locator|
44
+ textfield(element_name, locator)
45
+ end
37
46
  end
38
47
 
39
- def self.label(element_name, strategy, locator)
40
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppLabel.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
48
+ def self.switch(element_name, locator)
49
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppSwitch.new("#{element_name}", self, #{locator}, :page);end))
41
50
  end
42
51
 
43
- def self.list(element_name, strategy, locator)
44
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppList.new("#{element_name}", self, "#{strategy}", "#{locator}", :page);end))
52
+ def self.switches(element_hash)
53
+ element_hash.each do |element_name, locator|
54
+ switch(element_name, locator)
55
+ end
56
+ end
57
+
58
+ def self.checkbox(element_name, locator)
59
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppCheckBox.new("#{element_name}", self, #{locator}, :page);end))
60
+ end
61
+
62
+ def self.checkboxes(element_hash)
63
+ element_hash.each do |element_name, locator|
64
+ checkbox(element_name, locator)
65
+ end
66
+ end
67
+
68
+ def self.label(element_name, locator)
69
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppLabel.new("#{element_name}", self, #{locator}, :page);end))
70
+ end
71
+
72
+ def self.labels(element_hash)
73
+ element_hash.each do |element_name, locator|
74
+ label(element_name, locator)
75
+ end
76
+ end
77
+
78
+ def self.list(element_name, locator)
79
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppList.new("#{element_name}", self, #{locator}, :page);end))
80
+ end
81
+
82
+ def self.lists(element_hash)
83
+ element_hash.each do |element_name, locator|
84
+ list(element_name, locator)
85
+ end
86
+ end
87
+
88
+ def self.image(element_name, locator)
89
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppImage.new("#{element_name}", self, #{locator}, :page);end))
90
+ end
91
+
92
+ def self.images(element_hash)
93
+ element_hash.each do |element_name, locator|
94
+ image(element_name, locator)
95
+ end
96
+ end
97
+
98
+ def self.alert(element_name, locator)
99
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppAlert.new("#{element_name}", self, #{locator}, :page);end))
45
100
  end
46
101
 
47
102
  def self.section(section_name, class_name)
48
103
  class_eval(%(def #{section_name};@#{section_name} ||= #{class_name}.new("#{section_name}", self, :page);end))
49
104
  end
50
105
 
106
+ def self.sections(section_hash)
107
+ section_hash.each do |section_name, class_name|
108
+ section(section_name, class_name)
109
+ end
110
+ end
111
+
112
+
51
113
  def open_portal
52
114
  environment = Environ.current
53
115
 
@@ -56,10 +118,32 @@ module TestCentricity
56
118
 
57
119
  def verify_page_exists
58
120
  wait = Selenium::WebDriver::Wait.new(timeout: Environ.default_max_wait_time)
59
- wait.until { $driver.find_element(@strategy.to_sym, @locator).displayed? }
121
+ wait.until { exists? }
60
122
  PageManager.current_page = self
61
123
  rescue
62
- raise "Could not find page_locator for screen object '#{self.class.name}' (:#{@strategy}, #{@locator}) after #{Environ.default_max_wait_time} seconds"
124
+ raise "Could not find page_locator for screen object '#{self.class.name}' (#{@locator}) after #{Environ.default_max_wait_time} seconds"
125
+ end
126
+
127
+ def exists?
128
+ @locator.is_a?(Array) ? tries ||= 2 : tries ||= 1
129
+ if @locator.is_a?(Array)
130
+ loc = @locator[tries - 1]
131
+ find_element(loc.keys[0], loc.values[0])
132
+ else
133
+ find_element(@locator.keys[0], @locator.values[0])
134
+ end
135
+ true
136
+ rescue
137
+ retry if (tries -= 1) > 0
138
+ false
139
+ end
140
+
141
+ def wait_until_gone(seconds = nil)
142
+ timeout = seconds.nil? ? Environ.default_max_wait_time : seconds
143
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
144
+ wait.until { !exists? }
145
+ rescue
146
+ raise "Screen object #{self.class.name} remained visible after #{timeout} seconds" if exists?
63
147
  end
64
148
 
65
149
  def navigate_to; end
@@ -67,6 +151,7 @@ module TestCentricity
67
151
  def verify_page_ui; end
68
152
 
69
153
  def load_page
154
+ navigate_to unless exists?
70
155
  verify_page_exists
71
156
  PageManager.current_page = self
72
157
  end
@@ -77,10 +162,8 @@ module TestCentricity
77
162
  ui_states.each do |ui_object, object_states|
78
163
  object_states.each do |property, state|
79
164
 
80
-
81
165
  puts "#{ui_object.get_name} - #{property} = #{state}" if ENV['DEBUG']
82
166
 
83
-
84
167
  case property
85
168
  when :exists
86
169
  actual = ui_object.exists?
@@ -104,10 +187,22 @@ module TestCentricity
104
187
  actual = ui_object.tag_name
105
188
  when :placeholder
106
189
  actual = ui_object.get_placeholder
190
+ when :readonly
191
+ actual = ui_object.read_only?
192
+ when :maxlength
193
+ actual = ui_object.get_max_length
107
194
  when :items
108
195
  actual = ui_object.get_list_items
109
196
  when :itemcount
110
197
  actual = ui_object.get_item_count
198
+ when :width
199
+ actual = ui_object.width
200
+ when :height
201
+ actual = ui_object.height
202
+ when :x
203
+ actual = ui_object.x_loc
204
+ when :y
205
+ actual = ui_object.y_loc
111
206
  end
112
207
 
113
208
  if state.is_a?(Hash) && state.length == 1
@@ -7,7 +7,6 @@ module TestCentricity
7
7
  attr_reader :context, :name
8
8
  attr_accessor :locator
9
9
  attr_accessor :parent
10
- attr_accessor :strategy
11
10
  attr_accessor :parent_list
12
11
  attr_accessor :list_index
13
12
 
@@ -17,50 +16,31 @@ module TestCentricity
17
16
  @context = context
18
17
  @parent_list = nil
19
18
  @list_index = nil
20
- @strategy = nil
21
19
  @locator = nil
22
20
  end
23
21
 
24
22
  def get_locator
25
- if @locator.nil? && defined?(section_locator)
26
- @strategy = section_locator[0]
27
- @locator = section_locator[1]
28
- end
29
-
23
+ @locator = section_locator
30
24
  locators = []
31
25
  if @context == :section && !@parent.nil?
32
- parent_strategy, parent_locator = @parent.get_locator
26
+ locators.push(@parent.get_locator)
33
27
  end
34
28
 
35
29
  if @parent_list.nil?
36
- if parent_strategy == @strategy
37
- locators.push([@strategy, @locator])
38
- else
39
- locators.push([parent_strategy, parent_locator]) unless parent_strategy.nil?
40
- locators.push([@strategy, "#{parent_locator}#{@locator}"])
41
- end
30
+ locators.push(@locator)
42
31
  else
43
- list_strategy, list_locator = @parent_list.get_locator
44
- if parent_strategy == list_strategy
45
- list_locator = "#{parent_locator}#{list_locator}"
32
+ locators.push(@parent_list.get_locator)
33
+ if @list_index.nil?
34
+ locators.push(@locator)
46
35
  else
47
- locators.push([parent_strategy, parent_locator]) unless parent_strategy.nil?
36
+ list_key = @locator.keys[0]
37
+ list_value = "#{@locator.values[0]}[#{@list_index}]"
38
+ locators.push( { list_key => list_value } )
48
39
  end
49
- if list_strategy == @strategy
50
- obj_locator = "#{list_locator}#{@locator}"
51
- else
52
- obj_locator = @locator
53
- locators.push([list_strategy, list_locator])
54
- end
55
- unless @list_index.nil?
56
- obj_locator = "#{obj_locator}[#{@list_index}]"
57
- end
58
- locators.push([@strategy, obj_locator])
59
40
  end
60
41
  locators
61
42
  end
62
43
 
63
-
64
44
  def set_list_index(list, index = 1)
65
45
  @parent_list = list unless list.nil?
66
46
  @list_index = index
@@ -92,54 +72,114 @@ module TestCentricity
92
72
  @parent = parent
93
73
  end
94
74
 
95
-
96
75
  def self.trait(trait_name, &block)
97
76
  define_method(trait_name.to_s, &block)
98
77
  end
99
78
 
100
- def self.element(element_name, strategy, locator)
101
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppUIElement.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
79
+ def self.element(element_name, locator)
80
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppUIElement.new("#{element_name}", self, #{locator}, :section);end))
81
+ end
82
+
83
+ def self.elements(element_hash)
84
+ element_hash.each do |element_name, locator|
85
+ element(element_name, locator)
86
+ end
87
+ end
88
+
89
+ def self.button(element_name, locator)
90
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppButton.new("#{element_name}", self, #{locator}, :section);end))
91
+ end
92
+
93
+ def self.buttons(element_hash)
94
+ element_hash.each do |element_name, locator|
95
+ button(element_name, locator)
96
+ end
97
+ end
98
+
99
+ def self.textfield(element_name, locator)
100
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppTextField.new("#{element_name}", self, #{locator}, :section);end))
101
+ end
102
+
103
+ def self.textfields(element_hash)
104
+ element_hash.each do |element_name, locator|
105
+ textfield(element_name, locator)
106
+ end
107
+ end
108
+
109
+ def self.switch(element_name, locator)
110
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppSwitch.new("#{element_name}", self, #{locator}, :section);end))
111
+ end
112
+
113
+ def self.switches(element_hash)
114
+ element_hash.each do |element_name, locator|
115
+ switch(element_name, locator)
116
+ end
117
+ end
118
+
119
+ def self.checkbox(element_name, locator)
120
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppCheckBox.new("#{element_name}", self, #{locator}, :section);end))
121
+ end
122
+
123
+ def self.checkboxes(element_hash)
124
+ element_hash.each do |element_name, locator|
125
+ checkbox(element_name, locator)
126
+ end
127
+ end
128
+
129
+ def self.label(element_name, locator)
130
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppLabel.new("#{element_name}", self, #{locator}, :section);end))
102
131
  end
103
132
 
104
- def self.button(element_name, strategy, locator)
105
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppButton.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
133
+ def self.labels(element_hash)
134
+ element_hash.each do |element_name, locator|
135
+ label(element_name, locator)
136
+ end
106
137
  end
107
138
 
108
- def self.textfield(element_name, strategy, locator)
109
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppTextField.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
139
+ def self.list(element_name, locator)
140
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppList.new("#{element_name}", self, #{locator}, :section);end))
110
141
  end
111
142
 
112
- def self.switch(element_name, strategy, locator)
113
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppSwitch.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
143
+ def self.lists(element_hash)
144
+ element_hash.each do |element_name, locator|
145
+ list(element_name, locator)
146
+ end
114
147
  end
115
148
 
116
- def self.checkbox(element_name, strategy, locator)
117
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppCheckBox.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
149
+ def self.image(element_name, locator)
150
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppImage.new("#{element_name}", self, #{locator}, :section);end))
118
151
  end
119
152
 
120
- def self.label(element_name, strategy, locator)
121
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppLabel.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
153
+ def self.images(element_hash)
154
+ element_hash.each do |element_name, locator|
155
+ image(element_name, locator)
156
+ end
122
157
  end
123
158
 
124
- def self.list(element_name, strategy, locator)
125
- class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppList.new("#{element_name}", self, "#{strategy}", "#{locator}", :section);end))
159
+ def self.alert(element_name, locator)
160
+ class_eval(%(def #{element_name};@#{element_name} ||= TestCentricity::AppAlert.new("#{element_name}", self, #{locator}, :page);end))
126
161
  end
127
162
 
128
163
  def self.section(section_name, class_name)
129
164
  class_eval(%(def #{section_name};@#{section_name} ||= #{class_name}.new("#{section_name}", self, :section);end))
130
165
  end
131
166
 
167
+ def self.sections(section_hash)
168
+ section_hash.each do |section_name, class_name|
169
+ section(section_name, class_name)
170
+ end
171
+ end
132
172
 
133
173
 
134
174
  def click
135
175
  section = find_section
136
- raise "Section object '#{get_name}' (#{get_locator}) not found" unless section
176
+ section_not_found_exception(section)
137
177
  section.click
138
178
  end
139
179
 
140
180
  def tap
141
181
  section = find_section
142
- raise "Section object '#{get_name}' (#{get_locator}) not found" unless section
182
+ section_not_found_exception(section)
143
183
  x = section.location.x
144
184
  y = section.location.y
145
185
  tap_action = Appium::TouchAction.new.tap(element: section, x: x, y: y)
@@ -148,7 +188,7 @@ module TestCentricity
148
188
 
149
189
  def double_tap
150
190
  section = find_section
151
- raise "Section object '#{get_name}' (#{get_locator}) not found" unless section
191
+ section_not_found_exception(section)
152
192
  x = section.location.x
153
193
  y = section.location.y
154
194
  tap_action = Appium::TouchAction.new.double_tap(element: section, x: x, y: y)
@@ -162,13 +202,13 @@ module TestCentricity
162
202
 
163
203
  def enabled?
164
204
  section = find_section
165
- raise "Section object '#{get_name}' (#{get_locator}) not found" unless section
205
+ section_not_found_exception(section)
166
206
  section.enabled?
167
207
  end
168
208
 
169
209
  def disabled?
170
210
  section = find_section
171
- raise "Section object '#{get_name}' (#{get_locator}) not found" unless section
211
+ section_not_found_exception(section)
172
212
  section.enabled?
173
213
  end
174
214
 
@@ -217,14 +257,40 @@ module TestCentricity
217
257
  end
218
258
 
219
259
 
260
+
261
+ def width
262
+ section = find_section
263
+ section_not_found_exception(section)
264
+ section.size.width
265
+ end
266
+
267
+ def height
268
+ section = find_section
269
+ section_not_found_exception(section)
270
+ section.size.height
271
+ end
272
+
273
+ def x_loc
274
+ section = find_section
275
+ section_not_found_exception(section)
276
+ section.location.x
277
+ end
278
+
279
+ def y_loc
280
+ section = find_section
281
+ section_not_found_exception(section)
282
+ section.location.y
283
+ end
284
+
285
+
286
+
287
+
220
288
  def verify_ui_states(ui_states)
221
289
  ui_states.each do |ui_object, object_states|
222
290
  object_states.each do |property, state|
223
291
 
224
-
225
292
  puts "#{ui_object.get_name} - #{property} = #{state}" if ENV['DEBUG']
226
293
 
227
-
228
294
  case property
229
295
  when :exists
230
296
  actual = ui_object.exists?
@@ -248,10 +314,22 @@ module TestCentricity
248
314
  actual = ui_object.tag_name
249
315
  when :placeholder
250
316
  actual = ui_object.get_placeholder
317
+ when :readonly
318
+ actual = ui_object.read_only?
319
+ when :maxlength
320
+ actual = ui_object.get_max_length
251
321
  when :items
252
322
  actual = ui_object.get_list_items
253
323
  when :itemcount
254
324
  actual = ui_object.get_item_count
325
+ when :width
326
+ actual = ui_object.width
327
+ when :height
328
+ actual = ui_object.height
329
+ when :x
330
+ actual = ui_object.x_loc
331
+ when :y
332
+ actual = ui_object.y_loc
255
333
  end
256
334
 
257
335
  if state.is_a?(Hash) && state.length == 1
@@ -324,9 +402,24 @@ module TestCentricity
324
402
  private
325
403
 
326
404
  def find_section
327
- find_element(@strategy, @locator)
405
+ obj = nil
406
+ locators = get_locator
407
+ locators.each do |loc|
408
+ if obj.nil?
409
+ obj = find_element(loc.keys[0], loc.values[0])
410
+ puts "Found object #{loc}" if ENV['DEBUG']
411
+ else
412
+ obj = obj.find_element(loc.keys[0], loc.values[0])
413
+ puts "Found object #{loc}" if ENV['DEBUG']
414
+ end
415
+ end
416
+ obj
328
417
  rescue
329
418
  nil
330
419
  end
420
+
421
+ def section_not_found_exception(obj)
422
+ raise "Section object '#{get_name}' (#{get_locator}) not found" unless obj
423
+ end
331
424
  end
332
425
  end
@@ -0,0 +1,27 @@
1
+ module TestCentricity
2
+ class AppAlert < AppUIElement
3
+ def initialize(name, parent, locator, context)
4
+ super
5
+ @type = :alert
6
+ end
7
+
8
+ def await(seconds)
9
+ timeout = seconds.nil? ? Environ.default_max_wait_time : seconds
10
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
11
+ wait.until { exists? }
12
+ true
13
+ rescue
14
+ false
15
+ end
16
+
17
+ def accept
18
+ alert_accept
19
+ wait_until_gone(5)
20
+ end
21
+
22
+ def dismiss
23
+ alert_dismiss
24
+ wait_until_gone(5)
25
+ end
26
+ end
27
+ end
@@ -4,16 +4,14 @@ module TestCentricity
4
4
  class AppUIElement
5
5
  include Test::Unit::Assertions
6
6
 
7
- attr_reader :parent, :strategy, :locator, :context, :type, :name
8
- attr_accessor :mru_element, :mru_name
7
+ attr_reader :parent, :locator, :context, :type, :name
9
8
 
10
- def initialize(name, parent, strategy, locator, context)
11
- @name = name
12
- @parent = parent
13
- @strategy = strategy.to_sym
14
- @locator = locator
15
- @context = context
16
- @type = nil
9
+ def initialize(name, parent, locator, context)
10
+ @name = name
11
+ @parent = parent
12
+ @locator = locator
13
+ @context = context
14
+ @type = nil
17
15
  end
18
16
 
19
17
  def get_object_type
@@ -21,7 +19,7 @@ module TestCentricity
21
19
  end
22
20
 
23
21
  def get_locator
24
- [@strategy.to_sym, @locator]
22
+ @locator
25
23
  end
26
24
 
27
25
  def get_name
@@ -78,16 +76,34 @@ module TestCentricity
78
76
  def get_value
79
77
  obj = element
80
78
  object_not_found_exception(obj)
81
- obj.value
79
+ if AppiumConnect.is_webview?
80
+ case obj.tag_name.downcase
81
+ when 'input', 'select', 'textarea'
82
+ obj.value
83
+ else
84
+ obj.text
85
+ end
86
+ else
87
+ obj.value
88
+ end
82
89
  end
83
90
 
84
91
  def get_caption
85
92
  obj = element
86
93
  object_not_found_exception(obj)
87
- if obj.tag_name == 'XCUIElementTypeNavigationBar'
88
- obj.attribute('name')
94
+ if AppiumConnect.is_webview?
95
+ case obj.tag_name.downcase
96
+ when 'input', 'select', 'textarea'
97
+ obj.value
98
+ else
99
+ obj.text
100
+ end
89
101
  else
90
- obj.attribute('label')
102
+ if obj.tag_name == 'XCUIElementTypeNavigationBar'
103
+ obj.attribute('name')
104
+ else
105
+ obj.attribute('label')
106
+ end
91
107
  end
92
108
  end
93
109
 
@@ -230,13 +246,52 @@ module TestCentricity
230
246
  raise "Value of UI #{object_ref_message} failed to change from '#{value}' after #{timeout} seconds" if get_value == value
231
247
  end
232
248
 
249
+ def width
250
+ obj = element
251
+ object_not_found_exception(obj)
252
+ obj.size.width
253
+ end
254
+
255
+ # Return height of object.
256
+ #
257
+ # @return [Integer]
258
+ # @example
259
+ # button_height = my_button.height
260
+ #
261
+ def height
262
+ obj = element
263
+ object_not_found_exception(obj)
264
+ obj.size.height
265
+ end
266
+
267
+ # Return x coordinate of object's location.
268
+ #
269
+ # @return [Integer]
270
+ # @example
271
+ # button_x = my_button.x
272
+ #
273
+ def x_loc
274
+ obj = element
275
+ object_not_found_exception(obj)
276
+ obj.location.x
277
+ end
233
278
 
234
- def scroll_into_view
235
- scroll(:down) unless visible?
279
+ # Return y coordinate of object's location.
280
+ #
281
+ # @return [Integer]
282
+ # @example
283
+ # button_y = my_button.y
284
+ #
285
+ def y_loc
286
+ obj = element
287
+ object_not_found_exception(obj)
288
+ obj.location.y
236
289
  end
237
290
 
238
291
  def scroll(direction)
239
- execute_script('mobile: scroll', direction: direction.to_s)
292
+ obj = element
293
+ object_not_found_exception(obj)
294
+ execute_script('mobile: scroll', direction: direction.to_s, element: obj)
240
295
  end
241
296
 
242
297
  def swipe(direction)
@@ -255,25 +310,18 @@ module TestCentricity
255
310
  locators = @parent.get_locator
256
311
  locators.each do |parent_locator|
257
312
  if parent_obj.nil?
258
- parent_obj = find_element(parent_locator[0], parent_locator[1])
313
+ parent_obj = find_element(parent_locator.keys[0], parent_locator.values[0])
259
314
  else
260
- parent_obj = parent_obj.find_element(parent_locator[0], parent_locator[1])
315
+ parent_obj = parent_obj.find_element(parent_locator.keys[0], parent_locator.values[0])
261
316
  end
262
317
  end
263
-
264
318
  puts "Found parent object '#{@parent.get_name}' - #{@parent.get_locator}" if ENV['DEBUG']
265
-
266
-
267
- obj = parent_obj.find_element(@strategy, @locator)
268
-
269
- puts "Found object '#{@name}' - [:#{@strategy}, #{@locator}]" if ENV['DEBUG']
270
-
319
+ obj = parent_obj.find_element(@locator.keys[0], @locator.values[0])
320
+ puts "Found object '#{@name}' - #{@locator}" if ENV['DEBUG']
271
321
  obj
272
322
  else
273
- obj = find_element(@strategy, @locator)
274
-
275
- puts "Found object '#{@name}' - [:#{@strategy}, #{@locator}]" if ENV['DEBUG']
276
-
323
+ obj = find_element(@locator.keys[0], @locator.values[0])
324
+ puts "Found object '#{@name}' - #{@locator}" if ENV['DEBUG']
277
325
  obj
278
326
  end
279
327
  rescue
@@ -1,6 +1,6 @@
1
1
  module TestCentricity
2
2
  class AppButton < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :button
6
6
  end
@@ -1,20 +1,26 @@
1
1
  module TestCentricity
2
2
  class AppCheckBox < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :checkbox
6
6
  end
7
7
 
8
8
  def checked?
9
- element.attribute('checked') == 'true'
9
+ obj = element
10
+ object_not_found_exception(obj)
11
+ obj.attribute('checked') == 'true'
10
12
  end
11
13
 
12
14
  def check
13
- element.click unless checked?
15
+ obj = element
16
+ object_not_found_exception(obj)
17
+ obj.click unless obj.attribute('checked') == 'true'
14
18
  end
15
19
 
16
20
  def uncheck
17
- element.click if checked?
21
+ obj = element
22
+ object_not_found_exception(obj)
23
+ obj.click if obj.attribute('checked') == 'true'
18
24
  end
19
25
  end
20
26
  end
@@ -0,0 +1,8 @@
1
+ module TestCentricity
2
+ class AppImage < AppUIElement
3
+ def initialize(name, parent, locator, context)
4
+ super
5
+ @type = :image
6
+ end
7
+ end
8
+ end
@@ -1,6 +1,6 @@
1
1
  module TestCentricity
2
2
  class AppLabel < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :label
6
6
  end
@@ -1,15 +1,17 @@
1
1
  module TestCentricity
2
2
  class AppList < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :list
6
6
  end
7
7
 
8
8
  def get_item_count
9
+ obj = element
10
+ object_not_found_exception(obj)
9
11
  if Environ.device_os == :ios
10
- items = find_elements(class: 'XCUIElementTypeCell')
12
+ items = obj.find_elements(:class, 'XCUIElementTypeCell')
11
13
  else
12
- items = find_elements(class: 'android.widget.FrameLayout')
14
+ items = obj.find_elements(:class, 'android.widget.FrameLayout')
13
15
  end
14
16
  items.size
15
17
  end
@@ -21,5 +23,22 @@ module TestCentricity
21
23
  def get_list_item(index)
22
24
 
23
25
  end
26
+
27
+ def wait_until_item_count_is(value, seconds = nil)
28
+ timeout = seconds.nil? ? Environ.default_max_wait_time : seconds
29
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
30
+ wait.until { get_item_count == value }
31
+ rescue
32
+ raise "Value of List #{object_ref_message} failed to equal '#{value}' after #{timeout} seconds" unless get_item_count == value
33
+ end
34
+
35
+ def wait_until_item_count_changes(seconds = nil)
36
+ value = get_item_count
37
+ timeout = seconds.nil? ? Environ.default_max_wait_time : seconds
38
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
39
+ wait.until { get_item_count != value }
40
+ rescue
41
+ raise "Value of List #{object_ref_message} failed to change from '#{value}' after #{timeout} seconds" if get_item_count == value
42
+ end
24
43
  end
25
44
  end
@@ -1,20 +1,26 @@
1
1
  module TestCentricity
2
2
  class AppSwitch < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :switch
6
6
  end
7
7
 
8
8
  def on?
9
- element.get_value == 1
9
+ obj = element
10
+ object_not_found_exception(obj)
11
+ obj.get_value == 1
10
12
  end
11
13
 
12
14
  def on
13
- element.click unless on?
15
+ obj = element
16
+ object_not_found_exception(obj)
17
+ obj.click unless obj.get_value == 1
14
18
  end
15
19
 
16
20
  def off
17
- element.click if on?
21
+ obj = element
22
+ object_not_found_exception(obj)
23
+ obj.click if obj.get_value == 1
18
24
  end
19
25
  end
20
26
  end
@@ -1,12 +1,49 @@
1
1
  module TestCentricity
2
2
  class AppTextField < AppUIElement
3
- def initialize(name, parent, strategy, locator, context)
3
+ def initialize(name, parent, locator, context)
4
4
  super
5
5
  @type = :textfield
6
6
  end
7
7
 
8
+ # Is text field set to read-only?
9
+ #
10
+ # @return [Boolean]
11
+ # @example
12
+ # comments_field.read_only?
13
+ #
14
+ def read_only?
15
+ obj = element
16
+ object_not_found_exception(obj)
17
+ !!obj.attribute('readonly')
18
+ end
19
+
20
+ # Return maxlength character count of a text field.
21
+ #
22
+ # @return [Integer]
23
+ # @example
24
+ # max_num_chars = comments_field.get_max_length
25
+ #
26
+ def get_max_length
27
+ obj = element
28
+ object_not_found_exception(obj)
29
+ max_length = obj.attribute('maxlength')
30
+ max_length.to_i unless max_length.blank?
31
+ end
32
+
33
+ # Return placeholder text of a text field.
34
+ #
35
+ # @return [String]
36
+ # @example
37
+ # placeholder_message = username_field.get_placeholder
38
+ #
8
39
  def get_placeholder
9
- element.text
40
+ obj = element
41
+ object_not_found_exception(obj)
42
+ if AppiumConnect.is_webview?
43
+ obj.attribute('placeholder')
44
+ else
45
+ obj.text
46
+ end
10
47
  end
11
48
  end
12
49
  end
@@ -36,6 +36,7 @@ module TestCentricity
36
36
  attr_accessor :device_type
37
37
  attr_accessor :device_os
38
38
  attr_accessor :device_orientation
39
+ attr_accessor :screen_size
39
40
  attr_accessor :platform
40
41
  attr_accessor :driver
41
42
  attr_accessor :tunneling
@@ -130,6 +131,14 @@ module TestCentricity
130
131
  @browser_size
131
132
  end
132
133
 
134
+ def self.screen_size=(size)
135
+ @screen_size = size
136
+ end
137
+
138
+ def self.screen_size
139
+ @screen_size
140
+ end
141
+
133
142
  def self.session_state=(session_state)
134
143
  @session_state = session_state
135
144
  end
@@ -1,3 +1,3 @@
1
1
  module TestCentricity
2
- VERSION = '2.3.13'
2
+ VERSION = '2.3.14'
3
3
  end
@@ -69,5 +69,22 @@ module TestCentricity
69
69
  "#{@locator} > #{@list_item}:nth-of-type(#{row})"
70
70
  end
71
71
  end
72
+
73
+ def wait_until_item_count_is(value, seconds = nil)
74
+ timeout = seconds.nil? ? Capybara.default_max_wait_time : seconds
75
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
76
+ wait.until { get_item_count == value }
77
+ rescue
78
+ raise "Value of List #{object_ref_message} failed to equal '#{value}' after #{timeout} seconds" unless get_item_count == value
79
+ end
80
+
81
+ def wait_until_item_count_changes(seconds = nil)
82
+ value = get_item_count
83
+ timeout = seconds.nil? ? Capybara.default_max_wait_time : seconds
84
+ wait = Selenium::WebDriver::Wait.new(timeout: timeout)
85
+ wait.until { get_item_count != value }
86
+ rescue
87
+ raise "Value of List #{object_ref_message} failed to change from '#{value}' after #{timeout} seconds" if get_item_count == value
88
+ end
72
89
  end
73
90
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: testcentricity
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.3.13
4
+ version: 2.3.14
5
5
  platform: ruby
6
6
  authors:
7
7
  - A.J. Mrozinski
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-02-21 00:00:00.000000000 Z
11
+ date: 2018-02-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -252,9 +252,11 @@ files:
252
252
  - lib/testcentricity/app_core/appium_server.rb
253
253
  - lib/testcentricity/app_core/screen_objects_helper.rb
254
254
  - lib/testcentricity/app_core/screen_sections_helper.rb
255
+ - lib/testcentricity/app_elements/alert.rb
255
256
  - lib/testcentricity/app_elements/app_element_helper.rb
256
257
  - lib/testcentricity/app_elements/button.rb
257
258
  - lib/testcentricity/app_elements/checkbox.rb
259
+ - lib/testcentricity/app_elements/image.rb
258
260
  - lib/testcentricity/app_elements/label.rb
259
261
  - lib/testcentricity/app_elements/list.rb
260
262
  - lib/testcentricity/app_elements/switch.rb