rails_readonly_injector 0.2.0 → 1.2.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.
Files changed (44) hide show
  1. checksums.yaml +5 -5
  2. data/.github/ISSUE_TEMPLATE.md +18 -0
  3. data/.github/PULL_REQUEST_TEMPLATE.md +24 -0
  4. data/.gitignore +1 -1
  5. data/.rubocop.yml +7 -0
  6. data/.travis.yml +3 -1
  7. data/Appraisals +10 -1
  8. data/CHANGELOG.md +6 -0
  9. data/CODE_OF_CONDUCT.md +0 -0
  10. data/Gemfile +4 -2
  11. data/LICENSE.txt +0 -0
  12. data/README.md +25 -6
  13. data/Rakefile +4 -2
  14. data/bin/console +4 -3
  15. data/cucumber_features/configuration.feature +0 -0
  16. data/cucumber_features/step_definitions/.gitkeep +0 -0
  17. data/cucumber_features/step_definitions/generic_steps.rb +5 -3
  18. data/cucumber_features/step_definitions/user_steps.rb +18 -14
  19. data/cucumber_features/support/.gitkeep +0 -0
  20. data/cucumber_features/user_controller.feature +0 -0
  21. data/cucumber_features/user_controller_readonly.feature +0 -0
  22. data/cucumber_features/user_model.feature +0 -0
  23. data/cucumber_features/user_model_readonly.feature +0 -0
  24. data/development_tasks/support/file_helpers.rb +57 -0
  25. data/development_tasks/support/gem_helpers.rb +63 -0
  26. data/development_tasks/tests.rake +40 -93
  27. data/gemfiles/.bundle/config +0 -0
  28. data/gemfiles/rails_3.gemfile +0 -0
  29. data/gemfiles/rails_4_0.gemfile +0 -0
  30. data/gemfiles/rails_4_1.gemfile +0 -0
  31. data/gemfiles/rails_4_2.gemfile +0 -0
  32. data/gemfiles/rails_5_0.gemfile +0 -0
  33. data/gemfiles/rails_5_1.gemfile +0 -0
  34. data/gemfiles/rails_5_2.gemfile +10 -0
  35. data/lib/rails_readonly_injector.rb +37 -20
  36. data/lib/rails_readonly_injector/configuration.rb +86 -20
  37. data/lib/rails_readonly_injector/version.rb +3 -1
  38. data/rails_readonly_injector.gemspec +16 -14
  39. data/rspec_specs/.gitkeep +0 -0
  40. data/rspec_specs/rails_readonly_injector/configuration_spec.rb +167 -0
  41. data/rspec_specs/{readonly_site_toggle_spec.rb → rails_readonly_injector_spec.rb} +42 -1
  42. data/rspec_specs/support/.gitkeep +0 -0
  43. metadata +36 -18
  44. data/rspec_specs/readonly_site_toggle/configuration_spec.rb +0 -31
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 9509703bc12b066f6af792e478484e61bb0a0249
4
- data.tar.gz: 21225186b776c134d52ec75b95ce3483fd70c21f
2
+ SHA256:
3
+ metadata.gz: b312c92be7dd7bf454f93b2359d6615eac31e5db380c10823da084b1a012c43f
4
+ data.tar.gz: 82fd6c6929b64104bf7d68044e5c13557bf798cedaad996a5495234c99d08366
5
5
  SHA512:
