effective_test_bot 0.7.0 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +46 -47
- data/app/helpers/effective_test_bot_controller_helper.rb +46 -32
- data/config/application_system_test_case.rb +8 -0
- data/config/test_helper.rb +12 -70
- data/lib/effective_test_bot.rb +0 -1
- data/lib/effective_test_bot/engine.rb +4 -26
- data/lib/effective_test_bot/version.rb +1 -1
- data/lib/generators/effective_test_bot/install_generator.rb +3 -8
- data/lib/tasks/effective_test_bot_tasks.rake +3 -29
- data/test/support/effective_test_bot_assertions.rb +9 -22
- data/test/support/effective_test_bot_form_helper.rb +0 -2
- data/test/support/effective_test_bot_screenshots_helper.rb +2 -3
- data/test/support/effective_test_bot_test_helper.rb +13 -16
- data/test/test_bot/{integration → system}/application_test.rb +2 -2
- data/test/test_bot/{integration → system}/environment_test.rb +5 -4
- data/test/test_botable/base_test.rb +1 -4
- metadata +24 -94
- data/lib/effective_test_bot/middleware.rb +0 -40
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 64b44fba9d50f01fd32b612de3d11d810c6ba12a
|
4
|
+
data.tar.gz: a07e93aee37f18a0af63098c6ac6ac540d61d8a8
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 5ba5cc490a7296da4d6a82f33faa5cc7bce2f8b2cbe29b01b913812bd59963b0381d73c58d886792144a8a318f27c56389ebdbc5412451abcf624863f0e6bbc7
|
7
|
+
data.tar.gz: fc19738de32fde123f04dd8b606eb17627236601323dc8a9267d58a5d88ca195a467943a97a5ba9efb9fe6a0004b8711bb1fc3c37ffe1863f69309e391a1c75f
|
data/README.md
CHANGED
@@ -2,32 +2,32 @@
|
|
2
2
|
|
3
3
|
Stop testing and start test botting.
|
4
4
|
|
5
|
-
A [minitest](https://github.com/seattlerb/minitest) library of [capybara](https://github.com/jnicklas/capybara) based
|
5
|
+
A [minitest](https://github.com/seattlerb/minitest) library of [capybara](https://github.com/jnicklas/capybara) based Rails System Tests that should pass in every Ruby on Rails application.
|
6
6
|
|
7
7
|
Adds many additional assertions and quality of life helper functions.
|
8
8
|
|
9
9
|
Provides a curated set of minitest and capybara focused rails testing gems and a well configured `test_helper.rb` file.
|
10
10
|
|
11
|
-
Run `rails test:bot:environment` to validate your testing environment.
|
11
|
+
Run `rails test:bot:environment` to validate your testing environment. Ensures that all fixtures and seeds are properly initialized. Makes sure database transactions and web sessions correctly reset between tests.
|
12
12
|
|
13
13
|
Adds many class and instance level 1-liners to run entire test suites and check many assertions all at once.
|
14
14
|
|
15
15
|
Autosaves an animated .gif for any failing test.
|
16
16
|
|
17
|
-
Run `rails test:bot` to automatically check every route in your application against an appropriate test suite, without writing any code.
|
17
|
+
Run `rails test:bot` to automatically check every route in your application against an appropriate test suite, without writing any code. Clicks through every page, intelligently fills forms with appropriate pseudo-random input and checks for all kinds of errors and omissions.
|
18
18
|
|
19
19
|
Turn on tour mode to programatically generate an animated .gif of every workflow in your website.
|
20
20
|
|
21
21
|
Make sure everything actually works.
|
22
22
|
|
23
|
-
## Capybara Webkit
|
24
23
|
|
25
|
-
|
24
|
+
## Rails System Tests
|
26
25
|
|
27
|
-
|
26
|
+
This is the 'Rails System Test' branch of effective_test_bot.
|
28
27
|
|
29
|
-
|
28
|
+
This requires Rails 5.1+
|
30
29
|
|
30
|
+
Please check out [Effective TestBot Capybara-Webkit branch](https://github.com/code-and-effect/effective_test_bot/tree/capybara-webit) for more information using this gem with Capybara Webkit and Rails < 5.1.
|
31
31
|
|
32
32
|
## Getting Started
|
33
33
|
|
@@ -120,10 +120,8 @@ The following assertions are added for use in any integration test:
|
|
120
120
|
- `assert_email(action)` asserts an email with the given action name was sent. Also supports `assert_email(to: email)` type syntax with to, from, subject, body.
|
121
121
|
- `assert_flash`, optionally with the desired `:success`, `:error` key and/or message, makes sure the flash is set.
|
122
122
|
- `assert_jquery_ujs_disable_with` makes sure all `input[type=submit]` elements on the page have the `data-disable-with` property set.
|
123
|
-
- `assert_no_exceptions` checks for any exceptions in the last page request and gives a stacktrace if there was.
|
124
123
|
- `assert_no_html_form_validation_errors` checks for frontend html5 errors.
|
125
|
-
- `assert_no_js_errors`
|
126
|
-
- `assert_no_unpermitted_params` makes sure the last submitted form did not include any unpermitted params and prints out any unpermitted params that do exist.
|
124
|
+
- `assert_no_js_errors` checks for any javascript errors on the page.
|
127
125
|
- `assert_page_content(content)` checks that the given content is present without waiting the capybara default wait time.
|
128
126
|
- `assert_no_page_content(content)` checks that the given content is blank without waiting the capybara default wait time.
|
129
127
|
- `assert_page_status` checks for a given http status, default 200.
|
@@ -135,7 +133,7 @@ The following assertions are added for use in any integration test:
|
|
135
133
|
|
136
134
|
As well,
|
137
135
|
|
138
|
-
- `assert_page_normal` checks for general errors on the current page.
|
136
|
+
- `assert_page_normal` checks for general errors on the current page. Checks include `assert_page_status`, `assert_no_js_errors`, and `assert_page_title`.
|
139
137
|
|
140
138
|
## Capybara Extras
|
141
139
|
|
@@ -156,10 +154,13 @@ It clicks through bootstrap tabs and fill them nicely left-to-right, one tab at
|
|
156
154
|
You can pass a Hash of 'fills' to specify specific input values:
|
157
155
|
|
158
156
|
```ruby
|
159
|
-
|
157
|
+
# app/test/system/posts_test.rb
|
158
|
+
require 'application_system_test_case'
|
159
|
+
|
160
|
+
class PostTest < ApplicationSystemTestCase
|
160
161
|
test 'creating a new post' do
|
161
162
|
visit new_post_path
|
162
|
-
fill_form(:
|
163
|
+
fill_form(title: 'A Cool Post', 'author.last_name': 'Smith')
|
163
164
|
submit_form
|
164
165
|
end
|
165
166
|
end
|
@@ -168,10 +169,10 @@ end
|
|
168
169
|
And you can disable specific fields from being filled, by modifying the input html in your normal view:
|
169
170
|
|
170
171
|
```ruby
|
171
|
-
= f.input :too_complicated, 'data-test-bot-skip'
|
172
|
+
= f.input :too_complicated, 'data-test-bot-skip': true
|
172
173
|
```
|
173
174
|
|
174
|
-
Sometimes you have the requirement that inputs add upto a certain number.
|
175
|
+
Sometimes you have the requirement that inputs add upto a certain number. For example, having to provide percentages in 3-4 input fields that always add upto 100%.
|
175
176
|
|
176
177
|
You can use the html `min` and `max` properties to indicate this requirement.
|
177
178
|
|
@@ -188,7 +189,9 @@ Clicks the first `input[type='submit']` field (or first submit field with the gi
|
|
188
189
|
Automatically checks for `assert_no_html5_form_validation_errors`, `assert_jquery_ujs_disable_with` and `assert_no_unpermitted_params`
|
189
190
|
|
190
191
|
```ruby
|
191
|
-
|
192
|
+
require 'application_system_test_case'
|
193
|
+
|
194
|
+
class PostTest < ApplicationSystemTestCase
|
192
195
|
test 'creating a new post' do
|
193
196
|
visit(new_post_path) and fill_form
|
194
197
|
submit_form # or submit_form('Save and Continue')
|
@@ -207,22 +210,20 @@ end
|
|
207
210
|
- `sign_up` visits the devise `new_user_registration_path` and signs up as a new user.
|
208
211
|
- `synchronize!` should fix any timing issues waiting for page elements.
|
209
212
|
- `was_redirect?` returns true/false if the last time we changed pages was a 304 redirect.
|
210
|
-
- `was_download?` if clicking a link returned a file of any type rather than a page change.
|
211
213
|
- `within_if(selector, boolean) do .. end` runs the block inside capybara's `within do .. end` if boolean is true, otherwise runs the same block skipping the `within`.
|
212
214
|
|
213
215
|
## Capybara Super Extras
|
214
216
|
|
215
|
-
Running
|
217
|
+
Running system tests is supposed to be a black-box integration testing experience. This provides a lot of benefits, but also some severe limitations.
|
216
218
|
|
217
|
-
The test web server runs in a totally separate process.
|
219
|
+
The test web server runs in a totally separate process. It knows nothing about your application and it does not have access to any of the rails internal state. It only sees html, javascript, css and urls.
|
218
220
|
|
219
|
-
effective_test_bot fills in this knowledge gap by serializing any interesting values
|
221
|
+
effective_test_bot fills in this knowledge gap by serializing any interesting values with a javascript payload. This gives our tests a way to peek inside the black box.
|
220
222
|
|
221
223
|
The following representations of the rails internal state are made available:
|
222
224
|
|
223
|
-
- `assigns` a Hash representation of the current page's rails `view_assigns`. Serializes any `ActiveRecord` objects, as well as any `TrueClass`, `FalseClass`, `NilClass`, `String`, `Symbol`, and `Numeric` objects.
|
225
|
+
- `assigns` a Hash representation of the current page's rails `view_assigns`. Serializes any `ActiveRecord` objects, as well as any `TrueClass`, `FalseClass`, `NilClass`, `String`, `Symbol`, and `Numeric` objects. Does not serialize anything else, but sets a symbol `assigns[key] == :present_but_not_serialized`.
|
224
226
|
- `flash` a Hash representation of the current page's flash.
|
225
|
-
- `unpermitted_params` an Array of any unpermitted parameters that were encountered by the last request.
|
226
227
|
|
227
228
|
## Effective Test Suites
|
228
229
|
|
@@ -248,19 +249,20 @@ The following instance level `crud_action_test` methods are available:
|
|
248
249
|
- `crud_action_test(:edit)` signs in as the given user, finds or creates a resource, visits `edit_resource_path` and checks that an appropriate form exists for this resource.
|
249
250
|
- `crud_action_test(:update_invalid)` signs in as the given user, finds or creates a resource, visits `edit_resource_path` and submits an empty form. Checks that the existing resource wasn't updated and that all errors are properly assigned and displayed.
|
250
251
|
- `crud_action_test(:update_valid)` signs in as the given user, finds or creates a resource, visits `edit_resource_path` and submits a valid form. Checks for any errors and makes sure the existing resource was updated.
|
251
|
-
- `crud_action_test(:destroy)` signs in as the given user, finds or creates a resource, visits `resources_path`. It then finds or creates a link to destroy the resource and clicks the link.
|
252
|
+
- `crud_action_test(:destroy)` signs in as the given user, finds or creates a resource, visits `resources_path`. It then finds or creates a link to destroy the resource and clicks the link. Checks for any errors and makes sure the resource was deleted. If the resource `respond_to?(:archived)` it will check for archive behavior instead of delete.
|
252
253
|
|
253
254
|
Also,
|
254
255
|
|
255
|
-
- `crud_action_test(:tour)` signs in as a given user and calls all the above `crud_action_test` methods from inside one test.
|
256
|
+
- `crud_action_test(:tour)` signs in as a given user and calls all the above `crud_action_test` methods from inside one test. The animated .gif produced from this test suite records the entire process of creating, showing, editing and deleting a resource from start to finish. It makes all the same assertions as running the test suites individually.
|
256
257
|
|
257
|
-
|
258
|
-
A quick note on speed: You can speed up these test suites by fixturing, seeding or first creating an instance of the resource being tested. Any tests that need to `find_or_create_resource` check for an existing resource first, otherwise visit `new_resource_path` and submit a form to create the resource. Having a resource already created will speed things up.
|
258
|
+
A quick note on speed: You can speed up these test suites by fixturing, seeding or first creating an instance of the resource being tested. Any tests that need to `find_or_create_resource` check for an existing resource first, otherwise visit `new_resource_path` and submit a form to create the resource. Having a resource already created will speed things up.
|
259
259
|
|
260
260
|
There are a few variations on the one-liner method:
|
261
261
|
|
262
262
|
```ruby
|
263
|
-
|
263
|
+
require 'application_system_test_case'
|
264
|
+
|
265
|
+
class PostTest < ApplicationSystemTestCase
|
264
266
|
# Runs all 9 crud_action tests against /posts
|
265
267
|
crud_test(resource: Post)
|
266
268
|
|
@@ -284,7 +286,9 @@ end
|
|
284
286
|
The individual test suites may also be used as part of a larger test:
|
285
287
|
|
286
288
|
```ruby
|
287
|
-
|
289
|
+
require 'application_system_test_case'
|
290
|
+
|
291
|
+
class PostTest < ApplicationSystemTestCase
|
288
292
|
test 'user may only update a post once' do
|
289
293
|
crud_action_test(test: :create_valid, resource: Post, user: User.first)
|
290
294
|
assert_text 'successfully created post. You may only update it once.'
|
@@ -312,7 +316,7 @@ This test runs through the the [devise](https://github.com/plataformatec/devise)
|
|
312
316
|
Use as a one-liner:
|
313
317
|
|
314
318
|
```ruby
|
315
|
-
class MyApplicationTest <
|
319
|
+
class MyApplicationTest < ApplicationSystemTestCase
|
316
320
|
devise_test # Runs all tests (sign_up, sign_in_valid, and sign_in_invalid)
|
317
321
|
end
|
318
322
|
```
|
@@ -320,7 +324,7 @@ end
|
|
320
324
|
Or each individually in part of a regular test:
|
321
325
|
|
322
326
|
```ruby
|
323
|
-
class MyApplicationTest <
|
327
|
+
class MyApplicationTest < ApplicationSystemTestCase
|
324
328
|
test 'user receives 10 tokens after signing up' do
|
325
329
|
devise_action_test(test: :sign_up)
|
326
330
|
assert_text 'Tokens: 10'
|
@@ -345,7 +349,7 @@ This test signs in as the given user, visits the given controller/action/page an
|
|
345
349
|
Use it as a one-liner:
|
346
350
|
|
347
351
|
```ruby
|
348
|
-
class PostsTest <
|
352
|
+
class PostsTest < ApplicationSystemTestCase
|
349
353
|
# Uses find_or_create_resource! to load a seeded resource or create a new one
|
350
354
|
member_test(controller: 'posts', action: 'unarchive', user: User.first)
|
351
355
|
|
@@ -357,7 +361,7 @@ end
|
|
357
361
|
Or as part of a regular test:
|
358
362
|
|
359
363
|
```ruby
|
360
|
-
class PostsTest <
|
364
|
+
class PostsTest < ApplicationSystemTestCase
|
361
365
|
test 'posts can be unarchived' do
|
362
366
|
post = Post.create(title: 'first post', archived: true)
|
363
367
|
|
@@ -375,7 +379,7 @@ This test signs in as the given user, visits the given page and simply checks `a
|
|
375
379
|
Use it as a one-liner:
|
376
380
|
|
377
381
|
```ruby
|
378
|
-
class PostsTest <
|
382
|
+
class PostsTest < ApplicationSystemTestCase
|
379
383
|
page_test(path: :posts_path, user: User.first) # Runs the page_test test suite against posts_path as User.first
|
380
384
|
end
|
381
385
|
```
|
@@ -383,7 +387,7 @@ end
|
|
383
387
|
Or as part of a regular test:
|
384
388
|
|
385
389
|
```ruby
|
386
|
-
class PostsTest <
|
390
|
+
class PostsTest < ApplicationSystemTestCase
|
387
391
|
test 'posts are displayed on the index page' do
|
388
392
|
Post.create(title: 'first post')
|
389
393
|
|
@@ -402,7 +406,7 @@ This test signs in as the given user, visits the given page then checks `assert_
|
|
402
406
|
Use it as a one-liner:
|
403
407
|
|
404
408
|
```ruby
|
405
|
-
class PostsTest <
|
409
|
+
class PostsTest < ApplicationSystemTestCase
|
406
410
|
# Visits /blog and tests that it redirects to a working /posts page
|
407
411
|
redirect_test(from: '/blog', to: '/posts', user: User.first)
|
408
412
|
end
|
@@ -411,7 +415,7 @@ end
|
|
411
415
|
Or as part of a regular test:
|
412
416
|
|
413
417
|
```ruby
|
414
|
-
class PostsTest <
|
418
|
+
class PostsTest < ApplicationSystemTestCase
|
415
419
|
test 'visiting blog redirects to posts' do
|
416
420
|
Post.create(title: 'first post')
|
417
421
|
redirect_action_test(from: '/blog', to: '/posts', user: User.first)
|
@@ -431,7 +435,7 @@ As well, in the `wizard_action_test`, each page is yielded to the calling method
|
|
431
435
|
Use it as a one-liner:
|
432
436
|
|
433
437
|
```ruby
|
434
|
-
class PostsTest <
|
438
|
+
class PostsTest < ApplicationSystemTestCase
|
435
439
|
wizard_test(from: '/build_post/step1', to: '/build_post/step5', user: User.first)
|
436
440
|
end
|
437
441
|
```
|
@@ -439,7 +443,7 @@ end
|
|
439
443
|
Or as part of a regular test:
|
440
444
|
|
441
445
|
```ruby
|
442
|
-
class PostsTest <
|
446
|
+
class PostsTest < ApplicationSystemTestCase
|
443
447
|
test 'building a post in 5 steps' do
|
444
448
|
wizard_action_test(from: '/build_post/step1', to: '/build_post/step5', user: User.first) do
|
445
449
|
if page.current_path.end_with?('step4')
|
@@ -491,9 +495,9 @@ Please see the installed `effective_test_bot.rb` initializer file for a full des
|
|
491
495
|
|
492
496
|
Unfortunately, with the current day ruby on rails ecosystem, simply getting a testing environment setup correctly is a non-trivial endeavor filled with gotchas and many things that can go wrong.
|
493
497
|
|
494
|
-
User sessions need to properly reset and database transactions must be correctly rolled back between tests.
|
498
|
+
User sessions need to properly reset and database transactions must be correctly rolled back between tests. Seeds and fixtures that were once valid may become invalid as the application changes. Database migrations must stay up to date. Capybara needs to query your app with a single shared connection or weird things start happening.
|
495
499
|
|
496
|
-
Included with this gem is the `rails generate effective_test_bot:install` that does its best to provide a known-good set of configuration files that initialize all required testing gems.
|
500
|
+
Included with this gem is the `rails generate effective_test_bot:install` that does its best to provide a known-good set of configuration files that initialize all required testing gems. However, every developer's machine is different, and there are just too many points of failure. Everyone's `test/test_helper.rb` will be slightly different.
|
497
501
|
|
498
502
|
Run `rails test:bot:environment` to check that capybara is doing the right thing, everything is reset properly between test runs, an initial user record exists, all seeded and fixtured data is valid, devise works and rails' jquery-ujs is present.
|
499
503
|
|
@@ -501,7 +505,7 @@ If all environment tests pass, you will have a great experience with automated t
|
|
501
505
|
|
502
506
|
## Automated full stack testing
|
503
507
|
|
504
|
-
One of the main goals of `effective_test_bot` is to increase the speed at which tests can be written in any ruby on rails application.
|
508
|
+
One of the main goals of `effective_test_bot` is to increase the speed at which tests can be written in any ruby on rails application. Well, there's no faster way of writing tests than by not writing them at all.
|
505
509
|
|
506
510
|
Run `rails test:bot` to scan every route defined in `routes.rb` and run an appropriate test suite.
|
507
511
|
|
@@ -522,17 +526,12 @@ rails test:bot TEST=posts#index
|
|
522
526
|
|
523
527
|
## Animated gifs and screenshots
|
524
528
|
|
525
|
-
Call `save_test_bot_screenshot` from within any test to take a screenshot of the current page.
|
529
|
+
Call `save_test_bot_screenshot` from within any test to take a screenshot of the current page. If an animated .gif is produced at the end of the test -- either from autosave_animated_gif_on_failure or tour mode -- this screenshot will be used as one of the frames in the animation.
|
526
530
|
|
527
531
|
This method is already called by `fill_form` and `submit_form`.
|
528
532
|
|
529
533
|
To disable taking screenshots entirely set `config.screenshots = false` in the `config/initializers/effective_test_bot.rb` initializer file.
|
530
534
|
|
531
|
-
### Autosave on failure
|
532
|
-
|
533
|
-
The `test/test_helper.rb` file that is installed by `effective_test_bot` enables [capybara-screenshot](https://github.com/mattheworiordan/capybara-screenshot)'s `autosave_on_failure` functionality. So whenever a test fails, the current html will be written and a .png screenshot will be saved. This is invaluable for troubleshooting why a test has failed.
|
534
|
-
|
535
|
-
Building on this type of feature, `effective_test_bot` will also autosave an animated gif on failure. This does slow down failing tests and can be disabled.
|
536
535
|
|
537
536
|
### Tour mode
|
538
537
|
|
@@ -1,44 +1,36 @@
|
|
1
1
|
module EffectiveTestBotControllerHelper
|
2
|
-
|
3
|
-
def assign_test_bot_http_headers
|
4
|
-
response.headers['Test-Bot-Flash'] = Base64.encode64(flash.to_hash.to_json)
|
2
|
+
BODY_TAG = '</body>'
|
5
3
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
4
|
+
# This is included as an after_action in the controller
|
5
|
+
def assign_test_bot_payload(payload = {})
|
6
|
+
return unless response.content_type == 'text/html'.freeze
|
7
|
+
return unless !!(response.body[BODY_TAG])
|
10
8
|
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
test_bot_assigns[key] = object
|
21
|
-
else
|
22
|
-
# We don't want to serialize them, but they should be present
|
23
|
-
test_bot_assigns[key] = :present_but_not_serialized
|
24
|
-
end
|
9
|
+
payload.merge!({ response_code: response.code, assigns: test_bot_view_assigns, flash: flash.to_hash })
|
10
|
+
|
11
|
+
payload = view_context.content_tag(:script, id: 'test_bot_payload') do
|
12
|
+
[
|
13
|
+
'',
|
14
|
+
'window.effective_test_bot = {};',
|
15
|
+
payload.map { |k, v| "window.effective_test_bot.#{k} = #{v.respond_to?(:to_json) ? v.to_json : ("'" + v + "'")};" },
|
16
|
+
'',
|
17
|
+
].join("\n").html_safe
|
25
18
|
end
|
26
19
|
|
27
|
-
|
20
|
+
split = response.body.split(BODY_TAG)
|
21
|
+
response.body = "#{split.first}#{payload}#{BODY_TAG}#{split.last if split.size > 1}"
|
28
22
|
end
|
29
23
|
|
30
|
-
#
|
31
|
-
def
|
32
|
-
|
33
|
-
response.headers['Test-Bot-Unpermitted-Params'] = Base64.encode64(exception.params.to_json)
|
34
|
-
end
|
24
|
+
# This is called in an ActionController rescue_from.
|
25
|
+
def assign_test_bot_access_denied_exception(exception)
|
26
|
+
assign_test_bot_payload(test_bot_access_denied(exception))
|
35
27
|
end
|
36
28
|
|
37
|
-
|
38
|
-
return unless Rails.env.test?
|
29
|
+
private
|
39
30
|
|
40
|
-
|
41
|
-
|
31
|
+
def test_bot_access_denied(exception)
|
32
|
+
{
|
33
|
+
access_denied: exception,
|
42
34
|
action: exception.action,
|
43
35
|
subject: (
|
44
36
|
if exception.subject.kind_of?(Symbol)
|
@@ -49,7 +41,29 @@ module EffectiveTestBotControllerHelper
|
|
49
41
|
exception.subject.class.name
|
50
42
|
end
|
51
43
|
)
|
52
|
-
}
|
44
|
+
}
|
45
|
+
end
|
46
|
+
|
47
|
+
def test_bot_view_assigns
|
48
|
+
assigns = {}
|
49
|
+
|
50
|
+
view_assigns.each do |key, object|
|
51
|
+
case object
|
52
|
+
when ActiveRecord::Base
|
53
|
+
assigns[key] = object.attributes
|
54
|
+
assigns[key][:errors] = object.errors.messages.delete_if { |_, v| v.blank? } if object.errors.present?
|
55
|
+
when (ActiveModel::Model rescue nil)
|
56
|
+
assigns[key] = object.respond_to?(:attributes) ? object.attributes : { present_but_not_serialized: true }
|
57
|
+
assigns[key][:errors] = object.errors.messages.delete_if { |_, v| v.blank? } if object.errors.present?
|
58
|
+
when TrueClass, FalseClass, NilClass, String, Symbol, Numeric
|
59
|
+
assigns[key] = object
|
60
|
+
else
|
61
|
+
# We don't want to serialize them, but they should be present
|
62
|
+
assigns[key] = :present_but_not_serialized
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
assigns
|
53
67
|
end
|
54
68
|
|
55
69
|
end
|
data/config/test_helper.rb
CHANGED
@@ -1,59 +1,26 @@
|
|
1
|
-
ENV['RAILS_ENV']
|
2
|
-
|
1
|
+
ENV['RAILS_ENV'] ||= 'test'
|
2
|
+
require_relative '../config/environment'
|
3
|
+
|
3
4
|
require 'rake'
|
4
5
|
require 'rails/test_help'
|
5
|
-
require 'minitest/rails'
|
6
|
-
require 'minitest/rails/capybara'
|
7
|
-
require 'minitest/pride'
|
8
|
-
require 'minitest/reporters'
|
9
6
|
|
10
|
-
require '
|
11
|
-
require '
|
12
|
-
require '
|
13
|
-
|
14
|
-
# require 'database_cleaner'
|
7
|
+
require 'minitest/spec'
|
8
|
+
require 'minitest/reporters'
|
9
|
+
require 'minitest/fail_fast' if EffectiveTestBot.fail_fast?
|
15
10
|
|
16
11
|
class ActiveSupport::TestCase
|
17
12
|
# Setup all fixtures in test/fixtures/*.yml for all tests in alphabetical order.
|
18
13
|
fixtures :all
|
19
|
-
use_transactional_fixtures = true
|
20
|
-
end
|
21
|
-
|
22
|
-
class Capybara::Rails::TestCase
|
23
|
-
# Make the Capybara DSL available in all integration tests
|
24
|
-
include Capybara::DSL
|
25
|
-
include Capybara::Assertions
|
26
|
-
include Capybara::Screenshot::MiniTestPlugin
|
27
|
-
include Warden::Test::Helpers if defined?(Devise)
|
28
|
-
|
29
|
-
include EffectiveTestBot::DSL
|
30
|
-
|
31
|
-
# Needed for Rails < 5.1
|
32
|
-
# def after_setup
|
33
|
-
# super()
|
34
|
-
# DatabaseCleaner.start
|
35
|
-
# end
|
36
14
|
|
37
|
-
#
|
38
|
-
|
39
|
-
# DatabaseCleaner.clean
|
40
|
-
# Capybara.reset_sessions! # Some apps seem to need this to correctly reset the test_06:_capybara_can_sign_in
|
41
|
-
# end
|
15
|
+
# For the let syntax
|
16
|
+
extend Minitest::Spec::DSL
|
42
17
|
end
|
43
18
|
|
44
|
-
Capybara.default_driver = :webkit
|
45
|
-
Capybara.javascript_driver = :webkit
|
46
|
-
Capybara::Screenshot.autosave_on_failure = true
|
47
|
-
Capybara::Screenshot.prune_strategy = :keep_last_run
|
48
|
-
Capybara::Screenshot.webkit_options = { width: 1024, height: 768 }
|
49
|
-
Capybara::Webkit.configure { |config| config.allow_unknown_urls }
|
50
|
-
|
51
19
|
Minitest::Reporters.use! Minitest::Reporters::SpecReporter.new
|
52
20
|
|
53
|
-
# These three lines are needed as of minitest-reporters 1.1.2
|
54
21
|
Rails.backtrace_cleaner.remove_silencers!
|
55
22
|
Rails.backtrace_cleaner.add_silencer { |line| line =~ /minitest/ }
|
56
|
-
Rails.backtrace_cleaner.add_silencer { |line| line =~ /effective_test_bot/ }
|
23
|
+
#Rails.backtrace_cleaner.add_silencer { |line| line =~ /effective_test_bot/ }
|
57
24
|
|
58
25
|
###############################################
|
59
26
|
### Effective Test Bot specific stuff below ###
|
@@ -63,7 +30,7 @@ Rails.application.load_tasks
|
|
63
30
|
|
64
31
|
# So the very first thing we do is consistently reset the database.
|
65
32
|
# This can be done with Snippet 1 or Snippet 2.
|
66
|
-
# Snippet 1 is faster, and will usually work.
|
33
|
+
# Snippet 1 is faster, and will usually work. Snippet 2 should always work.
|
67
34
|
|
68
35
|
# Snippet 1:
|
69
36
|
Rake::Task['db:schema:load'].invoke
|
@@ -76,31 +43,6 @@ ActiveRecord::Migration.maintain_test_schema!
|
|
76
43
|
# Rake::Task['db:migrate'].invoke
|
77
44
|
|
78
45
|
# Now we populate our test data:
|
79
|
-
Rake::Task['db:fixtures:load'].invoke
|
46
|
+
Rake::Task['db:fixtures:load'].invoke
|
80
47
|
Rake::Task['db:seed'].invoke
|
81
|
-
Rake::Task['test:load_fixture_seeds'].invoke #
|
82
|
-
|
83
|
-
if EffectiveTestBot.fail_fast?
|
84
|
-
require 'minitest/fail_fast'
|
85
|
-
end
|
86
|
-
|
87
|
-
# "Connection not rolling back" snippets
|
88
|
-
# These are some snippets that the internet has collected to fix test threading issues.
|
89
|
-
# They are unneeded with effective_test_bot. On my machine. But I leave them here as a reference.
|
90
|
-
# Try one or both if you are having issues passing rake test:bot:environment
|
91
|
-
|
92
|
-
# class ActiveRecord::Base
|
93
|
-
# mattr_accessor :shared_connection
|
94
|
-
# @@shared_connection = nil
|
95
|
-
|
96
|
-
# def self.connection
|
97
|
-
# @@shared_connection || retrieve_connection
|
98
|
-
# end
|
99
|
-
# end
|
100
|
-
# ActiveRecord::Base.shared_connection = ActiveRecord::Base.connection
|
101
|
-
|
102
|
-
# ActiveRecord::ConnectionAdapters::ConnectionPool.class_eval do
|
103
|
-
# def current_connection_id
|
104
|
-
# Thread.main.object_id
|
105
|
-
# end
|
106
|
-
# end
|
48
|
+
Rake::Task['test:load_fixture_seeds'].invoke # from effective_test_bot. Loads test/fixtures/seeds.rb
|
data/lib/effective_test_bot.rb
CHANGED
@@ -7,27 +7,16 @@ module EffectiveTestBot
|
|
7
7
|
config.autoload_paths += Dir["#{config.root}/test/support/**/"]
|
8
8
|
|
9
9
|
# Set up our default configuration options.
|
10
|
-
initializer
|
10
|
+
initializer 'effective_test_bot.defaults', before: :load_config_initializers do |app|
|
11
11
|
# Set up our defaults, as per our initializer template
|
12
12
|
eval File.read("#{config.root}/config/effective_test_bot.rb")
|
13
13
|
end
|
14
14
|
|
15
|
-
initializer 'effective_test_bot.middleware' do |app|
|
16
|
-
if Rails.env.test?
|
17
|
-
Rails.application.config.middleware.use EffectiveTestBot::Middleware
|
18
|
-
end
|
19
|
-
end
|
20
|
-
|
21
15
|
initializer 'effective_test_bot.email_logger' do |app|
|
22
16
|
if Rails.env.test?
|
23
17
|
ActiveSupport.on_load :action_mailer do
|
24
18
|
ActionMailer::Base.send :include, ::EffectiveTestBotMailerHelper
|
25
|
-
|
26
|
-
if ActionMailer::Base.respond_to?(:after_action)
|
27
|
-
ActionMailer::Base.send :after_action, :assign_test_bot_mailer_info
|
28
|
-
else
|
29
|
-
ActionMailer::Base.send :after_filter, :assign_test_bot_mailer_info
|
30
|
-
end
|
19
|
+
ActionMailer::Base.send :after_action, :assign_test_bot_mailer_info
|
31
20
|
end
|
32
21
|
end
|
33
22
|
end
|
@@ -37,19 +26,8 @@ module EffectiveTestBot
|
|
37
26
|
ActiveSupport.on_load :action_controller do
|
38
27
|
ActionController::Base.send :include, ::EffectiveTestBotControllerHelper
|
39
28
|
|
40
|
-
|
41
|
-
|
42
|
-
ActionController::Base.send :after_action, :assign_test_bot_http_headers
|
43
|
-
else
|
44
|
-
ActionController::Base.send :before_filter, :expires_now # Prevent 304 Not Modified caching
|
45
|
-
ActionController::Base.send :after_filter, :assign_test_bot_http_headers
|
46
|
-
end
|
47
|
-
|
48
|
-
ApplicationController.instance_exec do
|
49
|
-
rescue_from ActionController::UnpermittedParameters do |exception|
|
50
|
-
assign_test_bot_unpermitted_params_header(exception)
|
51
|
-
end
|
52
|
-
end
|
29
|
+
ActionController::Base.send :before_action, :expires_now # Prevent 304 Not Modified caching
|
30
|
+
ActionController::Base.send :after_action, :assign_test_bot_payload
|
53
31
|
end
|
54
32
|
end
|
55
33
|
end
|
@@ -3,22 +3,17 @@ module EffectiveTestBot
|
|
3
3
|
class InstallGenerator < Rails::Generators::Base
|
4
4
|
include Rails::Generators::Migration
|
5
5
|
|
6
|
-
desc
|
6
|
+
desc 'Creates an EffectiveTestBot initializer in your application.'
|
7
7
|
|
8
8
|
source_root File.expand_path('../../templates', __FILE__)
|
9
9
|
|
10
|
-
def install_minitest
|
11
|
-
return if File.exist?('test/test_helper.rb')
|
12
|
-
puts '[effective_test_bot] installing minitest'
|
13
|
-
run 'bundle exec rails generate minitest:install'
|
14
|
-
end
|
15
|
-
|
16
10
|
def copy_initializer
|
17
11
|
template ('../' * 3) + 'config/effective_test_bot.rb', 'config/initializers/effective_test_bot.rb'
|
18
12
|
end
|
19
13
|
|
20
|
-
def
|
14
|
+
def copy_test_helper
|
21
15
|
template ('../' * 3) + 'config/test_helper.rb', 'test/test_helper.rb'
|
16
|
+
template ('../' * 3) + 'config/application_system_test_case.rb', 'test/application_system_test_case.rb'
|
22
17
|
end
|
23
18
|
|
24
19
|
def thank_you
|
@@ -1,5 +1,3 @@
|
|
1
|
-
require 'rake/testtask'
|
2
|
-
|
3
1
|
# rake test:bot
|
4
2
|
# rake test:bot TEST=documents#new
|
5
3
|
# rake test:bot TEST=documents#new,documents#show
|
@@ -27,11 +25,7 @@ namespace :test do
|
|
27
25
|
ENV['TEST'] = nil
|
28
26
|
end
|
29
27
|
|
30
|
-
|
31
|
-
Rake::Task['test:effective_test_bot'].invoke
|
32
|
-
else
|
33
|
-
system("rails test #{File.dirname(__FILE__)}/../../test/test_bot/integration/application_test.rb")
|
34
|
-
end
|
28
|
+
system("rails test #{File.dirname(__FILE__)}/../../test/test_bot/system/application_test.rb")
|
35
29
|
end
|
36
30
|
|
37
31
|
desc "Runs 'rake test' with effective_test_bot tour mode enabled"
|
@@ -49,11 +43,7 @@ namespace :test do
|
|
49
43
|
namespace :bot do
|
50
44
|
desc 'Runs effective_test_bot environment test'
|
51
45
|
task :environment do
|
52
|
-
|
53
|
-
Rake::Task['test:effective_test_bot_environment'].invoke
|
54
|
-
else
|
55
|
-
system("rails test #{File.dirname(__FILE__)}/../../test/test_bot/integration/environment_test.rb")
|
56
|
-
end
|
46
|
+
system("rails test #{File.dirname(__FILE__)}/../../test/test_bot/system/environment_test.rb")
|
57
47
|
end
|
58
48
|
|
59
49
|
desc 'Deletes all effective_test_bot temporary, failure and tour screenshots'
|
@@ -114,26 +104,10 @@ namespace :test do
|
|
114
104
|
end # /namespace bot
|
115
105
|
|
116
106
|
desc 'loads test/fixtures/seeds.rb'
|
117
|
-
task :
|
107
|
+
task load_fixture_seeds: :environment do
|
118
108
|
puts 'loading fixture seed'
|
119
109
|
seeds = "#{Rails.root}/test/fixtures/seeds.rb"
|
120
110
|
load(seeds) if File.exist?(seeds)
|
121
111
|
end
|
122
112
|
|
123
|
-
# This ensures rake test:prepare is run before rake test:bot or rake test:bot:environment run
|
124
|
-
# Test files stuff is minitest hackery to just load the 1 test file
|
125
|
-
if Gem::Version.new(Rails.version) < Gem::Version.new('5.0')
|
126
|
-
Rake::TestTask.new('effective_test_bot' => 'test:prepare') do |t|
|
127
|
-
t.libs << 'test'
|
128
|
-
t.test_files = FileList["#{File.dirname(__FILE__)}/../../test/test_bot/integration/application_test.rb"]
|
129
|
-
t.warning = false
|
130
|
-
end
|
131
|
-
|
132
|
-
Rake::TestTask.new('effective_test_bot_environment' => 'test:prepare') do |t|
|
133
|
-
t.libs << 'test'
|
134
|
-
t.test_files = FileList["#{File.dirname(__FILE__)}/../../test/test_bot/integration/environment_test.rb"]
|
135
|
-
t.warning = false
|
136
|
-
end
|
137
|
-
end
|
138
|
-
|
139
113
|
end
|
@@ -17,16 +17,16 @@ module EffectiveTestBotAssertions
|
|
17
17
|
assert assigns['current_user'].blank?, message || 'Expected @current_user to be blank when signed out'
|
18
18
|
end
|
19
19
|
|
20
|
-
def
|
20
|
+
def assert_can_execute_javascript(message = "Expected page.evaluate_script() to be successful")
|
21
21
|
error = nil; result = nil;
|
22
22
|
|
23
23
|
begin
|
24
|
-
result = page.evaluate_script(
|
24
|
+
result = page.evaluate_script('1+1').to_s
|
25
25
|
rescue => e
|
26
26
|
error = e.message
|
27
27
|
end
|
28
28
|
|
29
|
-
assert (result == '
|
29
|
+
assert (result == '2'), "#{message}. Error was: #{error}"
|
30
30
|
end
|
31
31
|
|
32
32
|
def assert_jquery_present(message = "Expected jquery ($.fn.jquery) to be present")
|
@@ -55,14 +55,14 @@ module EffectiveTestBotAssertions
|
|
55
55
|
end
|
56
56
|
|
57
57
|
def assert_authorization(message = '(authorization) Expected authorized access')
|
58
|
-
if
|
58
|
+
if response_code == 403
|
59
59
|
exception = access_denied_exception
|
60
60
|
|
61
61
|
info = [
|
62
62
|
"Encountered a 403 Access Denied",
|
63
63
|
("(cannot :#{exception['action']}, #{exception['subject']})" if exception.present?),
|
64
64
|
"on #{page.current_path} as user #{user || 'no user'}.",
|
65
|
-
("\nAdd assign_test_bot_access_denied_exception(exception) if defined?(EffectiveTestBot) to your ApplicationController's rescue_from block to gather more information." unless exception.present?),
|
65
|
+
("\nAdd assign_test_bot_access_denied_exception(exception) if defined?(EffectiveTestBot) to the very bottom of your ApplicationController's rescue_from block to gather more information." unless exception.present?),
|
66
66
|
].compact.join(' ')
|
67
67
|
|
68
68
|
assert false, "#{message}.\n#{info}"
|
@@ -70,7 +70,7 @@ module EffectiveTestBotAssertions
|
|
70
70
|
end
|
71
71
|
|
72
72
|
def assert_page_status(status = 200, message = '(page_status) Expected :status: HTTP status code')
|
73
|
-
assert_equal status,
|
73
|
+
assert_equal status, response_code, message.sub(':status:', status.to_s)
|
74
74
|
end
|
75
75
|
|
76
76
|
def assert_current_path(path, message = '(current_path) Expected current_path to be :path:')
|
@@ -104,29 +104,16 @@ module EffectiveTestBotAssertions
|
|
104
104
|
end
|
105
105
|
|
106
106
|
def assert_no_js_errors(message = nil)
|
107
|
-
|
108
|
-
|
109
|
-
end
|
107
|
+
error = page.driver.browser.manage.logs.get(:browser).first # headless_chrome
|
108
|
+
error = error.message.gsub(/^http.+js \d+:\d+ /, '') if error.present?
|
110
109
|
|
111
|
-
|
112
|
-
assert unpermitted_params.blank?, message.sub(':unpermitted_params:', unpermitted_params.to_s)
|
110
|
+
assert error.blank?, message || "(no_js_errors) Unexpected javascript error:\n#{error}"
|
113
111
|
end
|
114
112
|
|
115
113
|
def assert_no_flash_errors(message = "(no_flash_errors) Unexpected flash error:\n:flash_errors:")
|
116
114
|
assert (!flash.key?('error') && !flash.key?('danger')), message.sub(':flash_errors:', flash.to_s)
|
117
115
|
end
|
118
116
|
|
119
|
-
def assert_no_exceptions(message = "(no_exceptions) Unexpected rails server exception:\n:exception:")
|
120
|
-
# this file is created by EffectiveTestBot::Middleware when an exception is encountered in the rails app
|
121
|
-
file = File.join(Dir.pwd, 'tmp', 'test_bot', 'exception.txt')
|
122
|
-
return unless File.exist?(file)
|
123
|
-
|
124
|
-
exception = File.read(file)
|
125
|
-
File.delete(file)
|
126
|
-
|
127
|
-
assert false, message.sub(':exception:', exception)
|
128
|
-
end
|
129
|
-
|
130
117
|
# This must be run after submit_form()
|
131
118
|
# It ensures there are no HTML5 validation errors that would prevent the form from being submit
|
132
119
|
# Browsers seem to only consider visible fields, so we will to
|
@@ -27,9 +27,7 @@ module EffectiveTestBotFormHelper
|
|
27
27
|
with_raised_unpermitted_params_exceptions { click_submit(label, last: last, debug: debug) }
|
28
28
|
end
|
29
29
|
|
30
|
-
assert_no_unpermitted_params unless test_bot_skip?(:no_unpermitted_params)
|
31
30
|
assert_no_assigns_errors unless test_bot_skip?(:no_assigns_errors)
|
32
|
-
assert_no_exceptions unless test_bot_skip?(:exceptions)
|
33
31
|
assert_authorization unless test_bot_skip?(:authorization)
|
34
32
|
assert_page_status unless test_bot_skip?(:page_status)
|
35
33
|
|
@@ -87,7 +87,7 @@ module EffectiveTestBotScreenshotsHelper
|
|
87
87
|
# current_test_failure_path: destination for .gifs of failing tests
|
88
88
|
|
89
89
|
def current_test_temp_path
|
90
|
-
@_current_test_temp_path ||= "#{Rails.root}/tmp/test_bot/#{current_test_name.parameterize}"
|
90
|
+
@_current_test_temp_path ||= "#{Rails.root}/tmp/test_bot/screenshots/#{current_test_name.parameterize}"
|
91
91
|
end
|
92
92
|
|
93
93
|
def current_test_failure_path
|
@@ -95,8 +95,7 @@ module EffectiveTestBotScreenshotsHelper
|
|
95
95
|
end
|
96
96
|
|
97
97
|
def current_test_failure_filename
|
98
|
-
#
|
99
|
-
"#{current_test_name.parameterize}-failure-#{Time.now.strftime('%Y-%m-%d-%H-%M-%S')}.gif"
|
98
|
+
"failures_#{current_test_name}.gif"
|
100
99
|
end
|
101
100
|
|
102
101
|
# Where the tour animated gif ends up
|
@@ -51,15 +51,6 @@ module EffectiveTestBotTestHelper
|
|
51
51
|
from_path != (to_path || page.current_path)
|
52
52
|
end
|
53
53
|
|
54
|
-
def was_download?(filename = nil)
|
55
|
-
if filename.present?
|
56
|
-
page.response_headers['Content-Disposition'].to_s.include?('filename=') &&
|
57
|
-
page.response_headers['Content-Disposition'].to_s.include?(filename)
|
58
|
-
else
|
59
|
-
page.response_headers['Content-Disposition'].to_s.include?('filename=')
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
54
|
# Calls capybara within do .. end if selector is present and bool is true
|
64
55
|
def within_if(selector, bool = true, &block)
|
65
56
|
(selector.present? && bool) ? within(selector) { yield } : yield
|
@@ -71,20 +62,26 @@ module EffectiveTestBotTestHelper
|
|
71
62
|
|
72
63
|
# EffectiveTestBot includes an after_filter on ApplicationController to set an http header
|
73
64
|
# These values are 'from the last page submit or refresh'
|
74
|
-
def
|
75
|
-
|
65
|
+
def response_code
|
66
|
+
page.evaluate_script('window.effective_test_bot.response_code')&.to_i
|
76
67
|
end
|
77
68
|
|
78
|
-
def
|
79
|
-
|
69
|
+
def flash
|
70
|
+
page.evaluate_script('window.effective_test_bot.flash')
|
80
71
|
end
|
81
72
|
|
82
|
-
def
|
83
|
-
|
73
|
+
def assigns
|
74
|
+
page.evaluate_script('window.effective_test_bot.assigns')
|
84
75
|
end
|
85
76
|
|
86
77
|
def access_denied_exception
|
87
|
-
|
78
|
+
return nil unless page.evaluate_script('window.effective_test_bot.access_denied').present?
|
79
|
+
|
80
|
+
{
|
81
|
+
'exception': page.evaluate_script('window.effective_test_bot.access_denied'),
|
82
|
+
'action': page.evaluate_script('window.effective_test_bot.action'),
|
83
|
+
'subject': page.evaluate_script('window.effective_test_bot.subject')
|
84
|
+
}
|
88
85
|
end
|
89
86
|
|
90
87
|
end
|
@@ -1,10 +1,10 @@
|
|
1
|
-
require '
|
1
|
+
require 'application_system_test_case'
|
2
2
|
|
3
3
|
# This gets run when we type `rake test:bot`
|
4
4
|
# Scan through every route and run a test suite against it
|
5
5
|
|
6
6
|
module TestBot
|
7
|
-
class ApplicationTest <
|
7
|
+
class ApplicationTest < ApplicationSystemTestCase
|
8
8
|
CRUD_ACTIONS = %w(index create new edit show update destroy) # Same order as resources :object creates them in
|
9
9
|
|
10
10
|
class << self
|
@@ -1,7 +1,7 @@
|
|
1
|
-
require
|
1
|
+
require 'application_system_test_case'
|
2
2
|
|
3
3
|
module TestBot
|
4
|
-
class EnvironmentTest <
|
4
|
+
class EnvironmentTest < ApplicationSystemTestCase
|
5
5
|
@@original_users_count = User.count
|
6
6
|
let(:original_users_count) { @@original_users_count }
|
7
7
|
|
@@ -52,7 +52,7 @@ module TestBot
|
|
52
52
|
user = User.new(email: 'unique@testbot.com', password: '!Password123', password_confirmation: '!Password123')
|
53
53
|
user.username = 'unique-username' if user.respond_to?(:username)
|
54
54
|
user.login = 'unique-login' if user.respond_to?(:login)
|
55
|
-
user.save
|
55
|
+
user.save!
|
56
56
|
|
57
57
|
without_screenshots { sign_in_manually(user, '!Password123') }
|
58
58
|
assert_signed_in("expected successful devise manual sign in with user created in this test.\nTry using one of the ActiveRecord shared_connection snippets in test/test_helper.rb")
|
@@ -60,7 +60,7 @@ module TestBot
|
|
60
60
|
|
61
61
|
test '09: capybara can execute javascript' do
|
62
62
|
visit root_path
|
63
|
-
|
63
|
+
assert_can_execute_javascript
|
64
64
|
end
|
65
65
|
|
66
66
|
test '10: jquery is present' do
|
@@ -79,5 +79,6 @@ module TestBot
|
|
79
79
|
"expected action_mailer.default_url_options[:host] to be present.\nAdd config.action_mailer.default_url_options = { host: 'example.com' } to config/environments/test.rb"
|
80
80
|
)
|
81
81
|
end
|
82
|
+
|
82
83
|
end
|
83
84
|
end
|
@@ -7,11 +7,10 @@ module BaseTest
|
|
7
7
|
def assert_page_normal(message = nil)
|
8
8
|
return if test_bot_skip?(:normal)
|
9
9
|
|
10
|
-
assert_no_exceptions unless test_bot_skip?(:exceptions)
|
11
10
|
assert_authorization unless test_bot_skip?(:authorization)
|
12
11
|
assert_page_status unless test_bot_skip?(:page_status)
|
13
12
|
assert_no_js_errors unless test_bot_skip?(:no_js_errors)
|
14
|
-
assert_page_title unless (test_bot_skip?(:page_title) || all('head').blank?
|
13
|
+
assert_page_title unless (test_bot_skip?(:page_title) || all('head').blank?)
|
15
14
|
end
|
16
15
|
|
17
16
|
private
|
@@ -53,7 +52,6 @@ module BaseTest
|
|
53
52
|
|
54
53
|
visit(new_path)
|
55
54
|
|
56
|
-
assert_no_exceptions
|
57
55
|
assert_authorization(hint)
|
58
56
|
assert_page_status
|
59
57
|
|
@@ -65,7 +63,6 @@ module BaseTest
|
|
65
63
|
fill_form(resource_attributes)
|
66
64
|
submit_novalidate_form
|
67
65
|
|
68
|
-
assert_no_exceptions
|
69
66
|
assert_authorization(hint)
|
70
67
|
assert_page_status
|
71
68
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: effective_test_bot
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 1.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Code and Effect
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-06-
|
11
|
+
date: 2018-06-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -16,78 +16,36 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version:
|
20
|
-
- - "<"
|
21
|
-
- !ruby/object:Gem::Version
|
22
|
-
version: '5.2'
|
23
|
-
type: :runtime
|
24
|
-
prerelease: false
|
25
|
-
version_requirements: !ruby/object:Gem::Requirement
|
26
|
-
requirements:
|
27
|
-
- - ">="
|
28
|
-
- !ruby/object:Gem::Version
|
29
|
-
version: 3.2.0
|
30
|
-
- - "<"
|
31
|
-
- !ruby/object:Gem::Version
|
32
|
-
version: '5.2'
|
33
|
-
- !ruby/object:Gem::Dependency
|
34
|
-
name: effective_resources
|
35
|
-
requirement: !ruby/object:Gem::Requirement
|
36
|
-
requirements:
|
37
|
-
- - ">="
|
38
|
-
- !ruby/object:Gem::Version
|
39
|
-
version: '0'
|
19
|
+
version: '5.1'
|
40
20
|
type: :runtime
|
41
21
|
prerelease: false
|
42
22
|
version_requirements: !ruby/object:Gem::Requirement
|
43
23
|
requirements:
|
44
24
|
- - ">="
|
45
25
|
- !ruby/object:Gem::Version
|
46
|
-
version: '
|
26
|
+
version: '5.1'
|
47
27
|
- !ruby/object:Gem::Dependency
|
48
|
-
name:
|
28
|
+
name: capybara
|
49
29
|
requirement: !ruby/object:Gem::Requirement
|
50
30
|
requirements:
|
51
31
|
- - ">="
|
52
32
|
- !ruby/object:Gem::Version
|
53
|
-
version: '
|
54
|
-
|
55
|
-
prerelease: false
|
56
|
-
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
requirements:
|
58
|
-
- - ">="
|
59
|
-
- !ruby/object:Gem::Version
|
60
|
-
version: '0'
|
61
|
-
- !ruby/object:Gem::Dependency
|
62
|
-
name: minitest-rails
|
63
|
-
requirement: !ruby/object:Gem::Requirement
|
64
|
-
requirements:
|
65
|
-
- - ">="
|
33
|
+
version: '2.15'
|
34
|
+
- - "<"
|
66
35
|
- !ruby/object:Gem::Version
|
67
|
-
version: '0'
|
36
|
+
version: '4.0'
|
68
37
|
type: :runtime
|
69
38
|
prerelease: false
|
70
39
|
version_requirements: !ruby/object:Gem::Requirement
|
71
40
|
requirements:
|
72
41
|
- - ">="
|
73
42
|
- !ruby/object:Gem::Version
|
74
|
-
version: '
|
75
|
-
-
|
76
|
-
name: minitest-capybara
|
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
|
-
- - ">="
|
43
|
+
version: '2.15'
|
44
|
+
- - "<"
|
87
45
|
- !ruby/object:Gem::Version
|
88
|
-
version: '0'
|
46
|
+
version: '4.0'
|
89
47
|
- !ruby/object:Gem::Dependency
|
90
|
-
name:
|
48
|
+
name: chromedriver-helper
|
91
49
|
requirement: !ruby/object:Gem::Requirement
|
92
50
|
requirements:
|
93
51
|
- - ">="
|
@@ -101,7 +59,7 @@ dependencies:
|
|
101
59
|
- !ruby/object:Gem::Version
|
102
60
|
version: '0'
|
103
61
|
- !ruby/object:Gem::Dependency
|
104
|
-
name:
|
62
|
+
name: selenium-webdriver
|
105
63
|
requirement: !ruby/object:Gem::Requirement
|
106
64
|
requirements:
|
107
65
|
- - ">="
|
@@ -115,7 +73,7 @@ dependencies:
|
|
115
73
|
- !ruby/object:Gem::Version
|
116
74
|
version: '0'
|
117
75
|
- !ruby/object:Gem::Dependency
|
118
|
-
name:
|
76
|
+
name: effective_resources
|
119
77
|
requirement: !ruby/object:Gem::Requirement
|
120
78
|
requirements:
|
121
79
|
- - ">="
|
@@ -129,7 +87,7 @@ dependencies:
|
|
129
87
|
- !ruby/object:Gem::Version
|
130
88
|
version: '0'
|
131
89
|
- !ruby/object:Gem::Dependency
|
132
|
-
name:
|
90
|
+
name: faker
|
133
91
|
requirement: !ruby/object:Gem::Requirement
|
134
92
|
requirements:
|
135
93
|
- - ">="
|
@@ -143,21 +101,7 @@ dependencies:
|
|
143
101
|
- !ruby/object:Gem::Version
|
144
102
|
version: '0'
|
145
103
|
- !ruby/object:Gem::Dependency
|
146
|
-
name:
|
147
|
-
requirement: !ruby/object:Gem::Requirement
|
148
|
-
requirements:
|
149
|
-
- - ">="
|
150
|
-
- !ruby/object:Gem::Version
|
151
|
-
version: 1.6.0
|
152
|
-
type: :runtime
|
153
|
-
prerelease: false
|
154
|
-
version_requirements: !ruby/object:Gem::Requirement
|
155
|
-
requirements:
|
156
|
-
- - ">="
|
157
|
-
- !ruby/object:Gem::Version
|
158
|
-
version: 1.6.0
|
159
|
-
- !ruby/object:Gem::Dependency
|
160
|
-
name: capybara-screenshot
|
104
|
+
name: minitest-fail-fast
|
161
105
|
requirement: !ruby/object:Gem::Requirement
|
162
106
|
requirements:
|
163
107
|
- - ">="
|
@@ -171,7 +115,7 @@ dependencies:
|
|
171
115
|
- !ruby/object:Gem::Version
|
172
116
|
version: '0'
|
173
117
|
- !ruby/object:Gem::Dependency
|
174
|
-
name:
|
118
|
+
name: minitest-reporters
|
175
119
|
requirement: !ruby/object:Gem::Requirement
|
176
120
|
requirements:
|
177
121
|
- - ">="
|
@@ -198,22 +142,8 @@ dependencies:
|
|
198
142
|
- - ">="
|
199
143
|
- !ruby/object:Gem::Version
|
200
144
|
version: '0'
|
201
|
-
|
202
|
-
|
203
|
-
requirement: !ruby/object:Gem::Requirement
|
204
|
-
requirements:
|
205
|
-
- - ">="
|
206
|
-
- !ruby/object:Gem::Version
|
207
|
-
version: '0'
|
208
|
-
type: :runtime
|
209
|
-
prerelease: false
|
210
|
-
version_requirements: !ruby/object:Gem::Requirement
|
211
|
-
requirements:
|
212
|
-
- - ">="
|
213
|
-
- !ruby/object:Gem::Version
|
214
|
-
version: '0'
|
215
|
-
description: A shared library of rails model & capybara-based feature tests that should
|
216
|
-
pass in every Rails application.
|
145
|
+
description: A shared library of rails model & system tests that should pass in every
|
146
|
+
Rails application.
|
217
147
|
email:
|
218
148
|
- info@codeandeffect.com
|
219
149
|
executables: []
|
@@ -224,12 +154,12 @@ files:
|
|
224
154
|
- README.md
|
225
155
|
- app/helpers/effective_test_bot_controller_helper.rb
|
226
156
|
- app/helpers/effective_test_bot_mailer_helper.rb
|
157
|
+
- config/application_system_test_case.rb
|
227
158
|
- config/effective_test_bot.rb
|
228
159
|
- config/test_helper.rb
|
229
160
|
- lib/effective_test_bot.rb
|
230
161
|
- lib/effective_test_bot/dsl.rb
|
231
162
|
- lib/effective_test_bot/engine.rb
|
232
|
-
- lib/effective_test_bot/middleware.rb
|
233
163
|
- lib/effective_test_bot/version.rb
|
234
164
|
- lib/generators/effective_test_bot/install_generator.rb
|
235
165
|
- lib/tasks/effective_test_bot_tasks.rake
|
@@ -249,8 +179,8 @@ files:
|
|
249
179
|
- test/support/effective_test_bot_minitest_helper.rb
|
250
180
|
- test/support/effective_test_bot_screenshots_helper.rb
|
251
181
|
- test/support/effective_test_bot_test_helper.rb
|
252
|
-
- test/test_bot/
|
253
|
-
- test/test_bot/
|
182
|
+
- test/test_bot/system/application_test.rb
|
183
|
+
- test/test_bot/system/environment_test.rb
|
254
184
|
- test/test_botable/base_test.rb
|
255
185
|
- test/test_botable/crud_test.rb
|
256
186
|
- test/test_botable/devise_test.rb
|
@@ -281,6 +211,6 @@ rubyforge_project:
|
|
281
211
|
rubygems_version: 2.4.5.1
|
282
212
|
signing_key:
|
283
213
|
specification_version: 4
|
284
|
-
summary: A shared library of rails model &
|
285
|
-
|
214
|
+
summary: A shared library of rails model & system tests that should pass in every
|
215
|
+
Rails application.
|
286
216
|
test_files: []
|
@@ -1,40 +0,0 @@
|
|
1
|
-
# Watch for any rails server exceptions and write the stacktrace to ./tmp/test_bot/exception.txt
|
2
|
-
# This file is checked for by assert_no_exceptions
|
3
|
-
|
4
|
-
module EffectiveTestBot
|
5
|
-
class Middleware
|
6
|
-
def initialize(app)
|
7
|
-
@app = app
|
8
|
-
end
|
9
|
-
|
10
|
-
def call(env)
|
11
|
-
begin
|
12
|
-
@app.call(env)
|
13
|
-
rescue Exception => exception
|
14
|
-
begin
|
15
|
-
save(exception)
|
16
|
-
rescue => e
|
17
|
-
puts "TestBotError: An error occurred while attempting to save a rails server exception: #{e.message}"
|
18
|
-
end
|
19
|
-
|
20
|
-
raise exception
|
21
|
-
end
|
22
|
-
end
|
23
|
-
|
24
|
-
def save(exception)
|
25
|
-
lines = [exception.message] + exception.backtrace.first(EffectiveTestBot.backtrace_lines)
|
26
|
-
|
27
|
-
dir = File.join(Dir.pwd, 'tmp', 'test_bot')
|
28
|
-
file = File.join(dir, 'exception.txt')
|
29
|
-
|
30
|
-
Dir.mkdir(dir) unless File.exist?(dir)
|
31
|
-
File.delete(file) if File.exist?(file)
|
32
|
-
|
33
|
-
File.open(file, 'w') do |file|
|
34
|
-
file.write "================== Start server exception ==================\n"
|
35
|
-
lines.each { |line| file.write(line); file.write("\n") }
|
36
|
-
file.write "=================== End server exception ===================\n"
|
37
|
-
end
|
38
|
-
end
|
39
|
-
end
|
40
|
-
end
|