testcentricity_web 4.6.10 → 4.7.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +30 -29
- data/LICENSE.md +1 -1
- data/README.md +7 -24
- data/lib/testcentricity_web/appium_server.rb +1 -5
- data/lib/testcentricity_web/data_objects/data_objects_helper.rb +149 -53
- data/lib/testcentricity_web/data_objects/environment.rb +20 -21
- data/lib/testcentricity_web/version.rb +1 -1
- data/lib/testcentricity_web/web_core/page_objects_helper.rb +10 -0
- data/lib/testcentricity_web/web_core/webdriver_helper.rb +1 -7
- metadata +37 -9
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 6102470c95dae002d34823ce559513917b2d97a01758253e343e6b510335dd29
|
|
4
|
+
data.tar.gz: 82c75b633a9fdc676081b08cb6dedf0cdafe8fc4a3e55760a5c9b077265a22b4
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 5299949e037fa7d870038e17a59d09a8df8b5280069c315ecd8c45935143aa21fd5ef809a62a3f252fe61c476d8eac5b5d7834c6deb6cb33bda402496e2407a7
|
|
7
|
+
data.tar.gz: 186ba585ddef4bfac4a4e4226095f5bb8887cb1a05871d47a7a2f2e9921922b5cca5cfbba220c5d038f8394938854cece55c05ba5d93db25ca89af66266d7381
|
data/CHANGELOG.md
CHANGED
|
@@ -2,10 +2,35 @@
|
|
|
2
2
|
All notable changes to this project will be documented in this file.
|
|
3
3
|
|
|
4
4
|
|
|
5
|
-
## [4.
|
|
5
|
+
## [4.7.0] - 12-JAN-2026
|
|
6
6
|
|
|
7
7
|
### Added
|
|
8
|
+
* Added `DataSource.read_file` method capable of reading from `.yml`, `.json`, `.csv`, or `.xml` data files, and accepting
|
|
9
|
+
`options` hash for specifying hash key and value conversions to data being read prior to passing to `DataPresenter` objects.
|
|
10
|
+
|
|
11
|
+
### Changed
|
|
12
|
+
* Refactored `EnvironData.read` method to allow passing `options` hash for specifying hash key and value conversions to
|
|
13
|
+
data being read prior to passing to `DataPresenter` objects.
|
|
14
|
+
* Refactored `PageObject.populate_data_fields` and `PageSection.populate_data_fields` methods to support passing a `Symbol`
|
|
15
|
+
for a UI element's name to support using `DataPresenter` object attributes to source data.
|
|
16
|
+
* Updated `appium_lib` gem to version 16.1.1.
|
|
17
|
+
* Updated `appium_lib_core` gem to version 11.2.0.
|
|
18
|
+
|
|
19
|
+
### Removed
|
|
20
|
+
* Unused `DataObject` class has been removed.
|
|
21
|
+
* Removed unused `DataSource.read_yaml_node_data` and `DataSource.read_json_node_data` methods.
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
## [4.6.11] - 24-NOV-2025
|
|
25
|
+
|
|
26
|
+
### Removed
|
|
27
|
+
|
|
28
|
+
* Appium version 1.x is no longer supported.
|
|
29
|
+
|
|
8
30
|
|
|
31
|
+
## [4.6.10] - 07-NOV-2025
|
|
32
|
+
|
|
33
|
+
### Added
|
|
9
34
|
* Added the following `Media` methods to support verification of media text tracks (subtitles, captions,
|
|
10
35
|
chapters, descriptions, or metadata):
|
|
11
36
|
* `active_track_cue_count`
|
|
@@ -25,14 +50,12 @@ All notable changes to this project will be documented in this file.
|
|
|
25
50
|
* `all_cues_data`
|
|
26
51
|
|
|
27
52
|
### Changed
|
|
28
|
-
|
|
29
53
|
* `Media.current_time` and `Media.duration` now return `Float` rounded to nearest tenth.
|
|
30
54
|
|
|
31
55
|
|
|
32
56
|
## [4.6.9] - 31-OCT-2025
|
|
33
57
|
|
|
34
58
|
### Added
|
|
35
|
-
|
|
36
59
|
* Added `Table.get_footer_columns` and `Table.get_footer_column`methods.
|
|
37
60
|
* Updated `PageObject.verify_ui_states` and `PageSection.verify_ui_states` methods to support verification of the following
|
|
38
61
|
`Table` properties:
|
|
@@ -41,14 +64,12 @@ All notable changes to this project will be documented in this file.
|
|
|
41
64
|
* `:column_header`
|
|
42
65
|
|
|
43
66
|
### Changed
|
|
44
|
-
|
|
45
67
|
* `UIElement.get_max` now works with HTML `<progress>` elements.
|
|
46
68
|
|
|
47
69
|
|
|
48
70
|
## [4.6.8] - 27-OCT-2025
|
|
49
71
|
|
|
50
72
|
### Changed
|
|
51
|
-
|
|
52
73
|
* `UIElement.aria_valuemax`, `UIElement.aria_valuemin`, and `UIElement.aria_valuenow` now return `Integer` or `Float`
|
|
53
74
|
instead of `String` result.
|
|
54
75
|
* `UIElement.aria_rowcount` and `UIElement.aria_colcount` now return `Integer` instead of `String` result.
|
|
@@ -67,7 +88,6 @@ All notable changes to this project will be documented in this file.
|
|
|
67
88
|
## [4.6.7] - 21-OCT-2025
|
|
68
89
|
|
|
69
90
|
### Added
|
|
70
|
-
|
|
71
91
|
* Added `UIElement.draggable?` method.
|
|
72
92
|
* Updated `PageObject.verify_ui_states` and `PageSection.verify_ui_states` methods to support verification of the
|
|
73
93
|
`draggable` property.
|
|
@@ -76,7 +96,6 @@ All notable changes to this project will be documented in this file.
|
|
|
76
96
|
## [4.6.6] - 10-OCT-2025
|
|
77
97
|
|
|
78
98
|
### Changed
|
|
79
|
-
|
|
80
99
|
* Update Nokogiri gem to address CVE-2025-6021, CVE-2025-6170, CVE-2025-49794, CVE-2025-49795, and CVE-2025-49796.
|
|
81
100
|
* Update REXML gem to address DoS vulnerability when parsing XML containing multiple XML declarations.
|
|
82
101
|
|
|
@@ -84,28 +103,24 @@ All notable changes to this project will be documented in this file.
|
|
|
84
103
|
## [4.6.5] - 18-JUL-2025
|
|
85
104
|
|
|
86
105
|
### Changed
|
|
87
|
-
|
|
88
106
|
* No longer bundling `selenium-webdriver` as a runtime dependency.
|
|
89
107
|
|
|
90
108
|
|
|
91
109
|
## [4.6.4] - 22-MAY-2025
|
|
92
110
|
|
|
93
111
|
### Changed
|
|
94
|
-
|
|
95
112
|
* Updated `selenium-webdriver` gem to version 4.32.0.
|
|
96
113
|
|
|
97
114
|
|
|
98
115
|
## [4.6.3] - 23-APR-2025
|
|
99
116
|
|
|
100
117
|
### Changed
|
|
101
|
-
|
|
102
118
|
* Updated `selenium-webdriver` gem to version 4.31.0.
|
|
103
119
|
|
|
104
120
|
|
|
105
121
|
## [4.6.2] - 28-MAR-2025
|
|
106
122
|
|
|
107
123
|
### Changed
|
|
108
|
-
|
|
109
124
|
* Updated `appium_lib` gem to version 16.1.0.
|
|
110
125
|
* Updated `appium_lib_core` gem to version 11.0.1.
|
|
111
126
|
* Updated `selenium-webdriver` gem to version 4.30.1.
|
|
@@ -114,7 +129,6 @@ All notable changes to this project will be documented in this file.
|
|
|
114
129
|
## [4.6.1] - 18-MAR-2025
|
|
115
130
|
|
|
116
131
|
### Changed
|
|
117
|
-
|
|
118
132
|
* Updated `appium_lib` gem to version 16.0.1.
|
|
119
133
|
* Updated `appium_lib_core` gem to version 10.0.0.
|
|
120
134
|
* Updated `selenium-webdriver` gem to version 4.29.1.
|
|
@@ -123,7 +137,6 @@ All notable changes to this project will be documented in this file.
|
|
|
123
137
|
## [4.6.0] - 25-JAN-2025
|
|
124
138
|
|
|
125
139
|
### Changed
|
|
126
|
-
|
|
127
140
|
* Updated `selenium-webdriver` gem to version 4.28.0.
|
|
128
141
|
* Updated `appium_lib` gem to version 15.3.0.
|
|
129
142
|
* Updated `appium_lib_core` gem to version 9.5.0.
|
|
@@ -133,7 +146,6 @@ All notable changes to this project will be documented in this file.
|
|
|
133
146
|
## [4.5.15] - 01-NOV-2024
|
|
134
147
|
|
|
135
148
|
### Changed
|
|
136
|
-
|
|
137
149
|
* Updated `selenium-webdriver` gem to version 4.26.0.
|
|
138
150
|
* Updated `rexml` gem to latest version to address ReDoS vulnerability.
|
|
139
151
|
|
|
@@ -141,35 +153,30 @@ All notable changes to this project will be documented in this file.
|
|
|
141
153
|
## [4.5.14] - 09-OCT-2024
|
|
142
154
|
|
|
143
155
|
### Fixed
|
|
144
|
-
|
|
145
156
|
* Disable Chrome search engine choice screen.
|
|
146
157
|
|
|
147
158
|
|
|
148
159
|
## [4.5.13] - 24-SEP-2024
|
|
149
160
|
|
|
150
161
|
### Changed
|
|
151
|
-
|
|
152
162
|
* Updated `selenium-webdriver` gem to version 4.25.0.
|
|
153
163
|
|
|
154
164
|
|
|
155
165
|
## [4.5.12] - 30-AUG-2024
|
|
156
166
|
|
|
157
167
|
### Changed
|
|
158
|
-
|
|
159
168
|
* Updated `selenium-webdriver` gem to version 4.24.0.
|
|
160
169
|
|
|
161
170
|
|
|
162
171
|
## [4.5.11] - 08-AUG-2024
|
|
163
172
|
|
|
164
173
|
### Changed
|
|
165
|
-
|
|
166
174
|
* Updated `appium_lib` gem to version 15.2.2.
|
|
167
175
|
|
|
168
176
|
|
|
169
177
|
## [4.5.10] - 05-AUG-2024
|
|
170
178
|
|
|
171
179
|
### Changed
|
|
172
|
-
|
|
173
180
|
* Updated `selenium-webdriver` gem to version 4.23.0.
|
|
174
181
|
* Updated `appium_lib` gem to version 15.2.1.
|
|
175
182
|
* Updated `appium_lib_core` gem to version 9.2.1.
|
|
@@ -178,7 +185,6 @@ All notable changes to this project will be documented in this file.
|
|
|
178
185
|
## [4.5.9.1] - 26-JUNE-2024
|
|
179
186
|
|
|
180
187
|
### Fixed
|
|
181
|
-
|
|
182
188
|
* Added `cuke_modeler` gem as a development dependency so that Cucumber test results logging would not fail when running
|
|
183
189
|
tests in parallel with Ruby version 3.1.0 or greater.
|
|
184
190
|
|
|
@@ -186,16 +192,14 @@ tests in parallel with Ruby version 3.1.0 or greater.
|
|
|
186
192
|
## [4.5.9] - 23-JUNE-2024
|
|
187
193
|
|
|
188
194
|
### Changed
|
|
189
|
-
|
|
190
195
|
* Updated `selenium-webdriver` gem to version 4.22.0.
|
|
191
196
|
|
|
192
197
|
|
|
193
198
|
## [4.5.8] - 21-MAY-2024
|
|
194
199
|
|
|
195
200
|
### Changed
|
|
196
|
-
|
|
197
201
|
* Setting `DOWNLOADS` Environment Variable to `true` will create a `/downloads` folder which will be used as the destination
|
|
198
|
-
for files that are downloaded by your automated tests. You
|
|
202
|
+
for files that are downloaded by your automated tests. You no longer need to manually create the `/downloads` folder.
|
|
199
203
|
* Updated `appium_lib` gem to version 15.1.0.
|
|
200
204
|
* Updated `appium_lib_core` gem to version 9.1.1.
|
|
201
205
|
* Updated `selenium-webdriver` gem to version 4.21.1.
|
|
@@ -204,7 +208,6 @@ for files that are downloaded by your automated tests. You know longer need to m
|
|
|
204
208
|
## [4.5.7] - 25-APR-2024
|
|
205
209
|
|
|
206
210
|
### Changed
|
|
207
|
-
|
|
208
211
|
* Updated `selenium-webdriver` gem to version 4.20.0.
|
|
209
212
|
* Updated `appium_lib` gem to version 15.0.0.
|
|
210
213
|
* Updated `appium_lib_core` gem to version 8.0.1.
|
|
@@ -213,7 +216,6 @@ for files that are downloaded by your automated tests. You know longer need to m
|
|
|
213
216
|
## [4.5.6] - 02-APR-2024
|
|
214
217
|
|
|
215
218
|
### Fixed
|
|
216
|
-
|
|
217
219
|
* `WebDriverConnect.initialize_web_driver`, `AppiumServer.start`, and `AppiumServer.running?` methods now support Appium
|
|
218
220
|
version 2.x. Backward compatibility with Appium version 1.x is provided if `APPIUM_SERVER_VERSION` Environment Variable
|
|
219
221
|
is set to `1`.
|
|
@@ -222,14 +224,12 @@ is set to `1`.
|
|
|
222
224
|
## [4.5.5] - 27-MAR-2024
|
|
223
225
|
|
|
224
226
|
### Changed
|
|
225
|
-
|
|
226
227
|
* Updated `selenium-webdriver` gem to version 4.19.0.
|
|
227
228
|
|
|
228
229
|
|
|
229
230
|
## [4.5.4] - 04-MAR-2024
|
|
230
231
|
|
|
231
232
|
### Changed
|
|
232
|
-
|
|
233
233
|
* Updated `selenium-webdriver` gem to version 4.18.1.
|
|
234
234
|
* Updated `rack` gem to version 3.0.9.1.
|
|
235
235
|
* Updated `nokogiri` gem to version 1.16.2.
|
|
@@ -238,14 +238,12 @@ is set to `1`.
|
|
|
238
238
|
## [4.5.3] - 27-JAN-2024
|
|
239
239
|
|
|
240
240
|
### Changed
|
|
241
|
-
|
|
242
241
|
* Updated `capybara` gem to version 3.40.0.
|
|
243
242
|
|
|
244
243
|
|
|
245
244
|
## [4.5.2] - 26-JAN-2024
|
|
246
245
|
|
|
247
246
|
### Changed
|
|
248
|
-
|
|
249
247
|
* Updated `appium_lib` gem to version 14.0.0.
|
|
250
248
|
* Updated `selenium-webdriver` gem to version 4.17.0.
|
|
251
249
|
|
|
@@ -1007,17 +1005,20 @@ Grid environments.
|
|
|
1007
1005
|
|
|
1008
1006
|
|
|
1009
1007
|
## [3.0.12] - 2018-08-09
|
|
1008
|
+
|
|
1010
1009
|
### Added
|
|
1011
1010
|
* `PageSection.hover` method.
|
|
1012
1011
|
* `List.hover_item` method.
|
|
1013
1012
|
|
|
1014
1013
|
|
|
1015
1014
|
## [3.0.11] - 2018-08-05
|
|
1015
|
+
|
|
1016
1016
|
### Added
|
|
1017
1017
|
* `UIElement.count` method.
|
|
1018
1018
|
|
|
1019
1019
|
|
|
1020
1020
|
## [3.0.10] - 2018-07-20
|
|
1021
|
+
|
|
1021
1022
|
### Added
|
|
1022
1023
|
* `Image.broken?` method.
|
|
1023
1024
|
* `UIElement.highlight` and `UIElement.unhighlight` methods.
|
data/LICENSE.md
CHANGED
data/README.md
CHANGED
|
@@ -92,12 +92,12 @@ that can be used in tests. A **Page Object** represents a single page in your AU
|
|
|
92
92
|
encapsulate the implementation details of a web page and expose an API that supports interaction with, and validation of
|
|
93
93
|
the UI elements on the page.
|
|
94
94
|
|
|
95
|
-
**Page Objects**
|
|
96
|
-
location - in
|
|
97
|
-
definitions are no longer required to hold specific information about a page's UI objects, thus minimizing
|
|
98
|
-
requirements. If any element on, or property of a page changes (URL path, text field attributes, button
|
|
99
|
-
maintenance is performed in the `PageObject` class definition only, typically with no need
|
|
100
|
-
files, scenarios, or step definitions.
|
|
95
|
+
**Page Objects** make it easier to maintain automated tests because changes to a page's UI elements are updated in only
|
|
96
|
+
one location - in th corresponding **Page Object** class definition. By adopting a **Page Object Model**, Cucumber Feature
|
|
97
|
+
files and step definitions are no longer required to hold specific information about a page's UI objects, thus minimizing
|
|
98
|
+
test maintenance requirements. If any element on, or property of a page changes (URL path, text field attributes, button
|
|
99
|
+
captions, etc.), maintenance is performed in the corresponding `PageObject` class definition only, typically with no need
|
|
100
|
+
to update the affected feature files, scenarios, or step definitions.
|
|
101
101
|
|
|
102
102
|
|
|
103
103
|
### Defining a PageObject
|
|
@@ -1895,10 +1895,6 @@ Below is an example of an `options` hash for specifying a connection to a grid h
|
|
|
1895
1895
|
|
|
1896
1896
|
Refer to [this page](https://appium.io/docs/en/2.2/guides/caps/) for information regarding specifying Appium capabilities.
|
|
1897
1897
|
|
|
1898
|
-
⚠️ If you are running locally hosted mobile web tests on iOS or Android simulators or devices using version 1.x of the Appium
|
|
1899
|
-
server, the `APPIUM_SERVER_VERSION` environment variable must be set to `1` in order to ensure that the correct Appium server
|
|
1900
|
-
endpoint is used.
|
|
1901
|
-
|
|
1902
1898
|
#### Mobile Safari Browser on iOS Simulators or iOS Physical Devices
|
|
1903
1899
|
|
|
1904
1900
|
You can run your mobile web tests against the mobile Safari browser on iOS device simulators or physically connected iOS
|
|
@@ -2115,15 +2111,6 @@ starting your Cucumber test suite(s):
|
|
|
2115
2111
|
|
|
2116
2112
|
run_appium: APPIUM_SERVER=run
|
|
2117
2113
|
|
|
2118
|
-
If you are running locally hosted mobile web tests on iOS or Android simulators or devices using version 1.x of the Appium
|
|
2119
|
-
server, the `APPIUM_SERVER_VERSION` environment variable must be set to `1` in order to ensure that the correct Appium server
|
|
2120
|
-
endpoint is used. This can be set by adding the following to your `cucumber.yml` file and including `-p appium_1x` in your
|
|
2121
|
-
command line when starting your Cucumber test suite(s):
|
|
2122
|
-
|
|
2123
|
-
appium_1x: APPIUM_SERVER_VERSION=1
|
|
2124
|
-
|
|
2125
|
-
Refer to [**section 8.9 (Using Browser Specific Profiles in `cucumber.yml`)**](#using-browser-specific-profiles-in-cucumber-yml) below.
|
|
2126
|
-
|
|
2127
2114
|
|
|
2128
2115
|
##### Using Appium Server with RSpec
|
|
2129
2116
|
|
|
@@ -2142,9 +2129,6 @@ body of an example group:
|
|
|
2142
2129
|
$server.stop if Environ.driver == :appium && $server.running?
|
|
2143
2130
|
end
|
|
2144
2131
|
```
|
|
2145
|
-
If you are running locally hosted mobile web tests on iOS or Android simulators or devices using version 1.x of the Appium
|
|
2146
|
-
server, the `APPIUM_SERVER_VERSION` environment variable must be set to `1` in order to ensure that the correct Appium server
|
|
2147
|
-
endpoint is used.
|
|
2148
2132
|
|
|
2149
2133
|
|
|
2150
2134
|
### Remote Cloud Hosted Desktop and Mobile Web Browsers
|
|
@@ -2966,7 +2950,6 @@ with access to your version control system.
|
|
|
2966
2950
|
#==============
|
|
2967
2951
|
|
|
2968
2952
|
run_appium: APPIUM_SERVER=run
|
|
2969
|
-
appium_1x: APPIUM_SERVER_VERSION=1
|
|
2970
2953
|
|
|
2971
2954
|
|
|
2972
2955
|
#==============
|
|
@@ -3176,7 +3159,7 @@ area sub-folders as needed. Likewise, `PageSection` class definitions should be
|
|
|
3176
3159
|
---
|
|
3177
3160
|
## Copyright and License
|
|
3178
3161
|
|
|
3179
|
-
TestCentricity™ Framework is Copyright (c) 2014-
|
|
3162
|
+
TestCentricity™ Framework is Copyright (c) 2014-2026, Tony Mrozinski.
|
|
3180
3163
|
All rights reserved.
|
|
3181
3164
|
|
|
3182
3165
|
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
|
|
@@ -38,11 +38,7 @@ module TestCentricity
|
|
|
38
38
|
# Check to see if Appium Server is running
|
|
39
39
|
#
|
|
40
40
|
def running?
|
|
41
|
-
endpoint =
|
|
42
|
-
'http://0.0.0.0:4723/wd/hub/sessions'
|
|
43
|
-
else
|
|
44
|
-
'http://0.0.0.0:4723/sessions'
|
|
45
|
-
end
|
|
41
|
+
endpoint = 'http://0.0.0.0:4723/sessions'
|
|
46
42
|
response = false
|
|
47
43
|
begin
|
|
48
44
|
response = Net::HTTP.get_response(URI(endpoint))
|
|
@@ -1,47 +1,28 @@
|
|
|
1
|
-
require '
|
|
2
|
-
require '
|
|
3
|
-
require 'virtus'
|
|
4
|
-
require 'time'
|
|
1
|
+
require 'active_support'
|
|
2
|
+
require 'active_support/core_ext/hash'
|
|
5
3
|
require 'chronic'
|
|
6
4
|
require 'faker'
|
|
5
|
+
require 'json'
|
|
6
|
+
require 'rexml/document'
|
|
7
|
+
require 'smarter_csv'
|
|
8
|
+
require 'time'
|
|
9
|
+
require 'virtus'
|
|
10
|
+
require 'yaml'
|
|
7
11
|
|
|
8
12
|
|
|
9
13
|
module TestCentricity
|
|
10
14
|
|
|
11
15
|
PRIMARY_DATA_PATH ||= 'config/test_data/'
|
|
16
|
+
SECONDARY_DATA_PATH ||= 'config/data/'
|
|
12
17
|
PRIMARY_DATA_FILE ||= "#{PRIMARY_DATA_PATH}data."
|
|
13
18
|
YML_PRIMARY_DATA_FILE ||= "#{PRIMARY_DATA_FILE}yml"
|
|
14
19
|
JSON_PRIMARY_DATA_FILE ||= "#{PRIMARY_DATA_FILE}json"
|
|
15
20
|
|
|
16
21
|
|
|
17
|
-
class DataObject
|
|
18
|
-
attr_accessor :current
|
|
19
|
-
attr_accessor :context
|
|
20
|
-
attr_accessor :hash_table
|
|
21
|
-
|
|
22
|
-
def initialize(data)
|
|
23
|
-
@hash_table = data
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def self.current
|
|
27
|
-
@current
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def self.current=(current)
|
|
31
|
-
@current = current
|
|
32
|
-
end
|
|
33
|
-
end
|
|
34
|
-
|
|
35
|
-
|
|
36
22
|
class DataPresenter
|
|
37
23
|
include Virtus.model
|
|
38
24
|
|
|
39
25
|
attr_accessor :current
|
|
40
|
-
attr_accessor :context
|
|
41
|
-
|
|
42
|
-
def initialize(data)
|
|
43
|
-
self.attributes = data unless data.nil?
|
|
44
|
-
end
|
|
45
26
|
|
|
46
27
|
def self.current
|
|
47
28
|
@current
|
|
@@ -53,47 +34,162 @@ module TestCentricity
|
|
|
53
34
|
end
|
|
54
35
|
|
|
55
36
|
|
|
56
|
-
# :nocov:
|
|
57
37
|
class DataSource
|
|
58
38
|
attr_accessor :file_path
|
|
59
|
-
attr_accessor :
|
|
39
|
+
attr_accessor :file_extension
|
|
60
40
|
|
|
61
|
-
def
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
41
|
+
def read_file(file_name, key = nil, node_name = nil, options = nil)
|
|
42
|
+
# check to see if full file path was specified
|
|
43
|
+
if File.exist?(file_name)
|
|
44
|
+
@file_path = file_name
|
|
45
|
+
else
|
|
46
|
+
# construct the full file path to the file to be read
|
|
47
|
+
@file_path = "#{PRIMARY_DATA_PATH}#{file_name}"
|
|
48
|
+
unless File.exist?(@file_path)
|
|
49
|
+
@file_path = "#{SECONDARY_DATA_PATH}#{file_name}"
|
|
50
|
+
raise "File #{file_name} not found in Primary or Secondary folders in config folder" unless File.exist?(@file_path)
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
# determine file type and read in data from file
|
|
54
|
+
@file_extension = File.extname(file_name)
|
|
55
|
+
data = case @file_extension
|
|
56
|
+
when '.yml'
|
|
57
|
+
YAML.load_file(@file_path)
|
|
58
|
+
when'.json'
|
|
59
|
+
JSON.parse(File.read(@file_path))
|
|
60
|
+
when '.xml'
|
|
61
|
+
xml_data = File.read(@file_path)
|
|
62
|
+
Hash.from_xml(xml_data)
|
|
63
|
+
when '.csv'
|
|
64
|
+
if options
|
|
65
|
+
SmarterCSV.process(@file_path, options)
|
|
66
|
+
else
|
|
67
|
+
SmarterCSV.process(@file_path)
|
|
68
|
+
end
|
|
69
|
+
else
|
|
70
|
+
raise "#{file_name} is not a supported file type"
|
|
71
|
+
end
|
|
72
|
+
# return data if sourced from a .csv file
|
|
73
|
+
return data if @file_extension == '.csv'
|
|
74
|
+
|
|
75
|
+
# read data from specified key and/or node
|
|
76
|
+
result = if key
|
|
77
|
+
raise "Key #{key} not found" unless data.key?(key)
|
|
78
|
+
|
|
79
|
+
if node_name
|
|
80
|
+
raise "Node #{node_name} not found" unless data[key].key?(node_name)
|
|
81
|
+
|
|
82
|
+
data[key][node_name]
|
|
83
|
+
else
|
|
84
|
+
data[key]
|
|
85
|
+
end
|
|
86
|
+
else
|
|
87
|
+
data
|
|
88
|
+
end
|
|
89
|
+
self.class.send(:process_data, result, options)
|
|
66
90
|
end
|
|
67
91
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
data
|
|
73
|
-
|
|
92
|
+
private
|
|
93
|
+
|
|
94
|
+
def self.process_data(data, options)
|
|
95
|
+
# calculate dynamic values if any are specified
|
|
96
|
+
if data.is_a?(Hash)
|
|
97
|
+
data.each do |key, value|
|
|
98
|
+
data[key] = calculate_dynamic_value(value) if value.to_s.start_with?('eval!')
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
return data unless options
|
|
102
|
+
|
|
103
|
+
# convert keys to symbols if :keys_as_symbols is true in options
|
|
104
|
+
if options.key?(:keys_as_symbols) && options[:keys_as_symbols]
|
|
105
|
+
data.transform_keys!(&:to_sym)
|
|
106
|
+
end
|
|
107
|
+
# convert values if :value_converters are specified in options
|
|
108
|
+
if options.key?(:value_converters)
|
|
109
|
+
map_values(data, options[:value_converters])
|
|
110
|
+
else
|
|
111
|
+
data
|
|
112
|
+
end
|
|
74
113
|
end
|
|
75
114
|
|
|
76
|
-
|
|
115
|
+
def self.map_values(data, value_converters)
|
|
116
|
+
data.each_with_object({}) do |(k, v), new_hash|
|
|
117
|
+
converter = value_converters[k]
|
|
118
|
+
v = converter.convert(v) if converter
|
|
119
|
+
new_hash[k] = v
|
|
120
|
+
end
|
|
121
|
+
end
|
|
77
122
|
|
|
78
123
|
def self.calculate_dynamic_value(value)
|
|
79
124
|
test_value = value.split('!', 2)
|
|
80
125
|
parameter = test_value[1].split('.', 2)
|
|
81
|
-
case parameter[0]
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
126
|
+
result = case parameter[0]
|
|
127
|
+
when 'Date'
|
|
128
|
+
Chronic.parse(parameter[1])
|
|
129
|
+
when 'FormattedDate', 'FormatDate'
|
|
130
|
+
date_time_params = parameter[1].split(' format! ', 2)
|
|
131
|
+
date_time = Chronic.parse(date_time_params[0].strip)
|
|
132
|
+
date_time.to_s.format_date_time("#{date_time_params[1].strip}")
|
|
133
|
+
else
|
|
134
|
+
if Faker.constants.include?(parameter[0].to_sym)
|
|
90
135
|
eval("Faker::#{parameter[0]}.#{parameter[1]}")
|
|
91
136
|
else
|
|
92
137
|
eval(test_value[1])
|
|
93
138
|
end
|
|
94
|
-
|
|
139
|
+
end
|
|
95
140
|
result.to_s
|
|
96
141
|
end
|
|
97
|
-
|
|
142
|
+
end
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
|
|
146
|
+
# perform conversion of String to Boolean when reading data from .csv or .xml files
|
|
147
|
+
class ToBoolean
|
|
148
|
+
def self.convert(value)
|
|
149
|
+
value.to_bool unless value.nil?
|
|
150
|
+
end
|
|
151
|
+
end
|
|
152
|
+
|
|
153
|
+
|
|
154
|
+
# perform conversion of Integer to String when reading data from .csv or .xml files
|
|
155
|
+
class ToString
|
|
156
|
+
def self.convert(value)
|
|
157
|
+
if value.is_a? Integer
|
|
158
|
+
value.to_s
|
|
159
|
+
else
|
|
160
|
+
value
|
|
161
|
+
end
|
|
162
|
+
end
|
|
163
|
+
end
|
|
164
|
+
|
|
165
|
+
|
|
166
|
+
# perform conversion of String to Integer when reading data from .csv or .xml files
|
|
167
|
+
class ToInteger
|
|
168
|
+
def self.convert(value)
|
|
169
|
+
if value.is_a? Integer
|
|
170
|
+
value
|
|
171
|
+
else
|
|
172
|
+
if value.is_int?
|
|
173
|
+
value.to_i
|
|
174
|
+
else
|
|
175
|
+
value
|
|
176
|
+
end
|
|
177
|
+
end
|
|
178
|
+
end
|
|
179
|
+
end
|
|
180
|
+
|
|
181
|
+
|
|
182
|
+
# perform conversion of String to Float when reading data from .csv or .xml files
|
|
183
|
+
class ToFloat
|
|
184
|
+
def self.convert(value)
|
|
185
|
+
if value.is_a? Float
|
|
186
|
+
value
|
|
187
|
+
else
|
|
188
|
+
if value.is_float?
|
|
189
|
+
value.to_f
|
|
190
|
+
else
|
|
191
|
+
value
|
|
192
|
+
end
|
|
193
|
+
end
|
|
98
194
|
end
|
|
99
195
|
end
|
|
@@ -22,13 +22,11 @@ module TestCentricity
|
|
|
22
22
|
read('Environments', environ_name)
|
|
23
23
|
when :json
|
|
24
24
|
# read generic test data from data.json file
|
|
25
|
-
|
|
26
|
-
@generic_data = JSON.parse(raw_data)
|
|
25
|
+
@generic_data = JSON.parse(File.read(JSON_PRIMARY_DATA_FILE))
|
|
27
26
|
# read environment specific test data
|
|
28
27
|
data_file = "#{PRIMARY_DATA_PATH}#{environ_name}_data.json"
|
|
29
28
|
@environ_specific_data = if File.exist?(data_file)
|
|
30
|
-
|
|
31
|
-
JSON.parse(raw_data)
|
|
29
|
+
JSON.parse(File.read(data_file))
|
|
32
30
|
else
|
|
33
31
|
{}
|
|
34
32
|
end
|
|
@@ -41,27 +39,21 @@ module TestCentricity
|
|
|
41
39
|
Environ.current = @current
|
|
42
40
|
end
|
|
43
41
|
|
|
44
|
-
def self.read(key_name, node_name)
|
|
45
|
-
if @environ_specific_data.key?(key_name) && @environ_specific_data[key_name].key?(node_name)
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
node_data = @generic_data[key_name][node_name]
|
|
52
|
-
end
|
|
42
|
+
def self.read(key_name, node_name, options = nil)
|
|
43
|
+
node_data = if @environ_specific_data.key?(key_name) && @environ_specific_data[key_name].key?(node_name)
|
|
44
|
+
@environ_specific_data[key_name][node_name]
|
|
45
|
+
else
|
|
46
|
+
raise "No key named #{key_name} in generic and environment-specific data" unless @generic_data.key?(key_name)
|
|
47
|
+
raise "No node named #{node_name} in #{key_name} section of generic and environment-specific data" unless @generic_data[key_name].key?(node_name)
|
|
53
48
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
end
|
|
58
|
-
end
|
|
59
|
-
node_data
|
|
49
|
+
@generic_data[key_name][node_name]
|
|
50
|
+
end
|
|
51
|
+
process_data(node_data, options)
|
|
60
52
|
end
|
|
61
53
|
end
|
|
62
54
|
|
|
63
55
|
|
|
64
|
-
class Environ
|
|
56
|
+
class Environ
|
|
65
57
|
@session_id = Time.now.strftime('%d%H%M%S%L')
|
|
66
58
|
@session_time_stamp = Time.now.strftime('%Y%m%d%H%M%S')
|
|
67
59
|
@test_environment = ENV['TEST_ENVIRONMENT']
|
|
@@ -69,6 +61,7 @@ module TestCentricity
|
|
|
69
61
|
@language = ENV['LANGUAGE'] || 'English'
|
|
70
62
|
@screen_shots = []
|
|
71
63
|
|
|
64
|
+
attr_accessor :current
|
|
72
65
|
attr_accessor :test_environment
|
|
73
66
|
attr_accessor :app_host
|
|
74
67
|
attr_accessor :browser
|
|
@@ -154,8 +147,14 @@ module TestCentricity
|
|
|
154
147
|
else
|
|
155
148
|
"#{@protocol}://#{@user_id}:#{@password}@#{url}"
|
|
156
149
|
end
|
|
150
|
+
end
|
|
151
|
+
|
|
152
|
+
def self.current
|
|
153
|
+
@current
|
|
154
|
+
end
|
|
157
155
|
|
|
158
|
-
|
|
156
|
+
def self.current=(current)
|
|
157
|
+
@current = current
|
|
159
158
|
end
|
|
160
159
|
|
|
161
160
|
def self.driver_state
|
|
@@ -365,6 +365,16 @@ module TestCentricity
|
|
|
365
365
|
timeout = wait_time.nil? ? 5 : wait_time
|
|
366
366
|
data.each do |data_field, data_param|
|
|
367
367
|
unless data_param != false && data_param.blank?
|
|
368
|
+
# if data_field is a Symbol, find the corresponding object reference
|
|
369
|
+
if data_field.is_a?(Symbol)
|
|
370
|
+
begin
|
|
371
|
+
obj = method(data_field)
|
|
372
|
+
rescue
|
|
373
|
+
puts "No corresponding data field found for #{data_field}" if ENV['DEBUG']
|
|
374
|
+
next
|
|
375
|
+
end
|
|
376
|
+
data_field = obj.call
|
|
377
|
+
end
|
|
368
378
|
# make sure the intended UI target element is visible before trying to set its value
|
|
369
379
|
data_field.wait_until_visible(timeout)
|
|
370
380
|
if data_param == '!DELETE'
|
|
@@ -310,13 +310,7 @@ module TestCentricity
|
|
|
310
310
|
@capabilities
|
|
311
311
|
end
|
|
312
312
|
# specify endpoint url
|
|
313
|
-
if @endpoint.nil?
|
|
314
|
-
@endpoint = if ENV['APPIUM_SERVER_VERSION'] && ENV['APPIUM_SERVER_VERSION'].to_i == 1
|
|
315
|
-
'http://127.0.0.1:4723/wd/hub'
|
|
316
|
-
else
|
|
317
|
-
'http://127.0.0.1:4723'
|
|
318
|
-
end
|
|
319
|
-
end
|
|
313
|
+
@endpoint = 'http://127.0.0.1:4723' if @endpoint.nil?
|
|
320
314
|
register_remote_driver(Environ.browser, caps)
|
|
321
315
|
end
|
|
322
316
|
|
metadata
CHANGED
|
@@ -1,15 +1,29 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: testcentricity_web
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 4.
|
|
4
|
+
version: 4.7.0
|
|
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:
|
|
11
|
+
date: 2026-01-12 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
|
+
- !ruby/object:Gem::Dependency
|
|
14
|
+
name: activesupport
|
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
|
16
|
+
requirements:
|
|
17
|
+
- - ">="
|
|
18
|
+
- !ruby/object:Gem::Version
|
|
19
|
+
version: '4.0'
|
|
20
|
+
type: :development
|
|
21
|
+
prerelease: false
|
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
23
|
+
requirements:
|
|
24
|
+
- - ">="
|
|
25
|
+
- !ruby/object:Gem::Version
|
|
26
|
+
version: '4.0'
|
|
13
27
|
- !ruby/object:Gem::Dependency
|
|
14
28
|
name: axe-core-cucumber
|
|
15
29
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -44,14 +58,14 @@ dependencies:
|
|
|
44
58
|
requirements:
|
|
45
59
|
- - '='
|
|
46
60
|
- !ruby/object:Gem::Version
|
|
47
|
-
version: 10.
|
|
61
|
+
version: 10.2.0
|
|
48
62
|
type: :development
|
|
49
63
|
prerelease: false
|
|
50
64
|
version_requirements: !ruby/object:Gem::Requirement
|
|
51
65
|
requirements:
|
|
52
66
|
- - '='
|
|
53
67
|
- !ruby/object:Gem::Version
|
|
54
|
-
version: 10.
|
|
68
|
+
version: 10.2.0
|
|
55
69
|
- !ruby/object:Gem::Dependency
|
|
56
70
|
name: cuke_modeler
|
|
57
71
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -156,14 +170,14 @@ dependencies:
|
|
|
156
170
|
requirements:
|
|
157
171
|
- - "~>"
|
|
158
172
|
- !ruby/object:Gem::Version
|
|
159
|
-
version: 4.
|
|
173
|
+
version: 4.39.0
|
|
160
174
|
type: :development
|
|
161
175
|
prerelease: false
|
|
162
176
|
version_requirements: !ruby/object:Gem::Requirement
|
|
163
177
|
requirements:
|
|
164
178
|
- - "~>"
|
|
165
179
|
- !ruby/object:Gem::Version
|
|
166
|
-
version: 4.
|
|
180
|
+
version: 4.39.0
|
|
167
181
|
- !ruby/object:Gem::Dependency
|
|
168
182
|
name: simplecov
|
|
169
183
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -198,14 +212,14 @@ dependencies:
|
|
|
198
212
|
requirements:
|
|
199
213
|
- - "~>"
|
|
200
214
|
- !ruby/object:Gem::Version
|
|
201
|
-
version: 16.1.
|
|
215
|
+
version: 16.1.1
|
|
202
216
|
type: :runtime
|
|
203
217
|
prerelease: false
|
|
204
218
|
version_requirements: !ruby/object:Gem::Requirement
|
|
205
219
|
requirements:
|
|
206
220
|
- - "~>"
|
|
207
221
|
- !ruby/object:Gem::Version
|
|
208
|
-
version: 16.1.
|
|
222
|
+
version: 16.1.1
|
|
209
223
|
- !ruby/object:Gem::Dependency
|
|
210
224
|
name: browserstack-local
|
|
211
225
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -304,6 +318,20 @@ dependencies:
|
|
|
304
318
|
- - "~>"
|
|
305
319
|
- !ruby/object:Gem::Version
|
|
306
320
|
version: '1.0'
|
|
321
|
+
- !ruby/object:Gem::Dependency
|
|
322
|
+
name: smarter_csv
|
|
323
|
+
requirement: !ruby/object:Gem::Requirement
|
|
324
|
+
requirements:
|
|
325
|
+
- - ">="
|
|
326
|
+
- !ruby/object:Gem::Version
|
|
327
|
+
version: '0'
|
|
328
|
+
type: :runtime
|
|
329
|
+
prerelease: false
|
|
330
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
331
|
+
requirements:
|
|
332
|
+
- - ">="
|
|
333
|
+
- !ruby/object:Gem::Version
|
|
334
|
+
version: '0'
|
|
307
335
|
- !ruby/object:Gem::Dependency
|
|
308
336
|
name: test-unit
|
|
309
337
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -406,7 +434,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
406
434
|
version: '0'
|
|
407
435
|
requirements:
|
|
408
436
|
- Capybara, Selenium-WebDriver
|
|
409
|
-
rubygems_version: 3.4.
|
|
437
|
+
rubygems_version: 3.4.19
|
|
410
438
|
signing_key:
|
|
411
439
|
specification_version: 4
|
|
412
440
|
summary: A Page Object Model Framework for desktop and mobile web testing
|