testcentricity_web 0.5.6 → 0.5.7
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +8 -0
- data/LICENSE.txt +2 -2
- data/README.md +117 -39
- data/lib/testcentricity_web.rb +24 -9
- data/lib/testcentricity_web/page_objects_helper.rb +0 -1
- data/lib/testcentricity_web/page_sections_helper.rb +0 -1
- data/lib/testcentricity_web/version.rb +1 -1
- data/testcentricity_web.gemspec +5 -6
- metadata +7 -36
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f8114408f91a111679a8117c65384050040eacf8
|
4
|
+
data.tar.gz: 80bf1711744152b92dbe5394cf520431d1feca99
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fca8c04fa90c2d8122a5729ca1cb5e5f7afde04621f2afda77a2b0529169adfb655e8545999209bbc52c656c3418d894cee234bfe221cd216d45c7d8f8a8da78
|
7
|
+
data.tar.gz: 7e65e2d4cf450772d12f2b78583ba042f3f9449278b2680e2e02a694706721a61e231c49e10a319be49145bf174cc831d2674c9e64a4e5b326f2ec5ed9edc422
|
data/.gitignore
CHANGED
@@ -7,6 +7,8 @@ Thumbs.db
|
|
7
7
|
.settings
|
8
8
|
.project
|
9
9
|
.idea/workspace.xml
|
10
|
+
.idea/.rakeTasks
|
11
|
+
*.iml
|
10
12
|
|
11
13
|
doc/*
|
12
14
|
.yardoc/*
|
@@ -15,5 +17,11 @@ coverage
|
|
15
17
|
.bundle
|
16
18
|
.ruby-version
|
17
19
|
.ruby-gemset
|
20
|
+
/my_templates
|
18
21
|
|
19
22
|
Gemfile.lock
|
23
|
+
|
24
|
+
|
25
|
+
.idea/testcentricity_web.iml
|
26
|
+
|
27
|
+
.idea/.rakeTasks
|
data/LICENSE.txt
CHANGED
@@ -6,10 +6,10 @@ Redistribution and use in source and binary forms, with or without
|
|
6
6
|
modification, are permitted provided that the following conditions are met:
|
7
7
|
|
8
8
|
1. Redistributions of source code must retain the above copyright notice,
|
9
|
-
this list of conditions and the following disclaimer.
|
9
|
+
this list of conditions, and the following disclaimer.
|
10
10
|
|
11
11
|
2. Redistributions in binary form must reproduce the above copyright
|
12
|
-
notice, this list of conditions and the following disclaimer in the
|
12
|
+
notice, this list of conditions, and the following disclaimer in the
|
13
13
|
documentation and/or other materials provided with the distribution.
|
14
14
|
|
15
15
|
3. Neither the name of the copyright holder nor the names of its contributors
|
data/README.md
CHANGED
@@ -1,10 +1,9 @@
|
|
1
|
-
#
|
1
|
+
# TestCentricityWeb
|
2
2
|
|
3
|
-
The TestCentricity™ core generic framework for desktop and
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
or CrossBrowserTesting services.
|
3
|
+
The TestCentricity™ core generic framework for desktop and mobile web site testing implements a Page Object and Data Object Model DSL for
|
4
|
+
use with Cucumber, Capybara, and selenium-webdriver. It supports testing against locally hosted desktop browsers (Firefox, Chrome, Safari,
|
5
|
+
IE, or Edge), locally hosted emulated iOS and Android mobile browsers (using Firefox), a "headless" browser (using Poltergeist and PhantomJS),
|
6
|
+
or on cloud hosted desktop or mobile web browsers using the BrowserStack, Sauce Labs, or CrossBrowserTesting services.
|
8
7
|
|
9
8
|
|
10
9
|
## Installation
|
@@ -43,8 +42,8 @@ If you are using RSpec instead, you need to require the following in your *env.r
|
|
43
42
|
|
44
43
|
###Selenium WebDriver
|
45
44
|
|
46
|
-
If you choose to not connect to selenium-webdriver using the ***WebDriverConnect.initialize_web_driver*** method, or if you need to
|
47
|
-
|
45
|
+
If you choose to not connect to selenium-webdriver using the ***WebDriverConnect.initialize_web_driver*** method, or if you need to directly
|
46
|
+
call methods in selenium-webdriver, you will also need to require the following in your *env.rb* file:
|
48
47
|
|
49
48
|
require 'selenium-webdriver'
|
50
49
|
|
@@ -52,9 +51,23 @@ directly call methods in selenium-webdriver, you will also need to require the f
|
|
52
51
|
|
53
52
|
##Usage
|
54
53
|
|
55
|
-
###
|
54
|
+
### Page Objects
|
56
55
|
|
57
|
-
|
56
|
+
The **Page Object Model** is a test automation pattern that aims to create an abstraction of your web app's User Interface that can be used
|
57
|
+
in tests. A **Page Object** is an object that represents a single page in your AUT (Application Under Test). **Page Objects** encapsulate the
|
58
|
+
implementation details of a web page and expose an API that supports interaction with, and validation of UI elements on the page.
|
59
|
+
|
60
|
+
**Page Objects** makes it easier to maintain automated tests, because changes to page UI elements are only changed in one location - in the
|
61
|
+
**Page Object** class definition. By adopting a **Page Object Model**, Cucumber Feature files and step definitions are no longer required to
|
62
|
+
hold specific information about a page's UI objects, thus minimizing maintenance requirements. If any element on a page changes (URL path,
|
63
|
+
text field attributes, button captions, etc.), maintenance is performed in the **Page Object** class definition only, typically with no need
|
64
|
+
to update the affected feature file, scenarios, or step definitions.
|
65
|
+
|
66
|
+
|
67
|
+
####Defining a Page Object
|
68
|
+
|
69
|
+
Your **Page Object** class definitions should be contained within individual *.rb* files in the ***features/support/pages*** folder of your
|
70
|
+
test automation project. You define new **Page Objects** as shown below:
|
58
71
|
|
59
72
|
class LoginPage < TestCentricity::PageObject
|
60
73
|
trait(:page_name) { 'Login' }
|
@@ -70,9 +83,9 @@ You define new **Page Objects** as shown below:
|
|
70
83
|
end
|
71
84
|
|
72
85
|
|
73
|
-
|
86
|
+
####Adding UI Elements to your Page Object
|
74
87
|
|
75
|
-
|
88
|
+
**UI Elements** are added to your **Page Object** class definition as shown below:
|
76
89
|
|
77
90
|
class LoginPage < TestCentricity::PageObject
|
78
91
|
trait(:page_name) { 'Login' }
|
@@ -86,32 +99,20 @@ Your Page Object's **UI Elements** are added as shown below:
|
|
86
99
|
checkbox :remember_checkbox, "rememberUser']"
|
87
100
|
label :error_message_label, 'div#statusBar.login-error'
|
88
101
|
end
|
89
|
-
|
90
|
-
|
91
|
-
###Instantiating your Page Objects
|
92
|
-
|
93
|
-
There are several ways to instantiate your **Page Objects**. One common implementation is shown below:
|
94
|
-
|
95
|
-
module WorldPages
|
96
|
-
def login_page
|
97
|
-
@login_page ||= LoginPage.new
|
98
|
-
end
|
99
102
|
|
100
|
-
|
101
|
-
|
102
|
-
end
|
103
|
-
end
|
104
|
-
|
105
|
-
Once instantiated, you can interact with the **UI Elements** in your **Page Objects**. An example is shown below:
|
103
|
+
Once your **Page Objects** have been instantiated, you can interact with the **UI Elements** in your **Page Objects**. An example is shown
|
104
|
+
below:
|
106
105
|
|
107
106
|
login_page.user_id_field.set('snicklefritz')
|
108
107
|
login_page.password_field.set('Pa55w0rd')
|
109
108
|
login_page.login_button.click
|
110
109
|
|
111
110
|
|
112
|
-
|
111
|
+
####Adding Methods to your Page Object
|
113
112
|
|
114
|
-
|
113
|
+
It is good practice for your Cucumber step definitions to call high level methods in your your **Page Object** instead of directly accessing
|
114
|
+
and interacting with a page object's UI elements. You can add high level methods to your **Page Object** class definition for interacting with
|
115
|
+
the UI to hide implementation details, as shown below:
|
115
116
|
|
116
117
|
class LoginPage < TestCentricity::PageObject
|
117
118
|
trait(:page_name) { 'Login' }
|
@@ -144,18 +145,28 @@ Once your **Page Objects** have been instantiated, you can call your methods as
|
|
144
145
|
|
145
146
|
|
146
147
|
|
147
|
-
###
|
148
|
+
### PageSection Objects
|
149
|
+
|
150
|
+
A **PageSection Object** is a collection of **UI Elements** that may appear in multiple locations on a page, or on multiple pages in a web
|
151
|
+
app. It is a collection of **UI Elements** that represent a conceptual area of functionality, like a navigation bar, a search capability,
|
152
|
+
or a menu. **UI Elements** and functional behavior are confined to the scope of a **PageSection Object**.
|
153
|
+
|
154
|
+
A **PageSection Object** may contain other **PageSection Objects**.
|
155
|
+
|
148
156
|
|
149
|
-
|
157
|
+
####Defining a PageSection Object
|
158
|
+
|
159
|
+
Your **PageSection** class definitions should be contained within individual *.rb* files in the ***features/support/sections*** folder of
|
160
|
+
your test automation project. You define new **PageSection Objects** as shown below:
|
150
161
|
|
151
162
|
class SearchForm < TestCentricity::PageSection
|
152
163
|
trait(:section_locator) { "//form[@id='gnav-search']" }
|
153
164
|
end
|
154
165
|
|
155
166
|
|
156
|
-
|
167
|
+
####Adding UI Elements to your PageSection Object
|
157
168
|
|
158
|
-
|
169
|
+
**UI Elements** are added to your **PageSection** class definition as shown below:
|
159
170
|
|
160
171
|
class SearchForm < TestCentricity::PageSection
|
161
172
|
trait(:section_locator) { "//form[@id='gnav-search']" }
|
@@ -166,9 +177,9 @@ Your PageSection Object's **UI Elements** are added as shown below:
|
|
166
177
|
end
|
167
178
|
|
168
179
|
|
169
|
-
|
180
|
+
####Adding Methods to your PageSection Object
|
170
181
|
|
171
|
-
You can add high level methods to your PageSection
|
182
|
+
You can add high level methods to your **PageSection** class definition, as shown below:
|
172
183
|
|
173
184
|
class SearchForm < TestCentricity::PageSection
|
174
185
|
trait(:section_locator) { "//form[@id='gnav-search']" }
|
@@ -184,9 +195,9 @@ You can add high level methods to your PageSection Objects, as shown below:
|
|
184
195
|
end
|
185
196
|
|
186
197
|
|
187
|
-
|
198
|
+
####Adding PageSection Objects to your Page Object
|
188
199
|
|
189
|
-
|
200
|
+
You add a **PageSection Object** to its associated **Page Object** as shown below:
|
190
201
|
|
191
202
|
class HomePage < TestCentricity::PageObject
|
192
203
|
trait(:page_name) { 'Home' }
|
@@ -203,9 +214,76 @@ Once your **Page Object** has been instantiated, you can call its **PageSection*
|
|
203
214
|
|
204
215
|
|
205
216
|
|
217
|
+
###Instantiating your Page Objects
|
218
|
+
|
219
|
+
Before you can call the methods in your **Page Objects** and **PageSection Objects**, you must instantiate the **Page Objects** of your
|
220
|
+
web application, as well as create instance variables which can be used when calling a **Page Objects** methods from your step definitions.
|
221
|
+
There are several ways to instantiate your **Page Objects**.
|
222
|
+
|
223
|
+
One common implementation is shown below:
|
224
|
+
|
225
|
+
module WorldPages
|
226
|
+
def login_page
|
227
|
+
@login_page ||= LoginPage.new
|
228
|
+
end
|
229
|
+
|
230
|
+
def home_page
|
231
|
+
@home_page ||= HomePage.new
|
232
|
+
end
|
233
|
+
|
234
|
+
def registration_page
|
235
|
+
@registration_page ||= RegistrationPage.new
|
236
|
+
end
|
237
|
+
end
|
238
|
+
|
239
|
+
World(WorldPages)
|
240
|
+
|
241
|
+
The **WorldPages** module above can be defined in your *env.rb* file, or you can define it in a separate *world_pages.rb* file in the
|
242
|
+
***features/support*** folder.
|
243
|
+
|
244
|
+
While this approach is effective for small web applications with only a few pages (and hence few **Page Objects**), it quickly becomes
|
245
|
+
cumbersome to manage if your web application has dozens of **Page Objects** that need to be instantiated and managed.
|
246
|
+
|
247
|
+
####Using the PageManager
|
248
|
+
|
249
|
+
The **PageManager** class provides methods for supporting the instantiation and management of **Page Objects**. In the code example below,
|
250
|
+
the **page_objects** method contains a hash table of your **Page Object** instance variables and their associated **Page Object** classes
|
251
|
+
to be instantiated by **PageManager**:
|
252
|
+
|
253
|
+
module WorldPages
|
254
|
+
def page_objects
|
255
|
+
{ :login_page => LoginPage,
|
256
|
+
:home_page => HomePage,
|
257
|
+
:registration_page => RegistrationPage,
|
258
|
+
:products_grid_page => ProductsCollectionPage,
|
259
|
+
:product_detail_page => ProductDetailPage,
|
260
|
+
:shopping_basket_page => ShoppingBasketPage,
|
261
|
+
:payment_method_page => PaymentMethodPage,
|
262
|
+
:confirm_purchase_page => PurchaseConfirmationPage,
|
263
|
+
:my_account_page => MyAccountPage,
|
264
|
+
:my_order_history_page => MyOrderHistoryPage,
|
265
|
+
:my_ship_to_addresses_page => MyShipToAddressesPage
|
266
|
+
}
|
267
|
+
end
|
268
|
+
end
|
269
|
+
|
270
|
+
World(WorldPages)
|
271
|
+
|
272
|
+
The **WorldPages** module above should be defined in the *world_pages.rb* file in the ***features/support*** folder.
|
273
|
+
|
274
|
+
Include the code below in your *env.rb* file to ensure that your **Page Objects** are instantiated before your Cucumber scenarios are
|
275
|
+
executed:
|
276
|
+
|
277
|
+
include WorldPages
|
278
|
+
WorldPages.instantiate_page_objects
|
279
|
+
|
280
|
+
|
281
|
+
|
282
|
+
|
283
|
+
|
206
284
|
## Copyright and License
|
207
285
|
|
208
|
-
TestCentricity
|
286
|
+
TestCentricity™ Framework is Copyright (c) 2014-2016, Tony Mrozinski.
|
209
287
|
All rights reserved.
|
210
288
|
|
211
289
|
|
data/lib/testcentricity_web.rb
CHANGED
@@ -1,5 +1,4 @@
|
|
1
1
|
require 'capybara/cucumber'
|
2
|
-
require 'rspec/expectations'
|
3
2
|
require 'test/unit'
|
4
3
|
require 'capybara/poltergeist'
|
5
4
|
require 'testcentricity_web/world_extensions'
|
@@ -32,23 +31,37 @@ module TestCentricity
|
|
32
31
|
end
|
33
32
|
end
|
34
33
|
|
34
|
+
# Have all PageObjects been registered?
|
35
|
+
#
|
36
|
+
# @return [Boolean] true if all PageObjects have been registered
|
37
|
+
# @example
|
38
|
+
# TestCentricity::PageManager.loaded?
|
39
|
+
#
|
35
40
|
def self.loaded?
|
36
41
|
not @page_objects.empty?
|
37
42
|
end
|
38
43
|
|
39
|
-
def self.pages
|
40
|
-
@page_objects
|
41
|
-
end
|
42
|
-
|
43
44
|
def self.find_page(page_name)
|
44
45
|
(page_name.is_a? String) ? page_id = page_name.gsub(/\s+/, "").downcase.to_sym : page_id = page_name
|
45
46
|
@page_objects[page_id]
|
46
47
|
end
|
47
48
|
|
49
|
+
# Get the currently active PageObject
|
50
|
+
#
|
51
|
+
# @return [PageObject]
|
52
|
+
# @example
|
53
|
+
# active_page = TestCentricity::PageManager.current_page
|
54
|
+
#
|
48
55
|
def self.current_page
|
49
56
|
@current_page
|
50
57
|
end
|
51
58
|
|
59
|
+
# Sets the currently active PageObject
|
60
|
+
#
|
61
|
+
# @param page [PageObject] Reference to the active PageObject
|
62
|
+
# @example
|
63
|
+
# TestCentricity::PageManager.set_current_page(product_search_page)
|
64
|
+
#
|
52
65
|
def self.set_current_page(page)
|
53
66
|
@current_page = page
|
54
67
|
end
|
@@ -62,12 +75,14 @@ module TestCentricity
|
|
62
75
|
@data_objects[data_type] = data_class unless @data_objects.has_key?(data_type)
|
63
76
|
end
|
64
77
|
|
78
|
+
# Have all DataObjects been registered?
|
79
|
+
#
|
80
|
+
# @return [Boolean] true if all DataObjects have been registered
|
81
|
+
# @example
|
82
|
+
# TestCentricity::DataManager.loaded?
|
83
|
+
#
|
65
84
|
def self.loaded?
|
66
85
|
not @data_objects.empty?
|
67
86
|
end
|
68
|
-
|
69
|
-
def self.data_objects
|
70
|
-
@data_objects
|
71
|
-
end
|
72
87
|
end
|
73
88
|
end
|
data/testcentricity_web.gemspec
CHANGED
@@ -12,10 +12,11 @@ Gem::Specification.new do |spec|
|
|
12
12
|
spec.email = ['test_automation@icloud.com']
|
13
13
|
spec.summary = %q{A Page Object and Data Object Model Framework for desktop and responsive mobile web testing}
|
14
14
|
spec.description = %q{
|
15
|
-
TestCentricity™ core generic framework for desktop and
|
16
|
-
|
17
|
-
(Firefox, Chrome, Safari, IE, or Edge), locally hosted emulated mobile browsers (using Firefox),
|
18
|
-
Poltergeist), or on cloud hosted browsers using the BrowserStack, Sauce Labs,
|
15
|
+
TestCentricity™ core generic framework for desktop and mobile web site testing implements a Page Object Model DSL,
|
16
|
+
for use with Cucumber, Capybara, and selenium-webdriver. Supports testing against locally hosted desktop browsers
|
17
|
+
(Firefox, Chrome, Safari, IE, or Edge), locally hosted emulated iOS and Android mobile browsers (using Firefox), a
|
18
|
+
"headless" browser (using Poltergeist and PhantomJS), or on cloud hosted browsers using the BrowserStack, Sauce Labs,
|
19
|
+
or CrossBrowserTesting services.}
|
19
20
|
spec.homepage = ''
|
20
21
|
spec.license = 'BSD3'
|
21
22
|
|
@@ -28,8 +29,6 @@ Gem::Specification.new do |spec|
|
|
28
29
|
spec.add_development_dependency 'rake'
|
29
30
|
|
30
31
|
spec.add_dependency 'capybara', ['>= 2.1', '< 3.0']
|
31
|
-
spec.add_dependency 'rspec-expectations'
|
32
|
-
spec.add_dependency 'rspec'
|
33
32
|
spec.add_dependency 'test-unit'
|
34
33
|
spec.add_dependency 'poltergeist'
|
35
34
|
spec.add_dependency 'selenium-webdriver', '>= 2.50.0'
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: testcentricity_web
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.5.
|
4
|
+
version: 0.5.7
|
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: 2016-03-
|
11
|
+
date: 2016-03-18 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -58,34 +58,6 @@ dependencies:
|
|
58
58
|
- - "<"
|
59
59
|
- !ruby/object:Gem::Version
|
60
60
|
version: '3.0'
|
61
|
-
- !ruby/object:Gem::Dependency
|
62
|
-
name: rspec-expectations
|
63
|
-
requirement: !ruby/object:Gem::Requirement
|
64
|
-
requirements:
|
65
|
-
- - ">="
|
66
|
-
- !ruby/object:Gem::Version
|
67
|
-
version: '0'
|
68
|
-
type: :runtime
|
69
|
-
prerelease: false
|
70
|
-
version_requirements: !ruby/object:Gem::Requirement
|
71
|
-
requirements:
|
72
|
-
- - ">="
|
73
|
-
- !ruby/object:Gem::Version
|
74
|
-
version: '0'
|
75
|
-
- !ruby/object:Gem::Dependency
|
76
|
-
name: rspec
|
77
|
-
requirement: !ruby/object:Gem::Requirement
|
78
|
-
requirements:
|
79
|
-
- - ">="
|
80
|
-
- !ruby/object:Gem::Version
|
81
|
-
version: '0'
|
82
|
-
type: :runtime
|
83
|
-
prerelease: false
|
84
|
-
version_requirements: !ruby/object:Gem::Requirement
|
85
|
-
requirements:
|
86
|
-
- - ">="
|
87
|
-
- !ruby/object:Gem::Version
|
88
|
-
version: '0'
|
89
61
|
- !ruby/object:Gem::Dependency
|
90
62
|
name: test-unit
|
91
63
|
requirement: !ruby/object:Gem::Requirement
|
@@ -172,10 +144,11 @@ dependencies:
|
|
172
144
|
version: 1.1.1
|
173
145
|
description: |2-
|
174
146
|
|
175
|
-
TestCentricity™ core generic framework for desktop and
|
176
|
-
|
177
|
-
(Firefox, Chrome, Safari, IE, or Edge), locally hosted emulated mobile browsers (using Firefox),
|
178
|
-
Poltergeist), or on cloud hosted browsers using the BrowserStack, Sauce Labs,
|
147
|
+
TestCentricity™ core generic framework for desktop and mobile web site testing implements a Page Object Model DSL,
|
148
|
+
for use with Cucumber, Capybara, and selenium-webdriver. Supports testing against locally hosted desktop browsers
|
149
|
+
(Firefox, Chrome, Safari, IE, or Edge), locally hosted emulated iOS and Android mobile browsers (using Firefox), a
|
150
|
+
"headless" browser (using Poltergeist and PhantomJS), or on cloud hosted browsers using the BrowserStack, Sauce Labs,
|
151
|
+
or CrossBrowserTesting services.
|
179
152
|
email:
|
180
153
|
- test_automation@icloud.com
|
181
154
|
executables: []
|
@@ -184,11 +157,9 @@ extra_rdoc_files: []
|
|
184
157
|
files:
|
185
158
|
- ".gitignore"
|
186
159
|
- ".idea/.name"
|
187
|
-
- ".idea/.rakeTasks"
|
188
160
|
- ".idea/encodings.xml"
|
189
161
|
- ".idea/misc.xml"
|
190
162
|
- ".idea/modules.xml"
|
191
|
-
- ".idea/testcentricity_web.iml"
|
192
163
|
- ".idea/vcs.xml"
|
193
164
|
- Gemfile
|
194
165
|
- LICENSE.txt
|