cuke_master 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: d8af6036a448eebd944beec9e0c061fd3d8d0f65
4
+ data.tar.gz: 0aa508eb0bce87c6e1f602d70b79cac97dcf53d8
5
+ SHA512:
6
+ metadata.gz: 0018a501de6217e257277a4b4b7c19440f3051456d8443d60b2373b378911baf6069359b20426cb895eddc6e43bd72caa6a204a1f98948c6f3531774bce26415
7
+ data.tar.gz: 4bfb1083980a67426d32f7a521595a99410e38cfd321cfdd078f4805b31ff275d4250b4286430ba54c4939a66656aa4734f42a136632a422faca557ee8cf53ab
data/.gitignore ADDED
@@ -0,0 +1,11 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
10
+ .DS_Store
11
+ *.gem
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in cuke_master.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2017 James Huynh
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,41 @@
1
+ # CukeMaster
2
+
3
+ Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/cuke_master`. To experiment with that code, run `bin/console` for an interactive prompt.
4
+
5
+ TODO: Delete this and the text above, and describe your gem
6
+
7
+ ## Installation
8
+
9
+ Add this line to your application's Gemfile:
10
+
11
+ ```ruby
12
+ gem 'cuke_master'
13
+ ```
14
+
15
+ And then execute:
16
+
17
+ $ bundle
18
+
19
+ Or install it yourself as:
20
+
21
+ $ gem install cuke_master
22
+
23
+ ## Usage
24
+
25
+ TODO: Write usage instructions here
26
+
27
+ ## Development
28
+
29
+ After checking out the repo, run `bin/setup` to install dependencies. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
30
+
31
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
32
+
33
+ ## Contributing
34
+
35
+ Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/cuke_master.
36
+
37
+
38
+ ## License
39
+
40
+ The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
41
+
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require "bundler/gem_tasks"
2
+ task :default => :spec
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "cuke_master"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,38 @@
1
+ # coding: utf-8
2
+
3
+ lib = File.expand_path('../lib', __FILE__)
4
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
+ require 'cuke_master/version'
6
+
7
+ # rubocop:disable BlockLength
8
+ Gem::Specification.new do |spec|
9
+ spec.name = 'cuke_master'
10
+ spec.version = CukeMaster::VERSION
11
+ spec.authors = ['James Huynh']
12
+ spec.email = ['james@rubify.com']
13
+
14
+ spec.summary = %(Cuke Master Steps)
15
+ spec.description = %(CukeP Master Steps)
16
+ spec.homepage = 'https://github.com/jameshuynh/cuke-master'
17
+ spec.license = 'MIT'
18
+
19
+ # Prevent pushing this gem to RubyGems.org. To allow pushes either set the 'allowed_push_host'
20
+ # to allow pushing to a single host or delete this section to allow pushing to any host.
21
+
22
+ spec.files = `git ls-files -z`.split("\x0").reject do |f|
23
+ f.match(%r{^(test|spec|features)/})
24
+ end
25
+ spec.bindir = 'exe'
26
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
27
+ spec.require_paths = ['lib']
28
+
29
+ spec.add_development_dependency 'bundler', '~> 1.14'
30
+ spec.add_development_dependency 'rake', '~> 10.0'
31
+
32
+ spec.add_dependency 'capybara', '~> 2.14'
33
+ spec.add_dependency 'capybara-screenshot', '~> 1.0'
34
+ spec.add_dependency 'cucumber', '~> 2.4'
35
+ spec.add_dependency 'minitest', '~> 5.8'
36
+ spec.add_dependency 'selenium-webdriver', '~> 3.4'
37
+ spec.add_dependency 'activesupport', '~> 5.1'
38
+ end
@@ -0,0 +1,50 @@
1
+ require 'capybara'
2
+ require 'selenium-webdriver'
3
+ require 'capybara/dsl'
4
+ require 'capybara/cucumber'
5
+ require 'minitest/autorun'
6
+ require 'capybara-screenshot/cucumber'
7
+ require 'active_support/all'
8
+
9
+ Capybara.run_server = false
10
+ Capybara.register_driver :headless_chrome do |app|
11
+ path =
12
+ [
13
+ '/Applications',
14
+ "Google\ Chrome.app",
15
+ 'Contents/MacOS/',
16
+ "Google\ Chrome"
17
+ ].join('/')
18
+
19
+ caps = Selenium::WebDriver::Remote::Capabilities.chrome(
20
+ chromeOptions: {
21
+ binary: path,
22
+ # args: %w[--headless --disable-gpu --no-sandbox window-size=1440,968]
23
+ args: %w[--disable-gpu --no-sandbox window-size=1400,5000]
24
+ }
25
+ )
26
+
27
+ Capybara::Selenium::Driver.new(
28
+ app,
29
+ browser: :chrome,
30
+ desired_capabilities: caps
31
+ )
32
+ end
33
+
34
+ # Capybara.default_max_wait_time = 30
35
+ Capybara.default_max_wait_time = 5
36
+ Capybara.default_driver = :headless_chrome
37
+ Capybara.save_path = './screenshots'
38
+ Capybara::Screenshot.register_driver(:headless_chrome) do |driver, path|
39
+ driver.browser.save_screenshot(path)
40
+ end
41
+ Capybara::Screenshot.prune_strategy = :keep_last_run
42
+
43
+ def in_browser(name)
44
+ old_session = Capybara.session_name
45
+
46
+ Capybara.session_name = name
47
+ yield
48
+
49
+ Capybara.session_name = old_session
50
+ end
@@ -0,0 +1,330 @@
1
+ # rubocop:disable Lint/Debugger, HandleExceptions
2
+
3
+ # 1. ========= BROWSE ACTIONS ===========
4
+ # 1.1 Visit a URL
5
+ When(/^I visit the url "([^"]*)"$/) do |url|
6
+ visit url
7
+ @pos_number = {
8
+ first: 1,
9
+ second: 2,
10
+ third: 3,
11
+ fourth: 4,
12
+ fifth: 5,
13
+ sixth: 6,
14
+ seventh: 7,
15
+ eighth: 8,
16
+ nineth: 9,
17
+ tenth: 10,
18
+ eleventh: 11,
19
+ twelveth: 12,
20
+ thirdteeenth: 13
21
+ }
22
+ end
23
+
24
+ # 2. ========= CLICK ACTIONS =============
25
+ # 2.1 Click on a button or a link
26
+ When(/^I click on "([^"]*)"$/) do |content|
27
+ el = first(:xpath, ".//*[contains(text(), '#{content}')]")
28
+ el = first(:xpath, ".//*[@value='#{content}']") unless el
29
+ el.click
30
+ end
31
+
32
+ # 2.2 Click on a button (in case you have a link with the same display)
33
+ When(/^I click on button "([^"]*)"$/) do |content|
34
+ el = first(:xpath, ".//button[contains(text(), '#{content}')]")
35
+ el = first(:xpath, ".//input[@value='#{content}']") unless el
36
+ el.click
37
+ end
38
+
39
+ # 2.3 Click on the link (in case you have a link with the same display)
40
+ When(/^I click on the link "([^"]*)"$/) do |arg1|
41
+ click_link arg1
42
+ end
43
+
44
+ # 2.4 Click on the first link
45
+ When(/^I click on the first link "([^"]*)"$/) do |arg1|
46
+ first(:link, arg1).click
47
+ end
48
+
49
+ # 2.4 Click on link or button with an attribute value
50
+ When(/^I click on "([^"]*)" with attribute "([^"]*)" value "([^"]*)"$/) \
51
+ do |content, attribute, attribute_value|
52
+ el = first(:xpath, ".//*[contains(text(), '#{content}') and \
53
+ contains(@#{attribute}, '#{attribute_value}')]")
54
+ unless el
55
+ el = first(:xpath, ".//input[@value='#{content}' and \
56
+ contains(@#{attribute}, '#{attribute_value}')]")
57
+ end
58
+ el.click
59
+ end
60
+
61
+ # 2.5 Click on a random element with an attribute value
62
+ When(/^I click on tag "([^"]*)" with attribute "([^"]*)" value "([^"]*)"$/) \
63
+ do |tag, attribute, attribute_value|
64
+ el = first(:xpath, ".//#{tag}[contains(@#{attribute}, '#{attribute_value}')]")
65
+ el.click
66
+ end
67
+
68
+ # 2.6 Click on a button in the same row as something that I can see
69
+ When(/^I click on ([^"]*) "([^"]*)" with attribute "([^"]*)" value "([^"]*)" \
70
+ in the same row as "([^"]*)"$/) \
71
+ do |position, tag, attribute, attribute_value, seeable_content|
72
+ parent_el = find(:xpath, ".//tr[td[contains(text(), '#{seeable_content}')]]")
73
+ pos_number = @pos_number[position.to_sym]
74
+
75
+ el = first(:xpath, "#{parent_el.path}//\
76
+ #{tag}\
77
+ [contains(@#{attribute}, '#{attribute_value}')]\
78
+ [position()=#{pos_number}]")
79
+ el.click
80
+ end
81
+
82
+ # 2.7 Click on ordered element
83
+ When(/^I click on the ([^"]*) "([^"]*)" with attribute "([^"]*)" value \
84
+ "([^"]*)"/) do |position, tag, attribute, attribute_value|
85
+ pos_number = @pos_number[position.to_sym]
86
+ el = first(:xpath, ".//#{tag}[contains(@#{attribute}, '#{attribute_value}')]\
87
+ [position()=#{pos_number}]")
88
+ el.click
89
+ end
90
+
91
+ # 2.8 Click on a tag in the same box as something that I can see
92
+ When(/^I click on the ([^"]*) "([^"]*)" with attribute "([^"]*)" value \
93
+ "([^"]*)" within the same box as "([^"]*)" with attribute "([^"]*)" value \
94
+ "([^"]*)" as "([^"]*)"$/) \
95
+ do |position, tag, attribute, attribute_value, box_tag, \
96
+ box_attribute_name, box_attribute_value, seeable_content|
97
+ parent_el =
98
+ find(:xpath,
99
+ ".//#{box_tag}[contains(@#{box_attribute_name}, \
100
+ '#{box_attribute_value}')]\
101
+ //*[contains(text(), '#{seeable_content}')]")
102
+
103
+ pos_number = @pos_number[position.to_sym]
104
+ el = first(:xpath, "#{parent_el.path}//\
105
+ #{tag}\
106
+ [contains(@#{attribute}, '#{attribute_value}')]\
107
+ [position()=#{pos_number}]")
108
+ el.click
109
+ end
110
+
111
+ # 3. ========= FILL FORM ACTIONS ===========
112
+ # 3.1 Fill in a text field (given that the text field and the
113
+ # label are connected)
114
+ When(/^I fill in "([^"]*)" with "([^"]*)"$/) do |field_name, field_value|
115
+ fill_in field_name, with: field_value
116
+ end
117
+
118
+ # 3.2 Fill in a text field identified by placeholder
119
+ Then(/^I fill in field with placeholder "([^"]*)" with "([^"]*)"$/) \
120
+ do |placeholder, value|
121
+ first(:xpath, ".//*[@placeholder='#{placeholder}']").set(value)
122
+ end
123
+
124
+ # 3.3 Fill in a text field by field type
125
+ Then(/^I fill in field with type "([^"]*)" with "([^"]*)"$/) \
126
+ do |field_type, value|
127
+ first(:xpath, ".//*[@type='#{field_type}']").set(value)
128
+ end
129
+
130
+ # 3.4 Fill in a field with name
131
+ When(/^I fill in field name "([^"]*)" with "([^"]*)"$/) do |name, value|
132
+ first(:xpath, ".//*[@name='#{name}']").set(value)
133
+ end
134
+
135
+ # 3.5 Fill in a field identify by an attribute of the field
136
+ When(/^I fill in field with attribute "([^"]*)" value "([^"]*)" \
137
+ with "([^"]*)"$/) do |attribute, attribute_value, field_value|
138
+ input = first(:xpath, ".//*[contains(@#{attribute}), '#{attribute_value}')]")
139
+ if input.readonly?
140
+ page.execute_script \
141
+ "document
142
+ .querySelector(
143
+ 'input[#{attribute}=\"#{attribute_value}\"]'
144
+ ).readOnly = false;"
145
+ end
146
+ input.set(field_value)
147
+ end
148
+
149
+ # 3.6 Select an option from a dropdown box
150
+ When(/^I select "([^"]*)" from "([^"]*)"$/) do |option, select|
151
+ select option, from: select
152
+ end
153
+
154
+ # 3.7. Select an option from a dropdown box identified by attribute
155
+ When(/^I select "([^"]*)" from drop down with \
156
+ attribute "([^"]*)" value "([^"]*)"$/) do |option, attribute, value|
157
+ select = first(:xpath, ".//select[contains(@#{attribute}, '#{value}')]")
158
+
159
+ if select.nil?
160
+ raise "No such select found with attribute \"#{attribute}\" ~= \"#{value}\""
161
+ end
162
+
163
+ option = select.find(:xpath, "option[contains(text(), '#{option}')]")
164
+
165
+ raise "No option found with text #{option}" if option.nil?
166
+ option.select_option
167
+ end
168
+
169
+ # 3.8 Select a date in date picker
170
+ # Use the command to fill in a text field
171
+
172
+ # 3.9 Upload a file
173
+ When(/^I attach file to "([^"]*)" with "([^"]*)"$/) do |field_name, file_path|
174
+ root_folder = File.expand_path('..', File.expand_path(File.dirname(__FILE__)))
175
+ root_folder = File.expand_path('..', root_folder)
176
+ attach_file field_name, "#{root_folder}/uploads/#{file_path}"
177
+ end
178
+
179
+ # 3.10 Fill in a with class name
180
+ When(/^I fill in ([^"]*) field with attribute "([^"]*)" value "([^"]*)" with \
181
+ "([^"]*)"$/) do |position, attribute_name, attribute_value, value|
182
+ pos_number = @pos_number[position.to_sym]
183
+
184
+ els = all(:xpath, ".//*[contains(@#{attribute_name}, '#{attribute_value}')]")
185
+ el = els[pos_number - 1]
186
+ el.set(value)
187
+ end
188
+
189
+ # 3.11 Upload a file
190
+ When(/^I attach file to field with attribute "([^"]*)" value "([^"]*)" with \
191
+ "([^"]*)"$/) do |attribute_name, attribute_value, file_path|
192
+ root_folder = File.expand_path('..', File.expand_path(File.dirname(__FILE__)))
193
+ root_folder = File.expand_path('..', root_folder)
194
+ page.execute_script \
195
+ "document
196
+ .querySelector(
197
+ 'input[#{attribute_name}=\"#{attribute_value}\"]'
198
+ ).style.display = 'block';"
199
+ page.execute_script \
200
+ "document
201
+ .querySelector(
202
+ 'input[#{attribute_name}=\"#{attribute_value}\"]'
203
+ ).name = 'uniqueFieldForCapybara';"
204
+
205
+ attach_file 'uniqueFieldForCapybara',
206
+ "#{root_folder}/uploads/#{file_path}",
207
+ visible: false
208
+ end
209
+
210
+ # 4. ========= CHECKING ACTIONS ===========
211
+ # 4.1 Check what can be seen on the page
212
+ Then(/^I should see "([^"]*)"$/) do |arg1|
213
+ assert page.has_content?(arg1)
214
+ end
215
+
216
+ # 4.2 Advanced checking of content based on html tag
217
+ Then(/^I should see tag "([^"]*)" with content "([^"]*)"$/) do |tag, content|
218
+ assert page.has_selector?(tag, text: content, visible: true)
219
+ end
220
+
221
+ # 5. ========= MISC ACTIONS ===========
222
+ # 5.1 Pause
223
+ Then(/^pause for ([^"]*) seconds$/) do |duration|
224
+ sleep duration.to_i
225
+ end
226
+
227
+ # 5.2 Take screenshot
228
+ Then(/^I take screenshot$/) do
229
+ save_screenshot(nil, full: true)
230
+ end
231
+
232
+ # 5.3 Scroll down
233
+ Then(/^I scroll down "([^"]*)"$/) do |scroll|
234
+ scroll = scroll.gsub('px', '')
235
+ page.execute_script "window.scrollBy(0, #{scroll})"
236
+ end
237
+
238
+ # 6. ========== ADVANCED SELECTOR ==========
239
+ # 6.1 Perform action in iframe
240
+ Then(/^(.*) in the iframe "([^"]*)"$/) do |step, iframe_name|
241
+ browser = page.driver.browser
242
+ browser.switch_to.frame(iframe_name)
243
+ step(step)
244
+ browser.switch_to.default_content
245
+ end
246
+
247
+ # 6.2 Perform action and ignore if error occurs
248
+ Then(/^(.*) if available$/) do |step|
249
+ begin
250
+ step(step)
251
+ rescue
252
+ # do nothing
253
+ end
254
+ end
255
+
256
+ # 6.3 within first tag with attribute ... value ...
257
+ Then(/^(.*) within ([^"]*) "([^"]*)" with attribute "([^"]*)" value \
258
+ "([^"]*)"/) do |step, position, tag, attribute_name, attribute_value|
259
+ pos_number = @pos_number[position.to_sym]
260
+ within(:xpath,
261
+ ".//#{tag}[contains(@#{attribute_name}, '#{attribute_value}')]\
262
+ [position()=#{pos_number}]") do
263
+ step(step)
264
+ end
265
+ end
266
+
267
+ # 6.4 In browser
268
+ Then(/^(.*) in browser "([^"]*)"/) do |step, browser_name|
269
+ in_browser(browser_name.to_sym) do
270
+ step(step)
271
+ end
272
+ end
273
+
274
+ # 7. ========= MEMORY ==============
275
+ # 7.1 Remember a variable
276
+ Then(/^I remember "([^"]*)" as "([^"]*)"$/) do |name, value|
277
+ instance_variable_set("@#{name}", value)
278
+ end
279
+
280
+ # 7.2 Remember as content of a div
281
+ Then(/^I remember "([^"]*)" as content of "([^"]*)" with attribute "([^"]*)" \
282
+ value "([^"]*)"$/) do |name, tag, attribute, value|
283
+ content = first(:xpath, ".//#{tag}[@#{attribute}='#{value}']")['innerText']
284
+ instance_variable_set("@#{name}", content)
285
+ end
286
+
287
+ # ============== TRANSFORMING =====================
288
+ Transform(/^\[([^"]*)\]$/) do |string|
289
+ val = instance_variable_get("@#{string}")
290
+ if val
291
+ val
292
+ else
293
+ string
294
+ end
295
+ end
296
+
297
+ # ============== TRANSFORMING =====================
298
+ Transform(/^([^"]*) from now( with format ([^"]*))?$/) \
299
+ do |string, _tmp, format|
300
+ number = string.split(' ')[0]
301
+ unit = string.split(' ')[1]
302
+ date_format = case format
303
+ when 'd-m-y'
304
+ '%d-%m-%Y'
305
+ when 'y-m-d'
306
+ '%Y-%m-%d'
307
+ when 'm-d-Y'
308
+ '%m-%d-%Y'
309
+ else
310
+ '%d-%m-%Y'
311
+ end
312
+ (Date.today + number.to_i.send(unit)).strftime(date_format)
313
+ end
314
+
315
+ Transform(/^([^"]*) prior to now( with format ([^"]*))?$/) \
316
+ do |string, _tmp, format|
317
+ number = string.split(' ')[0]
318
+ unit = string.split(' ')[1]
319
+ date_format = case format
320
+ when 'd-m-y'
321
+ '%d-%m-%Y'
322
+ when 'y-m-d'
323
+ '%Y-%m-%d'
324
+ when 'm-d-Y'
325
+ '%m-%d-%Y'
326
+ else
327
+ '%d-%m-%Y'
328
+ end
329
+ (Date.today - number.to_i.send(unit)).strftime(date_format)
330
+ end
@@ -0,0 +1,3 @@
1
+ module CukeMaster
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,5 @@
1
+ require "cuke_master/version"
2
+
3
+ module CukeMaster
4
+ # Your code goes here...
5
+ end