6
- metadata.gz: e5aa0948322922fd1940fb817fe4ac52bdcbf3fdc2ff3f1630835e7cd80f4fd4f0bb990812f974b447c2364379f008c5bb951fbf643fd8feb82b5a8fb949c25b
7
- data.tar.gz: 2d7734d7370b5eda65ceababacd75302013dddfd4c26ba2e95fcc4126e75db3c00310198d92a9e9d5d2b9790846f544422a8f67c4f03a4489431886108ec5bb6
6
+ metadata.gz: 5ebe26220df8db19da6ddf8623b5fb7f3d09a3c192eac5ffec3794106b9008126cbb4276f222027e6e4bfbfa1871f3abbd7da2f7356267a77a9e57760a677a5c
7
+ data.tar.gz: 476aa9f4c712902fac248b7b185a931b13d056f4414b5b483842087c19ddc7116118ddece04f3a86f41f579f2af1efe5826bce525f3846c60e2a851cf9bc680d
@@ -0,0 +1,18 @@
1
+ ## Expected Behavior
2
+
3
+
4
+ ## Actual Behavior
5
+
6
+
7
+ ## Steps to Reproduce the Problem
8
+
9
+ 1.
10
+ 2.
11
+ 3.
12
+ 4.
13
+
14
+ ## Specifications
15
+
16
+ - Version:
17
+ - Platform:
18
+ - Subsystem:
@@ -0,0 +1,24 @@
1
+ ## Problem
2
+
3
+ <!-- Describe the problem that this PR resolves -->
4
+
5
+ #### Related issues:
6
+ <!-- Link to issues that are related to this problem. If there aren't any, you can remove the heading. -->
7
+
8
+ ## How this PR resolves the problem
9
+
10
+ <!--- Describe how your PR resolves this problem -->
11
+
12
+ ## Types of changes
13
+
14
+ <!--- What types of changes does your code introduce? Put an `x` in all the boxes that apply: -->
15
+ - [ ] Bug fix (non-breaking change which fixes an issue).
16
+ - [ ] New feature (non-breaking change which adds functionality).
17
+ - [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected).
18
+
19
+ ## Checklist:
20
+
21
+ <!--- Go over all the following points, and put an `x` in all the boxes that apply. -->
22
+ - [ ] I've added tests for my code.
23
+ - [ ] My change requires a change to the documentation.
24
+ - [ ] I have updated the documentation accordingly.
data/.gitignore CHANGED
@@ -8,4 +8,4 @@
8
8
  /tmp/
9
9
  gemfiles/*.gemfile.lock
10
10
  .byebug_history
11
- Gemfile.lock
11
+ Gemfile.lock
@@ -0,0 +1,7 @@
1
+ AllCops:
2
+ Exclude:
3
+ - tmp/**/*
4
+
5
+ Metrics/BlockLength:
6
+ Exclude:
7
+ - rspec_specs/**/*
@@ -13,7 +13,6 @@ branches:
13
13
  only:
14
14
  - master
15
15
 
16
-
17
16
  before_script:
18
17
  - curl -L https://codeclimate.com/downloads/test-reporter/test-reporter-latest-linux-amd64 > ./cc-test-reporter
19
18
  - chmod +x ./cc-test-reporter
@@ -29,6 +28,7 @@ gemfile:
29
28
  - gemfiles/rails_4_2.gemfile
30
29
  - gemfiles/rails_5_0.gemfile
31
30
  - gemfiles/rails_5_1.gemfile
31
+ - gemfiles/rails_5_2.gemfile
32
32
 
33
33
  matrix:
34
34
  fast_finish: true
@@ -41,6 +41,8 @@ matrix:
41
41
  gemfile: gemfiles/rails_5_0.gemfile
42
42
  - rvm: 2.1.3
43
43
  gemfile: gemfiles/rails_5_1.gemfile
44
+ - rvm: 2.1.3
45
+ gemfile: gemfiles/rails_5_2.gemfile
44
46
  - rvm: 2.2.7
45
47
  gemfile: gemfiles/rails_3.gemfile
46
48
  - rvm: 2.3.6
data/Appraisals CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  appraise 'rails_3' do
2
4
  gem 'rails', '~> 3'
3
5
  gem 'cucumber-rails', '~> 1.4.5'
@@ -43,4 +45,11 @@ appraise 'rails_5_1' do
43
45
  gem 'cucumber-rails', '~> 1.5.0', group: :test, require: false
44
46
  gem 'rspec-rails', '~> 3.7.2', group: :test
45
47
  gem 'database_cleaner', '~> 1.0.1'
