cypress-on-rails 1.17.0 → 1.18.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/.github/workflows/ruby.yml +14 -14
- data/README.md +178 -22
- data/docs/authentication.md +30 -0
- data/docs/factory_bot_associations.md +14 -0
- data/lib/cypress_on_rails/configuration.rb +5 -0
- data/lib/cypress_on_rails/railtie.rb +10 -2
- data/lib/cypress_on_rails/vcr/insert_eject_middleware.rb +75 -0
- data/lib/cypress_on_rails/vcr/middleware_helpers.rb +51 -0
- data/lib/cypress_on_rails/vcr/use_cassette_middleware.rb +56 -0
- data/lib/cypress_on_rails/version.rb +1 -1
- data/lib/generators/cypress_on_rails/templates/config/initializers/cypress_on_rails.rb.erb +8 -0
- data/lib/generators/cypress_on_rails/templates/spec/cypress/support/commands.js +22 -0
- data/lib/generators/cypress_on_rails/templates/spec/cypress/support/on-rails.js +1 -0
- data/lib/generators/cypress_on_rails/templates/spec/e2e/e2e_helper.rb.erb +0 -5
- data/spec/cypress_on_rails/configuration_spec.rb +4 -1
- data/spec/cypress_on_rails/vcr/insert_eject_middleware_spec.rb +177 -0
- data/spec/cypress_on_rails/vcr/use_cassette_middleware_spec.rb +68 -0
- data/specs_e2e/rails_6_1/.gitattributes +10 -0
- data/specs_e2e/rails_6_1/Gemfile +20 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/Rakefile +1 -1
- data/specs_e2e/rails_6_1/app/assets/stylesheets/application.css +15 -0
- data/specs_e2e/rails_6_1/app/jobs/application_job.rb +7 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/layouts/application.html.erb +1 -1
- data/specs_e2e/rails_6_1/bin/bundle +114 -0
- data/specs_e2e/rails_6_1/bin/rails +5 -0
- data/specs_e2e/rails_6_1/bin/rake +5 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/bin/setup +15 -4
- data/specs_e2e/rails_6_1/bin/spring +14 -0
- data/specs_e2e/rails_6_1/bin/yarn +17 -0
- data/specs_e2e/rails_6_1/config/application.rb +34 -0
- data/specs_e2e/rails_6_1/config/boot.rb +4 -0
- data/specs_e2e/rails_6_1/config/cable.yml +10 -0
- data/specs_e2e/rails_6_1/config/credentials.yml.enc +1 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/database.yml +7 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/environment.rb +1 -1
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/environments/development.rb +22 -5
- data/specs_e2e/rails_6_1/config/environments/production.rb +120 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/environments/test.rb +24 -7
- data/specs_e2e/rails_6_1/config/initializers/backtrace_silencers.rb +8 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/initializers/content_security_policy.rb +5 -0
- data/specs_e2e/{rails_4_2 → rails_6_1}/config/initializers/filter_parameter_logging.rb +3 -1
- data/specs_e2e/rails_6_1/config/initializers/permissions_policy.rb +11 -0
- data/specs_e2e/{rails_3_2 → rails_6_1}/config/initializers/wrap_parameters.rb +5 -1
- data/specs_e2e/{rails_5_2 → rails_6_1}/config/locales/en.yml +1 -1
- data/specs_e2e/rails_6_1/config/master.key +1 -0
- data/specs_e2e/rails_6_1/config/puma.rb +43 -0
- data/specs_e2e/rails_6_1/config/storage.yml +34 -0
- data/specs_e2e/{rails_5_2 → rails_6_1}/config.ru +2 -1
- data/specs_e2e/{rails_5_2 → rails_6_1}/db/migrate/20180621085832_create_posts.rb +1 -1
- data/specs_e2e/rails_6_1/package.json +8 -0
- data/specs_e2e/rails_6_1/playwright-report/index.html +71 -0
- data/specs_e2e/rails_6_1/public/robots.txt +1 -0
- data/specs_e2e/rails_6_1/test-results/.last-run.json +4 -0
- data/specs_e2e/{rails_4_2 → rails_6_1}/test.sh +22 -15
- data/specs_e2e/rails_7_2/.gitattributes +9 -0
- data/specs_e2e/rails_7_2/.gitignore +16 -0
- data/specs_e2e/rails_7_2/.rubocop.yml +8 -0
- data/specs_e2e/rails_7_2/Gemfile +11 -0
- data/specs_e2e/{rails_4_2 → rails_7_2}/Rakefile +1 -1
- data/specs_e2e/rails_7_2/app/assets/stylesheets/application.css +15 -0
- data/specs_e2e/rails_7_2/app/controllers/application_controller.rb +4 -0
- data/specs_e2e/rails_7_2/app/controllers/posts_controller.rb +58 -0
- data/specs_e2e/rails_7_2/app/helpers/posts_helper.rb +2 -0
- data/specs_e2e/rails_7_2/app/jobs/application_job.rb +7 -0
- data/specs_e2e/rails_7_2/app/models/application_record.rb +3 -0
- data/specs_e2e/rails_7_2/app/models/post.rb +2 -0
- data/specs_e2e/rails_7_2/app/views/layouts/application.html.erb +22 -0
- data/specs_e2e/rails_7_2/app/views/posts/_form.html.erb +32 -0
- data/specs_e2e/rails_7_2/app/views/posts/edit.html.erb +6 -0
- data/specs_e2e/rails_7_2/app/views/posts/index.html.erb +31 -0
- data/specs_e2e/rails_7_2/app/views/posts/new.html.erb +5 -0
- data/specs_e2e/rails_7_2/app/views/posts/show.html.erb +19 -0
- data/specs_e2e/rails_7_2/bin/brakeman +7 -0
- data/specs_e2e/rails_7_2/bin/bundle +109 -0
- data/specs_e2e/rails_7_2/bin/importmap +4 -0
- data/specs_e2e/rails_7_2/bin/rails +4 -0
- data/specs_e2e/rails_7_2/bin/rake +4 -0
- data/specs_e2e/rails_7_2/bin/setup +37 -0
- data/specs_e2e/rails_7_2/config/application.rb +37 -0
- data/specs_e2e/rails_7_2/config/boot.rb +4 -0
- data/specs_e2e/rails_7_2/config/cable.yml +10 -0
- data/specs_e2e/rails_7_2/config/credentials.yml.enc +1 -0
- data/specs_e2e/rails_7_2/config/database.yml +32 -0
- data/specs_e2e/{rails_4_2 → rails_7_2}/config/environment.rb +1 -1
- data/specs_e2e/rails_7_2/config/environments/development.rb +54 -0
- data/specs_e2e/rails_7_2/config/environments/production.rb +105 -0
- data/specs_e2e/rails_7_2/config/environments/test.rb +45 -0
- data/specs_e2e/rails_7_2/config/importmap.rb +7 -0
- data/specs_e2e/rails_7_2/config/initializers/content_security_policy.rb +25 -0
- data/specs_e2e/rails_7_2/config/initializers/filter_parameter_logging.rb +8 -0
- data/specs_e2e/{rails_5_2 → rails_7_2}/config/initializers/inflections.rb +4 -4
- data/specs_e2e/rails_7_2/config/initializers/permissions_policy.rb +13 -0
- data/specs_e2e/rails_7_2/config/locales/en.yml +31 -0
- data/specs_e2e/rails_7_2/config/master.key +1 -0
- data/specs_e2e/rails_7_2/config/puma.rb +34 -0
- data/specs_e2e/rails_7_2/config/routes.rb +5 -0
- data/specs_e2e/rails_7_2/config/storage.yml +34 -0
- data/specs_e2e/{rails_4_2 → rails_7_2}/config.ru +3 -1
- data/specs_e2e/rails_7_2/db/migrate/20180621085832_create_posts.rb +11 -0
- data/specs_e2e/rails_7_2/db/seeds.rb +9 -0
- data/specs_e2e/rails_7_2/db/test.sqlite3-shm +0 -0
- data/specs_e2e/rails_7_2/db/test.sqlite3-wal +0 -0
- data/specs_e2e/rails_7_2/package.json +8 -0
- data/specs_e2e/rails_7_2/playwright-report/index.html +71 -0
- data/specs_e2e/{rails_4_2 → rails_7_2}/public/404.html +6 -6
- data/specs_e2e/rails_7_2/public/406-unsupported-browser.html +66 -0
- data/specs_e2e/{rails_4_2 → rails_7_2}/public/422.html +6 -6
- data/specs_e2e/{rails_4_2 → rails_7_2}/public/500.html +6 -6
- data/specs_e2e/rails_7_2/public/icon.png +0 -0
- data/specs_e2e/rails_7_2/public/icon.svg +3 -0
- data/specs_e2e/rails_7_2/public/robots.txt +1 -0
- data/specs_e2e/rails_7_2/storage/test.sqlite3 +0 -0
- data/specs_e2e/rails_7_2/test/controllers/posts_controller_test.rb +48 -0
- data/specs_e2e/rails_7_2/test/cypress_fixtures/posts.yml +11 -0
- data/specs_e2e/rails_7_2/test/fixtures/posts.yml +11 -0
- data/specs_e2e/rails_7_2/test/models/post_test.rb +7 -0
- data/specs_e2e/rails_7_2/test-results/.last-run.json +4 -0
- data/specs_e2e/rails_7_2/test.sh +57 -0
- data/specs_e2e/rails_8/.gitattributes +9 -0
- data/specs_e2e/rails_8/.gitignore +16 -0
- data/specs_e2e/rails_8/.rubocop.yml +8 -0
- data/specs_e2e/rails_8/Gemfile +20 -0
- data/specs_e2e/{rails_3_2 → rails_8}/Rakefile +2 -3
- data/specs_e2e/rails_8/app/assets/stylesheets/application.css +10 -0
- data/specs_e2e/rails_8/app/controllers/application_controller.rb +4 -0
- data/specs_e2e/rails_8/app/controllers/posts_controller.rb +58 -0
- data/specs_e2e/rails_8/app/helpers/posts_helper.rb +2 -0
- data/specs_e2e/rails_8/app/jobs/application_job.rb +7 -0
- data/specs_e2e/rails_8/app/models/application_record.rb +3 -0
- data/specs_e2e/rails_8/app/models/post.rb +2 -0
- data/specs_e2e/rails_8/app/views/layouts/application.html.erb +27 -0
- data/specs_e2e/rails_8/app/views/posts/_form.html.erb +32 -0
- data/specs_e2e/rails_8/app/views/posts/edit.html.erb +6 -0
- data/specs_e2e/rails_8/app/views/posts/index.html.erb +31 -0
- data/specs_e2e/rails_8/app/views/posts/new.html.erb +5 -0
- data/specs_e2e/rails_8/app/views/posts/show.html.erb +19 -0
- data/specs_e2e/rails_8/bin/brakeman +7 -0
- data/specs_e2e/rails_8/bin/bundle +109 -0
- data/specs_e2e/rails_8/bin/dev +2 -0
- data/specs_e2e/rails_8/bin/importmap +4 -0
- data/specs_e2e/rails_8/bin/rails +4 -0
- data/specs_e2e/rails_8/bin/rake +4 -0
- data/specs_e2e/rails_8/bin/setup +34 -0
- data/specs_e2e/rails_8/bin/thrust +5 -0
- data/specs_e2e/rails_8/config/application.rb +27 -0
- data/specs_e2e/rails_8/config/boot.rb +4 -0
- data/specs_e2e/rails_8/config/cable.yml +17 -0
- data/specs_e2e/rails_8/config/cache.yml +16 -0
- data/specs_e2e/rails_8/config/credentials.yml.enc +1 -0
- data/specs_e2e/rails_8/config/database.yml +41 -0
- data/specs_e2e/rails_8/config/deploy.yml +116 -0
- data/specs_e2e/rails_8/config/environment.rb +5 -0
- data/specs_e2e/rails_8/config/environments/development.rb +57 -0
- data/specs_e2e/rails_8/config/environments/production.rb +90 -0
- data/specs_e2e/rails_8/config/environments/test.rb +45 -0
- data/specs_e2e/rails_8/config/importmap.rb +7 -0
- data/specs_e2e/rails_8/config/initializers/content_security_policy.rb +25 -0
- data/specs_e2e/rails_8/config/initializers/filter_parameter_logging.rb +8 -0
- data/specs_e2e/rails_8/config/initializers/inflections.rb +16 -0
- data/specs_e2e/rails_8/config/locales/en.yml +31 -0
- data/specs_e2e/rails_8/config/master.key +1 -0
- data/specs_e2e/rails_8/config/puma.rb +41 -0
- data/specs_e2e/rails_8/config/queue.yml +18 -0
- data/specs_e2e/rails_8/config/recurring.yml +10 -0
- data/specs_e2e/rails_8/config/routes.rb +5 -0
- data/specs_e2e/rails_8/config/storage.yml +34 -0
- data/specs_e2e/rails_8/config.ru +6 -0
- data/specs_e2e/rails_8/db/cable_schema.rb +11 -0
- data/specs_e2e/rails_8/db/cache_schema.rb +14 -0
- data/specs_e2e/rails_8/db/migrate/20180621085832_create_posts.rb +11 -0
- data/specs_e2e/rails_8/db/queue_schema.rb +129 -0
- data/specs_e2e/rails_8/db/seeds.rb +9 -0
- data/specs_e2e/rails_8/package.json +8 -0
- data/specs_e2e/rails_8/playwright-report/index.html +71 -0
- data/specs_e2e/rails_8/public/400.html +114 -0
- data/specs_e2e/rails_8/public/404.html +114 -0
- data/specs_e2e/rails_8/public/406-unsupported-browser.html +114 -0
- data/specs_e2e/rails_8/public/422.html +114 -0
- data/specs_e2e/rails_8/public/500.html +114 -0
- data/specs_e2e/rails_8/public/icon.png +0 -0
- data/specs_e2e/rails_8/public/icon.svg +3 -0
- data/specs_e2e/rails_8/public/robots.txt +1 -0
- data/specs_e2e/rails_8/storage/test.sqlite3 +0 -0
- data/specs_e2e/rails_8/storage/test.sqlite3-shm +0 -0
- data/specs_e2e/rails_8/storage/test.sqlite3-wal +0 -0
- data/specs_e2e/rails_8/test/application_system_test_case.rb +5 -0
- data/specs_e2e/rails_8/test/controllers/posts_controller_test.rb +48 -0
- data/specs_e2e/rails_8/test/cypress_fixtures/posts.yml +11 -0
- data/specs_e2e/rails_8/test/fixtures/posts.yml +11 -0
- data/specs_e2e/rails_8/test/models/post_test.rb +7 -0
- data/specs_e2e/rails_8/test/test_helper.rb +15 -0
- data/specs_e2e/rails_8/test-results/.last-run.json +4 -0
- data/specs_e2e/{rails_5_2 → rails_8}/test.sh +1 -1
- metadata +217 -150
- data/lib/cypress_on_rails/vcr_middleware.rb +0 -73
- data/spec/cypress_on_rails/vcr_middleware_spec.rb +0 -119
- data/specs_e2e/rails_3_2/.gitignore +0 -9
- data/specs_e2e/rails_3_2/.ruby_version +0 -1
- data/specs_e2e/rails_3_2/Gemfile +0 -7
- data/specs_e2e/rails_3_2/README.rdoc +0 -261
- data/specs_e2e/rails_3_2/app/assets/stylesheets/application.css +0 -13
- data/specs_e2e/rails_3_2/app/controllers/application_controller.rb +0 -3
- data/specs_e2e/rails_3_2/app/controllers/welcome_controller.rb +0 -4
- data/specs_e2e/rails_3_2/app/helpers/application_helper.rb +0 -2
- data/specs_e2e/rails_3_2/app/models/post.rb +0 -21
- data/specs_e2e/rails_3_2/app/views/layouts/application.html.erb +0 -13
- data/specs_e2e/rails_3_2/app/views/welcome/index.html.erb +0 -24
- data/specs_e2e/rails_3_2/bin/rails +0 -6
- data/specs_e2e/rails_3_2/config/application.rb +0 -68
- data/specs_e2e/rails_3_2/config/boot.rb +0 -6
- data/specs_e2e/rails_3_2/config/environment.rb +0 -5
- data/specs_e2e/rails_3_2/config/environments/development.rb +0 -31
- data/specs_e2e/rails_3_2/config/environments/production.rb +0 -64
- data/specs_e2e/rails_3_2/config/environments/test.rb +0 -35
- data/specs_e2e/rails_3_2/config/initializers/backtrace_silencers.rb +0 -7
- data/specs_e2e/rails_3_2/config/initializers/inflections.rb +0 -15
- data/specs_e2e/rails_3_2/config/initializers/mime_types.rb +0 -5
- data/specs_e2e/rails_3_2/config/initializers/secret_token.rb +0 -7
- data/specs_e2e/rails_3_2/config/initializers/session_store.rb +0 -8
- data/specs_e2e/rails_3_2/config/locales/en.yml +0 -5
- data/specs_e2e/rails_3_2/config/routes.rb +0 -60
- data/specs_e2e/rails_3_2/config.ru +0 -4
- data/specs_e2e/rails_3_2/public/404.html +0 -26
- data/specs_e2e/rails_3_2/public/422.html +0 -26
- data/specs_e2e/rails_3_2/public/500.html +0 -25
- data/specs_e2e/rails_3_2/public/robots.txt +0 -5
- data/specs_e2e/rails_3_2/test.sh +0 -50
- data/specs_e2e/rails_4_2/.gitignore +0 -12
- data/specs_e2e/rails_4_2/Gemfile +0 -11
- data/specs_e2e/rails_4_2/README.rdoc +0 -28
- data/specs_e2e/rails_4_2/app/assets/javascripts/using_vcr.js +0 -2
- data/specs_e2e/rails_4_2/app/assets/stylesheets/using_vcr.css +0 -4
- data/specs_e2e/rails_4_2/app/controllers/application_controller.rb +0 -5
- data/specs_e2e/rails_4_2/app/controllers/using_vcr_controller.rb +0 -10
- data/specs_e2e/rails_4_2/app/controllers/welcome_controller.rb +0 -4
- data/specs_e2e/rails_4_2/app/models/post.rb +0 -23
- data/specs_e2e/rails_4_2/app/views/layouts/application.html.erb +0 -12
- data/specs_e2e/rails_4_2/app/views/using_vcr/index.html.erb +0 -6
- data/specs_e2e/rails_4_2/app/views/using_vcr/record_cats.html.erb +0 -7
- data/specs_e2e/rails_4_2/app/views/welcome/index.html.erb +0 -24
- data/specs_e2e/rails_4_2/bin/bundle +0 -3
- data/specs_e2e/rails_4_2/bin/rails +0 -4
- data/specs_e2e/rails_4_2/bin/rake +0 -4
- data/specs_e2e/rails_4_2/bin/setup +0 -29
- data/specs_e2e/rails_4_2/config/application.rb +0 -32
- data/specs_e2e/rails_4_2/config/boot.rb +0 -3
- data/specs_e2e/rails_4_2/config/environments/development.rb +0 -25
- data/specs_e2e/rails_4_2/config/environments/production.rb +0 -64
- data/specs_e2e/rails_4_2/config/environments/test.rb +0 -42
- data/specs_e2e/rails_4_2/config/initializers/backtrace_silencers.rb +0 -7
- data/specs_e2e/rails_4_2/config/initializers/cookies_serializer.rb +0 -3
- data/specs_e2e/rails_4_2/config/initializers/session_store.rb +0 -3
- data/specs_e2e/rails_4_2/config/initializers/to_time_preserves_timezone.rb +0 -10
- data/specs_e2e/rails_4_2/config/initializers/wrap_parameters.rb +0 -9
- data/specs_e2e/rails_4_2/config/locales/en.yml +0 -23
- data/specs_e2e/rails_4_2/config/routes.rb +0 -61
- data/specs_e2e/rails_4_2/config/secrets.yml +0 -22
- data/specs_e2e/rails_4_2/package.json +0 -12
- data/specs_e2e/rails_4_2/playwright-report/index.html +0 -62
- data/specs_e2e/rails_4_2/public/favicon.ico +0 -0
- data/specs_e2e/rails_4_2/public/robots.txt +0 -5
- data/specs_e2e/rails_4_2/spec/fixtures/vcr_cassettes/cats.yml +0 -63
- data/specs_e2e/rails_5_2/Gemfile +0 -15
- data/specs_e2e/rails_5_2/app/assets/javascripts/posts.js +0 -2
- data/specs_e2e/rails_5_2/app/assets/stylesheets/posts.css +0 -4
- data/specs_e2e/rails_5_2/app/assets/stylesheets/scaffold.css +0 -80
- data/specs_e2e/rails_5_2/app/jobs/application_job.rb +0 -2
- data/specs_e2e/rails_5_2/app/views/welcome/index.html.erb +0 -5
- data/specs_e2e/rails_5_2/bin/bundle +0 -3
- data/specs_e2e/rails_5_2/bin/rails +0 -4
- data/specs_e2e/rails_5_2/bin/rake +0 -4
- data/specs_e2e/rails_5_2/bin/update +0 -25
- data/specs_e2e/rails_5_2/config/application.rb +0 -33
- data/specs_e2e/rails_5_2/config/boot.rb +0 -4
- data/specs_e2e/rails_5_2/config/credentials.yml.enc +0 -1
- data/specs_e2e/rails_5_2/config/environments/production.rb +0 -68
- data/specs_e2e/rails_5_2/config/initializers/backtrace_silencers.rb +0 -7
- data/specs_e2e/rails_5_2/config/initializers/filter_parameter_logging.rb +0 -4
- data/specs_e2e/rails_5_2/config/initializers/mime_types.rb +0 -4
- data/specs_e2e/rails_5_2/config/initializers/wrap_parameters.rb +0 -9
- data/specs_e2e/rails_5_2/config/master.key +0 -1
- data/specs_e2e/rails_5_2/public/favicon.ico +0 -0
- data/specs_e2e/rails_5_2/public/robots.txt +0 -1
- /data/specs_e2e/{rails_5_2 → rails_6_1}/.gitignore +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/controllers/application_controller.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/controllers/posts_controller.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/helpers/posts_helper.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/models/application_record.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/models/post.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/posts/_form.html.erb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/posts/edit.html.erb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/posts/index.html.erb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/posts/new.html.erb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/app/views/posts/show.html.erb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/config/initializers/application_controller_renderer.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/config/initializers/cookies_serializer.rb +0 -0
- /data/specs_e2e/{rails_4_2 → rails_6_1}/config/initializers/inflections.rb +0 -0
- /data/specs_e2e/{rails_4_2 → rails_6_1}/config/initializers/mime_types.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/config/routes.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/public/404.html +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/public/422.html +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/public/500.html +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/public/apple-touch-icon-precomposed.png +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/public/apple-touch-icon.png +0 -0
- /data/specs_e2e/{rails_3_2 → rails_6_1}/public/favicon.ico +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/test/controllers/posts_controller_test.rb +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/test/cypress_fixtures/posts.yml +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/test/fixtures/posts.yml +0 -0
- /data/specs_e2e/{rails_5_2 → rails_6_1}/test/models/post_test.rb +0 -0
- /data/specs_e2e/{rails_3_2/log → rails_6_1/vendor}/.keep +0 -0
- /data/specs_e2e/{rails_3_2/tmp → rails_7_2/vendor}/.keep +0 -0
- /data/specs_e2e/{rails_4_2/spec → rails_7_2/vendor/javascript}/.keep +0 -0
- /data/specs_e2e/{rails_5_2 → rails_8}/README.md +0 -0
- /data/specs_e2e/{rails_4_2/vendor → rails_8/storage}/.keep +0 -0
- /data/specs_e2e/{rails_5_2 → rails_8}/vendor/.keep +0 -0
- /data/specs_e2e/{rails_3_2/vendor/.gitkeep → rails_8/vendor/javascript/.keep} +0 -0
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7fc65785a8f2d8eb2d7197abd2beac221b90c045f05ec126ee1ab96b2ee80f6c
|
4
|
+
data.tar.gz: dff5e1727f058aa6afc16ee9ca2c61c2f72039a9a0e2e00da4c95be38d6fd4a4
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c8cefbd4f704c001587c4a2321d5178a7f49e224039739079406b8666922571204d0bc6cb1f2dba9c7044d8932df5baf7c5c8c128afd349d3614dfa5a959b7ea
|
7
|
+
data.tar.gz: 5410e0101bc5bebf3acf5abecf3ee650a6dcb0fb328e700c87f3bd7f72a01b8f9ac47c67c322cf2f28205840f02ba331c2f6b5f7d03c8611d7a35c009e292826
|
data/.github/workflows/ruby.yml
CHANGED
@@ -7,57 +7,57 @@ on:
|
|
7
7
|
branches: [ master ]
|
8
8
|
|
9
9
|
jobs:
|
10
|
-
|
10
|
+
rails_6_1:
|
11
11
|
runs-on: ubuntu-latest
|
12
12
|
|
13
13
|
steps:
|
14
|
-
- uses: actions/checkout@
|
14
|
+
- uses: actions/checkout@v4
|
15
15
|
- name: Set up Ruby
|
16
16
|
uses: ruby/setup-ruby@v1
|
17
17
|
with:
|
18
|
-
ruby-version: 2.
|
18
|
+
ruby-version: 2.7.6
|
19
19
|
bundler-cache: true
|
20
20
|
- name: Run tests
|
21
21
|
run: bundle exec rake
|
22
|
-
- run: gem uninstall -v '>= 2' -ax bundler || true
|
23
|
-
- run: gem install bundler -v '< 2'
|
24
22
|
- name: Run interaction tests
|
25
|
-
run: ./specs_e2e/
|
23
|
+
run: ./specs_e2e/rails_6_1/test.sh
|
26
24
|
env:
|
27
25
|
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
|
28
26
|
|
29
|
-
|
27
|
+
rails_7_2:
|
30
28
|
runs-on: ubuntu-latest
|
31
29
|
|
32
30
|
steps:
|
33
|
-
- uses: actions/checkout@
|
31
|
+
- uses: actions/checkout@v4
|
34
32
|
- name: Set up Ruby
|
35
33
|
uses: ruby/setup-ruby@v1
|
36
34
|
with:
|
37
|
-
ruby-version:
|
35
|
+
ruby-version: 3.1.3
|
38
36
|
bundler-cache: true
|
39
37
|
- name: Run tests
|
40
38
|
run: bundle exec rake
|
41
39
|
- run: gem uninstall -v '>= 2' -ax bundler || true
|
42
40
|
- run: gem install bundler -v '< 2'
|
43
41
|
- name: Run interaction tests
|
44
|
-
run: ./specs_e2e/
|
42
|
+
run: ./specs_e2e/rails_7_2/test.sh
|
45
43
|
env:
|
46
44
|
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
|
47
45
|
|
48
|
-
|
46
|
+
rails_8:
|
49
47
|
runs-on: ubuntu-latest
|
50
48
|
|
51
49
|
steps:
|
52
|
-
- uses: actions/checkout@
|
50
|
+
- uses: actions/checkout@v4
|
53
51
|
- name: Set up Ruby
|
54
52
|
uses: ruby/setup-ruby@v1
|
55
53
|
with:
|
56
|
-
ruby-version: 2.
|
54
|
+
ruby-version: 3.2.2
|
57
55
|
bundler-cache: true
|
58
56
|
- name: Run tests
|
59
57
|
run: bundle exec rake
|
58
|
+
- run: gem uninstall -v '>= 2' -ax bundler || true
|
59
|
+
- run: gem install bundler -v '< 2'
|
60
60
|
- name: Run interaction tests
|
61
|
-
run: ./specs_e2e/
|
61
|
+
run: ./specs_e2e/rails_8/test.sh
|
62
62
|
env:
|
63
63
|
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
|
data/README.md
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# Cypress and Playwright on Rails
|
2
2
|
|
3
3
|

|
4
4
|
[](https://dashboard.cypress.io/projects/2b6cjr/runs)
|
@@ -6,33 +6,56 @@
|
|
6
6
|
|
7
7
|
----
|
8
8
|
|
9
|
-
This project is sponsored by the software consulting firm [ShakaCode](https://www.shakacode.com), creator of the [React on Rails Gem](https://github.com/shakacode/react_on_rails).
|
9
|
+
This project is sponsored by the software consulting firm [ShakaCode](https://www.shakacode.com), creator of the [React on Rails Gem](https://github.com/shakacode/react_on_rails).
|
10
10
|
|
11
|
-
|
11
|
+
### ShakaCode Support
|
12
12
|
|
13
|
-
|
13
|
+
[ShakaCode](https://www.shakacode.com) focuses on helping Ruby on Rails teams use React and Webpack better. We can upgrade your project and improve your development and customer experiences, allowing you to focus on building new features or fixing bugs instead.
|
14
|
+
|
15
|
+
For an overview of working with us, see our [Client Engagement Model](https://www.shakacode.com/blog/client-engagement-model/) article and [how we bill for time](https://www.shakacode.com/blog/shortcut-jira-trello-github-toggl-time-and-task-tracking/).
|
16
|
+
|
17
|
+
We also specialize in helping development teams lower infrastructure and CI costs. Check out our project [Control Plane Flow](https://github.com/shakacode/control-plane-flow/), which can allow you to get the ease of Heroku with the power of Kubernetes and big cost savings.
|
18
|
+
|
19
|
+
If you think ShakaCode can help your project, [click here](https://meetings.hubspot.com/justingordon/30-minute-consultation) to book a call with [Justin Gordon](mailto:justin@shakacode.com), the creator of React on Rails and Shakapacker.
|
20
|
+
|
21
|
+
Here's a testimonial of how ShakaCode can help from [Florian Gößler](https://github.com/FGoessler) of [Blinkist](https://www.blinkist.com/), January 2, 2023:
|
22
|
+
> Hey Justin 👋
|
23
|
+
>
|
24
|
+
> I just wanted to let you know that we today shipped the webpacker to shakapacker upgrades and it all seems to be running smoothly! Thanks again for all your support and your teams work! 😍
|
25
|
+
>
|
26
|
+
> On top of your work, it was now also very easy for me to upgrade Tailwind and include our external node_module based web component library which we were using for our other (more modern) apps already. That work is going to be shipped later this week though as we are polishing the last bits of it. 😉
|
27
|
+
>
|
28
|
+
> Have a great 2023 and maybe we get to work together again later in the year! 🙌
|
29
|
+
|
30
|
+
Read the [full review here](https://clutch.co/profile/shakacode#reviews?sort_by=date_DESC#review-2118154).
|
31
|
+
|
32
|
+
---
|
33
|
+
|
34
|
+
Feel free to engage in discussions around this gem at our [Slack Channel](https://join.slack.com/t/reactrails/shared_invite/enQtNjY3NTczMjczNzYxLTlmYjdiZmY3MTVlMzU2YWE0OWM0MzNiZDI0MzdkZGFiZTFkYTFkOGVjODBmOWEyYWQ3MzA2NGE1YWJjNmVlMGE) or our [forum category for Cypress](https://forum.shakacode.com/c/cypress-on-rails/55).
|
35
|
+
|
36
|
+
Need help with cypress-on-rails? Contact [Justin Gordon](mailto:justin@shakacode.com).
|
14
37
|
|
15
38
|
----
|
16
39
|
|
17
|
-
#
|
18
|
-
|
40
|
+
# New to Cypress?
|
41
|
+
Consider first learning the basics of Cypress before attempting to integrate with Ruby on Rails.
|
19
42
|
|
20
43
|
* [Good start Here](https://docs.cypress.io/examples/tutorials.html#Best-Practices)
|
21
44
|
|
22
45
|
# Totally new to Playwright?
|
23
|
-
|
46
|
+
Consider first learning the basics of Playwright before attempting to integrate with Ruby on Rails.
|
24
47
|
|
25
48
|
* [Good start Here](https://playwright.dev/docs/writing-tests)
|
26
49
|
|
27
50
|
## Overview
|
28
51
|
|
29
|
-
Gem for using [cypress.io](http://github.com/cypress-io/) or [playwright.dev](https://playwright.dev/) in Rails and Ruby Rack applications
|
52
|
+
Gem for using [cypress.io](http://github.com/cypress-io/) or [playwright.dev](https://playwright.dev/) in Rails and Ruby Rack applications to control state as mentioned in [Cypress Best Practices](https://docs.cypress.io/guides/references/best-practices.html#Organizing-Tests-Logging-In-Controlling-State).
|
30
53
|
|
31
|
-
It allows you to run code in the application
|
54
|
+
It allows you to run code in the context of the application when executing Cypress or Playwright tests.
|
32
55
|
Do things like:
|
33
56
|
* use database_cleaner before each test
|
34
57
|
* seed the database with default data for each test
|
35
|
-
* use factory_bot to
|
58
|
+
* use factory_bot to set up data
|
36
59
|
* create scenario files used for specific tests
|
37
60
|
|
38
61
|
Has examples of setting up state with:
|
@@ -96,10 +119,11 @@ Now you can create scenarios and commands that are plain Ruby files that get loa
|
|
96
119
|
|
97
120
|
### Update your database.yml
|
98
121
|
|
99
|
-
When writing and running tests on your local computer it's recommended to start your server in development mode so that changes you
|
122
|
+
When writing and running tests on your local computer, it's recommended to start your server in development mode so that changes you
|
100
123
|
make are picked up without having to restart your local server.
|
124
|
+
|
101
125
|
It's recommended you update your `database.yml` to check if the `CYPRESS` environment variable is set and switch it to the test database
|
102
|
-
otherwise cypress will keep clearing your development database.
|
126
|
+
otherwise, cypress will keep clearing your development database.
|
103
127
|
|
104
128
|
For example:
|
105
129
|
```yaml
|
@@ -148,6 +172,7 @@ npx cypress run --project ./e2e
|
|
148
172
|
|
149
173
|
You can run your [factory_bot](https://github.com/thoughtbot/factory_bot) directly as well
|
150
174
|
|
175
|
+
then in Cypress
|
151
176
|
```js
|
152
177
|
// spec/cypress/e2e/simple.cy.js
|
153
178
|
describe('My First Test', () => {
|
@@ -171,6 +196,32 @@ describe('My First Test', () => {
|
|
171
196
|
})
|
172
197
|
})
|
173
198
|
```
|
199
|
+
|
200
|
+
then in Playwright
|
201
|
+
```js
|
202
|
+
const { test, expect, request } = require('@playwright/test');
|
203
|
+
|
204
|
+
test.describe('My First Test', () => {
|
205
|
+
test('visit root', async ({ page }) => {
|
206
|
+
// This calls to the backend to prepare the application state
|
207
|
+
await appFactories([
|
208
|
+
['create_list', 'post', 10],
|
209
|
+
['create', 'post', { title: 'Hello World' }],
|
210
|
+
['create', 'post', 'with_comments', { title: 'Factory_bot Traits here' }]
|
211
|
+
]);
|
212
|
+
|
213
|
+
// Visit the application under test
|
214
|
+
await page.goto('/');
|
215
|
+
|
216
|
+
await expect(page).toHaveText('Hello World');
|
217
|
+
|
218
|
+
// Accessing result
|
219
|
+
const records = await appFactories([['create', 'invoice', { paid: false }]]);
|
220
|
+
await page.goto(`/invoices/${records[0].id}`);
|
221
|
+
});
|
222
|
+
});
|
223
|
+
```
|
224
|
+
|
174
225
|
You can check the [association docs](docs/factory_bot_associations.md) on more ways to setup association with the correct data.
|
175
226
|
|
176
227
|
In some cases, using static Cypress fixtures may not provide sufficient flexibility when mocking HTTP response bodies. It's possible to use `FactoryBot.build` to generate Ruby hashes that can then be used as mock JSON responses:
|
@@ -331,16 +382,21 @@ yarn add cypress-on-rails --dev
|
|
331
382
|
### for VCR
|
332
383
|
|
333
384
|
This only works when you start the Rails server with a single worker and single thread
|
385
|
+
It can be used in two modes:
|
386
|
+
- with separate insert/eject calls (more general, recommended way)
|
387
|
+
- with use_cassette wrapper (supports only GraphQL integration)
|
334
388
|
|
335
|
-
#### setup
|
389
|
+
#### basic setup
|
336
390
|
|
337
|
-
Add your VCR configuration to your `
|
391
|
+
Add your VCR configuration to your `config/cypress_on_rails.rb`
|
338
392
|
|
339
393
|
```ruby
|
340
|
-
|
341
|
-
|
342
|
-
|
343
|
-
|
394
|
+
c.vcr_options = {
|
395
|
+
hook_into: :webmock,
|
396
|
+
default_cassette_options: { record: :once },
|
397
|
+
# It's possible to override cassette_library_dir using install_folder
|
398
|
+
cassette_library_dir: File.expand_path("#{__dir__}/../../spec/cypress/fixtures/vcr_cassettes")
|
399
|
+
}
|
344
400
|
```
|
345
401
|
|
346
402
|
Add to your `cypress/support/index.js`:
|
@@ -357,13 +413,16 @@ VCR.turn_off!
|
|
357
413
|
WebMock.disable! if defined?(WebMock)
|
358
414
|
```
|
359
415
|
|
416
|
+
#### insert/eject setup
|
417
|
+
|
360
418
|
Add to your `config/cypress_on_rails.rb`:
|
361
419
|
|
362
420
|
```ruby
|
363
421
|
c.use_vcr_middleware = !Rails.env.production? && ENV['CYPRESS'].present?
|
422
|
+
# c.use_vcr_use_cassette_middleware = !Rails.env.production? && ENV['CYPRESS'].present?
|
364
423
|
```
|
365
424
|
|
366
|
-
#### usage
|
425
|
+
#### insert/eject usage
|
367
426
|
|
368
427
|
You have `vcr_insert_cassette` and `vcr_eject_cassette` available. https://www.rubydoc.info/github/vcr/vcr/VCR:insert_cassette
|
369
428
|
|
@@ -390,6 +449,63 @@ describe('My First Test', () => {
|
|
390
449
|
})
|
391
450
|
```
|
392
451
|
|
452
|
+
#### use_cassette setup
|
453
|
+
|
454
|
+
Add to your `config/cypress_on_rails.rb`:
|
455
|
+
|
456
|
+
```ruby
|
457
|
+
# c.use_vcr_middleware = !Rails.env.production? && ENV['CYPRESS'].present?
|
458
|
+
c.use_vcr_use_cassette_middleware = !Rails.env.production? && ENV['CYPRESS'].present?
|
459
|
+
```
|
460
|
+
|
461
|
+
Adjust record mode in `config/cypress_on_rails.rb` if needed:
|
462
|
+
|
463
|
+
```ruby
|
464
|
+
c.vcr_options = {
|
465
|
+
hook_into: :webmock,
|
466
|
+
default_cassette_options: { record: :once },
|
467
|
+
}
|
468
|
+
```
|
469
|
+
|
470
|
+
Add to your `cypress/support/command.js`:
|
471
|
+
|
472
|
+
```js
|
473
|
+
// Add proxy-like mock to add operation name into query string
|
474
|
+
Cypress.Commands.add('mockGraphQL', () => {
|
475
|
+
cy.on('window:before:load', (win) => {
|
476
|
+
const originalFetch = win.fetch;
|
477
|
+
const fetch = (path, options, ...rest) => {
|
478
|
+
if (options && options.body) {
|
479
|
+
try {
|
480
|
+
const body = JSON.parse(options.body);
|
481
|
+
if (body.operationName) {
|
482
|
+
return originalFetch(`${path}?operation=${body.operationName}`, options, ...rest);
|
483
|
+
}
|
484
|
+
} catch (e) {
|
485
|
+
return originalFetch(path, options, ...rest);
|
486
|
+
}
|
487
|
+
}
|
488
|
+
return originalFetch(path, options, ...rest);
|
489
|
+
};
|
490
|
+
cy.stub(win, 'fetch', fetch);
|
491
|
+
});
|
492
|
+
});
|
493
|
+
```
|
494
|
+
|
495
|
+
Add to your `cypress/support/on-rails.js`, to `beforeEach`:
|
496
|
+
|
497
|
+
```js
|
498
|
+
cy.mockGraphQL() // for GraphQL usage with use_cassette, see cypress/support/commands.rb
|
499
|
+
```
|
500
|
+
|
501
|
+
#### use_cassette usage
|
502
|
+
|
503
|
+
There is nothing special to be called during the Cypress scenario. Each request is wrapped with `VCR.use_cassette`.
|
504
|
+
Consider VCR configuration in `cypress_helper.rb` to ignore hosts.
|
505
|
+
|
506
|
+
All cassettes will be recorded and saved automatically, using the pattern `<vcs_cassettes_path>/graphql/<operation_name>`
|
507
|
+
|
508
|
+
|
393
509
|
## `before_request` configuration
|
394
510
|
|
395
511
|
You may perform any custom action before running a CypressOnRails command, such as authentication, or sending metrics. Please set `before_request` as part of the CypressOnRails configuration.
|
@@ -485,6 +601,46 @@ beforeEach(() => {
|
|
485
601
|
});
|
486
602
|
```
|
487
603
|
|
604
|
+
add the following file to Playwright
|
605
|
+
```js
|
606
|
+
// test/playwright/support/on-rails.js
|
607
|
+
async function appCommands(body) {
|
608
|
+
const context = await request.newContext();
|
609
|
+
const response = await context.post('/__e2e__/command', {
|
610
|
+
data: body,
|
611
|
+
headers: {
|
612
|
+
'Content-Type': 'application/json'
|
613
|
+
}
|
614
|
+
});
|
615
|
+
|
616
|
+
if (response.status() !== 201) {
|
617
|
+
const responseBody = await response.text();
|
618
|
+
throw new Error(`Expected status 201 but got ${response.status()} - ${responseBody}`);
|
619
|
+
}
|
620
|
+
|
621
|
+
return response.json();
|
622
|
+
}
|
623
|
+
|
624
|
+
async function app(name, commandOptions = {}) {
|
625
|
+
const body = await appCommands({ name, options: commandOptions });
|
626
|
+
return body[0];
|
627
|
+
}
|
628
|
+
|
629
|
+
async function appScenario(name, options = {}) {
|
630
|
+
const body = { name: `scenarios/${name}`, options };
|
631
|
+
const result = await appCommands(body);
|
632
|
+
return result[0];
|
633
|
+
}
|
634
|
+
|
635
|
+
async function appFactories(options) {
|
636
|
+
return app('factory_bot', options);
|
637
|
+
}
|
638
|
+
|
639
|
+
async function clean() {
|
640
|
+
await app('clean');
|
641
|
+
}
|
642
|
+
```
|
643
|
+
|
488
644
|
## API Prefix
|
489
645
|
|
490
646
|
If your Rails server is exposed under a proxy, typically https://my-local.dev/api, you can use the `api_prefix` option.
|
@@ -506,8 +662,8 @@ In `config/initializers/cypress_on_rails.rb`, add this line:
|
|
506
662
|
|
507
663
|
## Supporters
|
508
664
|
|
509
|
-
<a href="https://
|
510
|
-
<img src="https://
|
665
|
+
<a href="https://jb.gg/OpenSource" style="margin-right: 20px;">
|
666
|
+
<img src="https://resources.jetbrains.com/storage/products/company/brand/logos/jetbrains.png" alt="JetBrains" height="120px">
|
511
667
|
</a>
|
512
668
|
<a href="https://scoutapp.com">
|
513
669
|
<picture>
|
@@ -516,7 +672,7 @@ In `config/initializers/cypress_on_rails.rb`, add this line:
|
|
516
672
|
<img alt="ScoutAPM" src="https://user-images.githubusercontent.com/4244251/184881152-9f2d8fba-88ac-4ba6-873b-22387f8711c5.png" height="120px">
|
517
673
|
</picture>
|
518
674
|
</a>
|
519
|
-
<a href="https://controlplane.com">
|
675
|
+
<a href="https://shakacode.controlplane.com">
|
520
676
|
<picture>
|
521
677
|
<img alt="Control Plane" src="https://github.com/shakacode/.github/assets/20628911/90babd87-62c4-4de3-baa4-3d78ef4bec25" height="120px">
|
522
678
|
</picture>
|
data/docs/authentication.md
CHANGED
@@ -51,3 +51,33 @@ cy.forceLogin()
|
|
51
51
|
cy.forceLogin({redirect_to: '/profile'})
|
52
52
|
cy.forceLogin({email: 'someuser@mail.com'})
|
53
53
|
```
|
54
|
+
|
55
|
+
In `playwright/support/on-rails.js`:
|
56
|
+
|
57
|
+
```js
|
58
|
+
async function forceLogin(page, { email, redirect_to = '/' }) {
|
59
|
+
// Validate inputs
|
60
|
+
if (typeof email !== 'string' || typeof redirect_to !== 'string') {
|
61
|
+
throw new Error('Invalid input: email and redirect_to must be non-empty strings');
|
62
|
+
}
|
63
|
+
|
64
|
+
const response = await page.request.post('/__e2e__/force_login', {
|
65
|
+
data: { email: email, redirect_to: redirect_to },
|
66
|
+
headers: { 'Content-Type': 'application/json' }
|
67
|
+
});
|
68
|
+
|
69
|
+
// Handle response based on status code
|
70
|
+
if (response.ok()) {
|
71
|
+
await page.goto(redirect_to);
|
72
|
+
} else {
|
73
|
+
// Throw an exception for specific error statuses
|
74
|
+
throw new Error(`Login failed with status: ${response.status()}`);
|
75
|
+
}
|
76
|
+
}
|
77
|
+
```
|
78
|
+
|
79
|
+
Examples of usage in Playwright specs:
|
80
|
+
```js
|
81
|
+
await forceLogin(page, { email: 'someuser@mail.com', redirect_to: '/profile' });
|
82
|
+
|
83
|
+
```
|
@@ -54,6 +54,15 @@ cy.appFactories([['create', 'author']]).then((records) => {
|
|
54
54
|
})
|
55
55
|
```
|
56
56
|
|
57
|
+
then in Playwright
|
58
|
+
There are a few ways you can set up associations with the correct data using Playwright and FactoryBot.
|
59
|
+
```js
|
60
|
+
const records = await appFactories([['create', 'author', { name: 'James' }]], context);
|
61
|
+
await appFactories([['create', 'post', { title: 'Playwright is cool', author_id: records[0].id }]], context);
|
62
|
+
// Note: These Playwright examples demonstrate asynchronous interactions with the server for setting up data associations. Ensure that your environment is configured to handle these async operations.
|
63
|
+
```
|
64
|
+
|
65
|
+
|
57
66
|
## 2. Using transient attributes
|
58
67
|
|
59
68
|
```rb
|
@@ -81,6 +90,11 @@ cy.appFactories([['create', 'post', { title: 'Cypress is cool', author_name: 'Ja
|
|
81
90
|
cy.appFactories([['create', 'post']])
|
82
91
|
```
|
83
92
|
|
93
|
+
then in Playwright
|
94
|
+
```js
|
95
|
+
const records = await appFactories([['create', 'post', { title: 'Playwright is cool', author_name: 'James' }]]);
|
96
|
+
```
|
97
|
+
|
84
98
|
## 3. Using Nested Attributes
|
85
99
|
|
86
100
|
```rb
|
@@ -6,8 +6,10 @@ module CypressOnRails
|
|
6
6
|
attr_accessor :install_folder
|
7
7
|
attr_accessor :use_middleware
|
8
8
|
attr_accessor :use_vcr_middleware
|
9
|
+
attr_accessor :use_vcr_use_cassette_middleware
|
9
10
|
attr_accessor :before_request
|
10
11
|
attr_accessor :logger
|
12
|
+
attr_accessor :vcr_options
|
11
13
|
|
12
14
|
# Attributes for backwards compatibility
|
13
15
|
def cypress_folder
|
@@ -25,14 +27,17 @@ module CypressOnRails
|
|
25
27
|
|
26
28
|
alias :use_middleware? :use_middleware
|
27
29
|
alias :use_vcr_middleware? :use_vcr_middleware
|
30
|
+
alias :use_vcr_use_cassette_middleware? :use_vcr_use_cassette_middleware
|
28
31
|
|
29
32
|
def reset
|
30
33
|
self.api_prefix = ''
|
31
34
|
self.install_folder = 'spec/e2e'
|
32
35
|
self.use_middleware = true
|
33
36
|
self.use_vcr_middleware = false
|
37
|
+
self.use_vcr_use_cassette_middleware = false
|
34
38
|
self.before_request = -> (request) {}
|
35
39
|
self.logger = Logger.new(STDOUT)
|
40
|
+
self.vcr_options = {}
|
36
41
|
end
|
37
42
|
|
38
43
|
def tagged_logged
|
@@ -9,8 +9,16 @@ module CypressOnRails
|
|
9
9
|
app.middleware.use Middleware
|
10
10
|
end
|
11
11
|
if CypressOnRails.configuration.use_vcr_middleware?
|
12
|
-
require 'cypress_on_rails/
|
13
|
-
app.middleware.use
|
12
|
+
require 'cypress_on_rails/vcr/insert_eject_middleware'
|
13
|
+
app.middleware.use Vcr::InsertEjectMiddleware
|
14
|
+
end
|
15
|
+
if CypressOnRails.configuration.use_vcr_use_cassette_middleware?
|
16
|
+
if CypressOnRails.configuration.use_vcr_middleware?
|
17
|
+
raise 'Configure only one VCR middleware at a time: use_vcr_middleware OR use_vcr_use_cassette_middleware'
|
18
|
+
end
|
19
|
+
|
20
|
+
require 'cypress_on_rails/vcr/use_cassette_middleware'
|
21
|
+
app.middleware.use Vcr::UseCassetteMiddleware
|
14
22
|
end
|
15
23
|
end
|
16
24
|
end
|
@@ -0,0 +1,75 @@
|
|
1
|
+
require_relative 'middleware_helpers'
|
2
|
+
|
3
|
+
module CypressOnRails
|
4
|
+
module Vcr
|
5
|
+
# Middleware to handle vcr with insert/eject endpoints
|
6
|
+
class InsertEjectMiddleware
|
7
|
+
include MiddlewareHelpers
|
8
|
+
|
9
|
+
def initialize(app, vcr = nil)
|
10
|
+
@app = app
|
11
|
+
@vcr = vcr
|
12
|
+
@first_call = false
|
13
|
+
end
|
14
|
+
|
15
|
+
def call(env)
|
16
|
+
request = Rack::Request.new(env)
|
17
|
+
if request.path.start_with?('/__e2e__/vcr/insert')
|
18
|
+
configuration.tagged_logged { handle_insert(request) }
|
19
|
+
elsif request.path.start_with?('/__e2e__/vcr/eject')
|
20
|
+
configuration.tagged_logged { handle_eject }
|
21
|
+
else
|
22
|
+
do_first_call unless @first_call
|
23
|
+
@app.call(env)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
def handle_insert(req)
|
30
|
+
WebMock.enable! if defined?(WebMock)
|
31
|
+
vcr.turn_on!
|
32
|
+
body = parse_request_body(req)
|
33
|
+
logger.info "vcr insert cassette: #{body}"
|
34
|
+
cassette_name, options = extract_cassette_info(body)
|
35
|
+
vcr.insert_cassette(cassette_name, options)
|
36
|
+
[201, { 'Content-Type' => 'application/json' }, [{ 'message': 'OK' }.to_json]]
|
37
|
+
rescue JSON::ParserError => e
|
38
|
+
[400, { 'Content-Type' => 'application/json' }, [{ 'message': e.message }.to_json]]
|
39
|
+
rescue LoadError, ArgumentError => e
|
40
|
+
[500, { 'Content-Type' => 'application/json' }, [{ 'message': e.message }.to_json]]
|
41
|
+
end
|
42
|
+
|
43
|
+
def parse_request_body(req)
|
44
|
+
JSON.parse(req.body.read)
|
45
|
+
end
|
46
|
+
|
47
|
+
def extract_cassette_info(body)
|
48
|
+
cassette_name = body[0]
|
49
|
+
options = (body[1] || {}).symbolize_keys
|
50
|
+
options[:record] = options[:record].to_sym if options[:record]
|
51
|
+
options[:match_requests_on] = options[:match_requests_on].map(&:to_sym) if options[:match_requests_on]
|
52
|
+
options[:serialize_with] = options[:serialize_with].to_sym if options[:serialize_with]
|
53
|
+
options[:persist_with] = options[:persist_with].to_sym if options[:persist_with]
|
54
|
+
[cassette_name, options]
|
55
|
+
end
|
56
|
+
|
57
|
+
def handle_eject
|
58
|
+
logger.info 'vcr eject cassette'
|
59
|
+
vcr.eject_cassette
|
60
|
+
do_first_call
|
61
|
+
[201, { 'Content-Type' => 'application/json' }, [{ 'message': 'OK' }.to_json]]
|
62
|
+
rescue LoadError, ArgumentError => e
|
63
|
+
[500, { 'Content-Type' => 'application/json' }, [{ 'message': e.message }.to_json]]
|
64
|
+
end
|
65
|
+
|
66
|
+
def do_first_call
|
67
|
+
@first_call = true
|
68
|
+
vcr.turn_off!
|
69
|
+
WebMock.disable! if defined?(WebMock)
|
70
|
+
rescue LoadError
|
71
|
+
# nop
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
@@ -0,0 +1,51 @@
|
|
1
|
+
require 'cypress_on_rails/middleware_config'
|
2
|
+
|
3
|
+
module CypressOnRails
|
4
|
+
module Vcr
|
5
|
+
# Provides helper methods for VCR middlewares
|
6
|
+
module MiddlewareHelpers
|
7
|
+
include MiddlewareConfig
|
8
|
+
|
9
|
+
def vcr
|
10
|
+
@vcr ||= configure_vcr
|
11
|
+
end
|
12
|
+
|
13
|
+
def cassette_library_dir
|
14
|
+
configuration.vcr_options&.fetch(:cassette_library_dir) do
|
15
|
+
"#{configuration.install_folder}/fixtures/vcr_cassettes"
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
private
|
20
|
+
|
21
|
+
def configure_vcr
|
22
|
+
require 'vcr'
|
23
|
+
VCR.configure do |config|
|
24
|
+
config.cassette_library_dir = cassette_library_dir
|
25
|
+
apply_vcr_options(config) if configuration.vcr_options.present?
|
26
|
+
end
|
27
|
+
VCR
|
28
|
+
end
|
29
|
+
|
30
|
+
def apply_vcr_options(config)
|
31
|
+
configuration.vcr_options.each do |option, value|
|
32
|
+
next if option.to_sym == :cassette_library_dir
|
33
|
+
|
34
|
+
apply_vcr_option(config, option, value)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
def apply_vcr_option(config, option, value)
|
39
|
+
return unless config.respond_to?(option) || config.respond_to?("#{option}=")
|
40
|
+
|
41
|
+
if config.respond_to?("#{option}=")
|
42
|
+
config.send("#{option}=", value)
|
43
|
+
elsif value.is_a?(Array)
|
44
|
+
config.send(option, *value)
|
45
|
+
else
|
46
|
+
config.send(option, value)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
@@ -0,0 +1,56 @@
|
|
1
|
+
require_relative 'middleware_helpers'
|
2
|
+
|
3
|
+
module CypressOnRails
|
4
|
+
module Vcr
|
5
|
+
# Middleware to handle vcr with use_cassette
|
6
|
+
class UseCassetteMiddleware
|
7
|
+
include MiddlewareHelpers
|
8
|
+
|
9
|
+
def initialize(app, vcr = nil)
|
10
|
+
@app = app
|
11
|
+
@vcr = vcr
|
12
|
+
end
|
13
|
+
|
14
|
+
def call(env)
|
15
|
+
return @app.call(env) if should_not_use_vcr?
|
16
|
+
|
17
|
+
initialize_vcr
|
18
|
+
handle_request_with_vcr(env)
|
19
|
+
end
|
20
|
+
|
21
|
+
private
|
22
|
+
|
23
|
+
def vcr_defined?
|
24
|
+
defined?(VCR) != nil
|
25
|
+
end
|
26
|
+
|
27
|
+
def should_not_use_vcr?
|
28
|
+
vcr_defined? &&
|
29
|
+
VCR.configuration.cassette_library_dir.present? &&
|
30
|
+
VCR.configuration.cassette_library_dir != cassette_library_dir
|
31
|
+
end
|
32
|
+
|
33
|
+
def initialize_vcr
|
34
|
+
WebMock.enable! if defined?(WebMock)
|
35
|
+
vcr.turn_on!
|
36
|
+
end
|
37
|
+
|
38
|
+
def handle_request_with_vcr(env)
|
39
|
+
request = Rack::Request.new(env)
|
40
|
+
cassette_name = fetch_request_cassette(request)
|
41
|
+
vcr.use_cassette(cassette_name) do
|
42
|
+
logger.info "Handle request with cassette name: #{cassette_name}"
|
43
|
+
@app.call(env)
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
def fetch_request_cassette(request)
|
48
|
+
if request.path.start_with?('/graphql') && request.params.key?('operation')
|
49
|
+
"#{request.path}/#{request.params['operation']}"
|
50
|
+
else
|
51
|
+
request.path
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|