46
- end
48
+ end
49
+
50
+ appraise 'rails_5_2' do
51
+ gem 'rails', '~> 5.2.0'
52
+ gem 'cucumber-rails', '~> 1.6.0', group: :test, require: false
53
+ gem 'rspec-rails', '~> 3.7.2', group: :test
54
+ gem 'database_cleaner', '~> 1.0.1'
55
+ end
@@ -1,3 +1,9 @@
1
+ ## 1.0.1
2
+ - Added support for Rails 5.2
3
+ ## 1.0.0
4
+ - Removed the ability to read the current read-only status using `RailsReadonlyInjector.config.read_only`, and replaced it with `RailsReadonlyInjector.in_read_only_mode?`.
5
+ ## 0.3.0
6
+ - Added ability to explicitly include specific classes.
1
7
  ## 0.2.0
2
8
  - Added ability to exclude specific classes from read-only mode.
3
9
  - Improved support for Rails 5 (Automatic inclusion of descendants of `ApplicationRecord` rather than `ActiveRecord::Base`).
File without changes
data/Gemfile CHANGED
@@ -1,6 +1,8 @@
1
- source "https://rubygems.org"
1
+ # frozen_string_literal: true
2
2
 
3
- git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
3
+ source 'https://rubygems.org'
4
+
5
+ git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
4
6
 
5
7
  # Specify your gem's dependencies in rails_readonly_injector.gemspec
6
8
  gemspec
File without changes
data/README.md CHANGED
@@ -1,5 +1,6 @@
1
1
  # Rails ReadOnly Injector
2
2
  [![Build Status](https://travis-ci.org/xtrasimplicity/rails_readonly_injector.svg?branch=master)](https://travis-ci.org/xtrasimplicity/rails_readonly_injector)
3
+ [![Read the Docs](https://img.shields.io/readthedocs/pip.svg)](http://www.rubydoc.info/github/xtrasimplicity/rails_readonly_injector/master)
3
4
  [![Maintainability](https://api.codeclimate.com/v1/badges/427c153efd48ae03f688/maintainability)](https://codeclimate.com/github/xtrasimplicity/rails_readonly_injector/maintainability)
4
5
  [![Test Coverage](https://api.codeclimate.com/v1/badges/427c153efd48ae03f688/test_coverage)](https://codeclimate.com/github/xtrasimplicity/rails_readonly_injector/test_coverage)
5
6
  [![Gem Version](https://badge.fury.io/rb/rails_readonly_injector.svg)](https://badge.fury.io/rb/rails_readonly_injector)
@@ -24,14 +25,16 @@ Or install it yourself as:
24
25
 
25
26
  ## Usage
26
27
 
27
- In order to switch a complete site into read-only mode, you will first need to set the action to occur when an attempt to commit changes to the database is made, from within a controller. Usually, this won't need to change once the application has booted, so I recommend defining it within an initializer, as follows:
28
+ In order to switch a complete site into read-only mode, you will first need to set the action to occur when an attempt to commit changes to the database is made, from within a controller. This action will be executed from within the context of the referring controller.
29
+
30
+ Usually, this won't need to change once the application has booted, so I recommend defining it within an initializer, as follows:
28
31
 
29
32
  ```
30
33
  # config/initializers/rails_readonly_injector.rb
31
34
  RailsReadonlyInjector.config do |config|
32
35
  config.controller_rescue_action = lambda do |context|
33
36
  # Define actions to be performed if changes to a read-only model are attempted to be committed to the database.
34
- # This lambda expression is evaluated from within the instance of the referring controller.
37
+ # This lambda expression is evaluated from within the context of the referring controller.
35
38
 
36
39
  # You may want to set a redirect, or flash an error message, or something, here.
37
40
  # e.g.
@@ -41,21 +44,37 @@ RailsReadonlyInjector.config do |config|
41
44
  end
42
45
  ```
43
46
 
44
- When you want to switch a site into read-only mode, you can then simply set `RailsReadonlyInjector.read_only` to true and then call `RailsReadonlyInjector.reload!` to (re-)load the configuration. Alternatively, you can also set `read_only` from within the configuration block inside the initializer.
47
+ When you want to switch a site into read-only mode, you can then simply
48
+ * set `RailsReadOnlyInjector.config.read_only` to true, and then
49
+ * call `RailsReadonlyInjector.reload!` to (re-)load the configuration.
50
+
51
+ Alternatively, you can also set `read_only` from within the configuration block inside the initializer.
45
52
 
46
53
  If you want to reset the configuration to the defaults, you can simply call `RailsReadonlyInjector.reset_configuration!` from anywhere in your application.
47
54
 
55
+ If you want to check whether read-only mode is currently enabled, you can use `RailsReadonlyInjector.in_read_only_mode?`.
56
+
48
57
  ## Configuration Options
58
+ The following configuration options can be set through `RailsReadonlyInjector.config`:
59
+
49
60
  - `read_only` => Whether the site should be in read-only mode. (Default: false)
50
- - `exclude_classes` => An array of classes that should be exempt from read-only mode.
61
+ - `classes_to_exclude` => An array of classes that should be _exempt_ from read-only mode. (Default: `[]`)
62
+ - `classes_to_include` => An array of classes that should be set to read-only mode. (Defaults to `ActiveRecord::Base.descendants` on Rails 3-4, and `ApplicationRecord.descendants` on Rails 5.0+)
51
63
  - `controller_rescue_action` => A lambda expression/Proc to execute when an `ActiveRecord::ReadOnlyRecord` error is raised, from within a controller.
64
+
52
65
  ## Development
53
66
 
54
67
  After checking out the repo, run `bundle install` to install the dependencies.
55
68
 
56
- RSpec specs and Cucumber features are stored in `rspec_specs` and `cucumber_features`, respectively. When `bundle exec rake` is run against an appraisal, the contents of these folders are copied to the necessary folders under the temporary rails application that is generated (by `bundle exec rake`) into `tmp/rails_app`.
69
+ RSpec specs and Cucumber features are stored in `rspec_specs` and `cucumber_features`, respectively. When `bundle exec rake` is run against an appraisal, the contents of these folders are copied to the necessary folders under the temporary rails application that `bundle exec rake` generates into `tmp/rails_app`.
70
+
71
+ To run tests for a specific version of Rails, simply run `bundle exec appraisal {APPRAISAL} bundle exec rake`, where `{APPRAISAL}` is one of the appraisals found under `Appraisals`. e.g. `bundle exec appraisal rails_4_1 bundle exec rake`
72
+
73
+ If you don't want to re-build the temporary application each time you run tests, you can execute the following rake tasks against an appraisal:
57
74
 
58
- To run tests for a specific version of Rails, simply run `bundle exec appraisal {APPRAISAL} bundle exec rake`, where `{APPRAISAL}` is one of the appraisals found under `Appraisals`.
75
+ * `dev:run_features` => Synchronises features from `cucumber_features` into the temporary rails application, and runs cucumber against the temporary application.
76
+ * `dev:run_specs` => Synchronises specs from `rspec_specs` into the temporary rails application, and runs rspec against the temporary application.
77
+ * `dev:run_tests` => Runs both `dev:run_features` and `dev:run_specs`, and ret on failure.
59
78
 
60
79
  ## Contributing
61
80
 
data/Rakefile CHANGED
@@ -1,7 +1,9 @@
1
- require "bundler/gem_tasks"
1
+ # frozen_string_literal: true
2
+
3
+ require 'bundler/gem_tasks'
2
4
 
3
5
  development_tasks_path = File.expand_path('../development_tasks', __FILE__)
4
6
 
5
7
  Dir[File.join(development_tasks_path, '*.rake')].each { |rb| load rb }
6
8
 
7
- task :default => ['dev:deploy_test_app', 'dev:run_tests']
9
+ task default: ['dev:deploy_test_app', 'dev:run_tests']
@@ -1,7 +1,8 @@
1
1
  #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
2
3
 
3
- require "bundler/setup"
4
- require "rails_readonly_injector"
4
+ require 'bundler/setup'
5
+ require 'rails_readonly_injector'
5
6
 
6
7
  # You can add fixtures and/or initialization code here to make experimenting
7
8
  # with your gem easier. You can also use a different console, if you like.
@@ -10,5 +11,5 @@ require "rails_readonly_injector"
10
11
  # require "pry"
11
12
  # Pry.start
12
13
 
13
- require "irb"
14
+ require 'irb'
14
15
  IRB.start(__FILE__)
File without changes
@@ -1,7 +1,9 @@
1
- Given("I execute:") do |code|
1
+ # frozen_string_literal: true
2
+
3
+ Given('I execute:') do |code|
2
4
  eval code
3
5
  end
4
6
 
5
- Then("The page should contain {string}") do |string|
7
+ Then('The page should contain {string}') do |string|
6
8
  expect(page).to have_content(string)
7
- end
9
+ end
@@ -1,4 +1,6 @@
1
- Given("There is a user that has been persisted to the database") do
1
+ # frozen_string_literal: true
2
+
3
+ Given('There is a user that has been persisted to the database') do
2
4
  RailsReadonlyInjector.config.read_only = false
3
5
  RailsReadonlyInjector.reload!
4
6
 
@@ -7,43 +9,45 @@ Given("There is a user that has been persisted to the database") do
7
9
  expect(@user.persisted?).to eq(true)
8
10
  end
9
11
 
10
- Given("There is a user that has not been persisted to the database") do
12
+ Given('There is a user that has not been persisted to the database') do
11
13
  User.destroy_all
12
-
14
+
13
15
  @user = User.new(name: 'Bob')
14
16
  end
15
17
 
16
- When("I update the user") do
18
+ When('I update the user') do
17
19
  begin
18
20
  @user.update_attributes(name: 'Fred')
19
21
  rescue ActiveRecord::ReadOnlyRecord
20
22
  end
21
23
  end
22
24
 
23
- When("I save the user") do
25
+ When('I save the user') do
24
26
  begin
25
27
  @user.save
26
28
  rescue ActiveRecord::ReadOnlyRecord
27
29
  end
28
30
  end
29
31
 
30
- Then("the user should not be updated") do
32
+ Then('the user should not be updated') do
31
33
  @user.reload
32
-
34
+
33
35
  expect(@user.name).to eq('Bob')
34
36
  end
35
37
 
36
- Then("the user should be updated") do
38
+ Then('the user should be updated') do
37
39
  @user.reload
38
40
 
39
41
  expect(@user.name).to eq('Fred')
40
42
  end
41
43
 
42
- Then("the user should be saved") do
44
+ Then('the user should be saved') do
45
+ @user.reload
46
+
43
47
  expect(@user.persisted?).to eq(true)
44
48
  end
45
49
 
46
- Then("the user should not be saved") do
50
+ Then('the user should not be saved') do
47
51
  expect(User.all.length).to eq(0)
48
52
  end
49
53
 
@@ -54,15 +58,15 @@ When("I'm using a web browser and attempt to update the user") do
54
58
  end
55
59
 
56
60
  When("I'm using a web browser and attempt to create a user") do
57
- visit "/users/new"
61
+ visit '/users/new'
58
62
  fill_in 'user[name]', with: 'Fred'
59
63
  click_on 'Create User'
60
64
  end
61
65
 
62
- Then("the user should be created") do
66
+ Then('the user should be created') do
63
67
  expect(User.all.length).to eq(1)
64
68
  end
65
69
 
66
- Then("I should be able to create a user without any errors") do
70
+ Then('I should be able to create a user without any errors') do
67
71
  expect { User.create(name: 'Bob') }.not_to raise_error
68
- end
72
+ end
File without changes
File without changes
File without changes
@@ -0,0 +1,57 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'fileutils'
4
+
5
+ # :nodoc:
6
+ module FileHelpers
7
+ GEM_ROOT_PATH = File.expand_path('../../..', __FILE__).freeze
8
+ RAILS_APP_PATH = File.expand_path(File.join(GEM_ROOT_PATH, 'tmp', 'rails_app')).freeze
9
+
10
+ def append_to_file(path_to_file, content)
11
+ raise 'The specified path is not a file!' unless File.file? path_to_file
12
+
13
+ File.open(path_to_file, 'a') do |f|
14
+ f.write content
15
+ end
16
+ end
17
+
18
+ def append_to_beginning_of_file(path_to_file, content)
19
+ raise 'The specified path is not a file!' unless File.file? path_to_file
20
+
21
+ existing_content_as_array = File.open(path_to_file, 'r').readlines
22
+
23
+ new_content_arr = [content] + existing_content_as_array
24
+
25
+ write_file_with_content path_to_file, new_content_arr.join("\n")
26
+ end
27
+
28
+ def write_file_with_content(path_to_file, content)
29
+ File.open(path_to_file, 'w') do |f|
30
+ f.write content
31
+ end
32
+ end
33
+
34
+ def switch_to_gems_root_path
35
+ FileUtils.cd GEM_ROOT_PATH
36
+ end
37
+
38
+ def switch_to_rails_app_path
39
+ FileUtils.cd RAILS_APP_PATH
40
+ end
41
+
42
+ def generate_rails_application
43
+ # Remove the app, if it exists already
44
+ system("rm -rf #{RAILS_APP_PATH}")
45
+
46
+ FileUtils.mkdir_p RAILS_APP_PATH
47
+ system("bundle exec rails new #{RAILS_APP_PATH}")
48
+ end
49
+
50
+ def gems_root_path
51
+ GEM_ROOT_PATH
52
+ end
53
+
54
+ def rails_app_path
55
+ RAILS_APP_PATH
56
+ end
57
+ end
@@ -0,0 +1,63 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GemHelpers
4
+ def add_gem(name, attributes = {})
5
+ line = if attributes.empty?
6
+ "gem '#{name}'"
7
+ else
8
+ "gem '#{name}', #{attributes}"
9
+ end
10
+
11
+ append_to_file('Gemfile', "#{line}\n")
12
+ end
13
+
14
+ # 'Override'/force a specific gem version, as defined in the Appraisal.
15
+ def ensure_gem_versions_defined_in_appraisal_are_used
16
+ gems_defined_in_appraisal = retrieve_gems_from_gemfile(ENV['BUNDLE_GEMFILE'])
17
+ gems_defined_in_gemfile = retrieve_gems_from_gemfile('Gemfile').collect(&:gem_name)
18
+
19
+ gems_defined_in_appraisal.reject { |l| gems_defined_in_gemfile.include? l.gem_name }.each do |gem|
20
+ add_gem gem.gem_name, gem.attributes.join(',')
21
+ end
22
+ end
23
+
24
+ def install_simplecov(coverage_dir)
25
+ append_to_beginning_of_file 'spec/spec_helper.rb', %(
26
+ require 'simplecov'
27
+ require 'rails_readonly_injector'
28
+ )
29
+ append_to_beginning_of_file 'features/support/env.rb', "require 'simplecov'"
30
+
31
+ write_file_with_content '.simplecov', %(
32
+ SimpleCov.start do
33
+ coverage_dir '#{coverage_dir}'
34
+ end
35
+ )
36
+ end
37
+
38
+ def unset_appraisal_environment_variables
39
+ ENV.delete('BUNDLE_GEMFILE')
40
+ ENV.delete('BUNDLE_BIN_PATH')
41
+ ENV.delete('RUBYOPT')
42
+ end
43
+
44
+ private
45
+
46
+ def retrieve_gems_from_gemfile(file_path)
47
+ gems = []
48
+
49
+ File.open(file_path).readlines.each do |line|
50
+ matches = line.match(/^\s*gem\s+['|"]/)
51
+
52
+ next if matches.nil?
53
+
54
+ parts = line.split(',')
55
+
56
+ gem_name = parts.first.gsub(/\s*gem\s*|["|']|\n/, '')
57
+
58
+ gems << OpenStruct.new(gem_name: gem_name, attributes: parts.drop(1))
59
+ end
60
+
61
+ gems
62
+ end
63
+ end