rspec-authorization 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: d32c0f50faa40a57496f87a21d5ec3cdbf538f01
4
+ data.tar.gz: 4ad22903e43240efdf66a025c70d9812bb97c8a2
5
+ SHA512:
6
+ metadata.gz: 68c08236ab63ec53595788a07de8256941934bf1993727d2edf002ab71efd6d6681060feb64ec4e96748a22a7d5457d4cf960d132a5d1d99744e53e7c8471da5
7
+ data.tar.gz: 342c1b6aa908f713b56eba516821f47af14d78e0659c8ff8f8574e11143570d1940d2f31d2a30ace4e05c4f65f02d8d4ee5555fb947cd47b30dd0393ed715840
data/.editorconfig ADDED
@@ -0,0 +1,9 @@
1
+ root = true
2
+
3
+ [*]
4
+ end_of_line = lf
5
+ indent_style = space
6
+ indent_size = 2
7
+ insert_final_newline = true
8
+ trim_trailing_whitespace = true
9
+
data/.gitignore ADDED
@@ -0,0 +1,17 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
10
+ *.bundle
11
+ *.so
12
+ *.o
13
+ *.a
14
+ mkmf.log
15
+
16
+ /config
17
+ /spec/.rails
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --color
2
+ --format documentation
3
+ --require spec_helper
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ 2.1.4
data/Gemfile ADDED
@@ -0,0 +1,14 @@
1
+ source 'https://rubygems.org'
2
+ ruby '2.1.4'
3
+
4
+ gemspec
5
+
6
+ group :development, :test do
7
+ gem 'declarative_authorization', github: 'stffn/declarative_authorization'
8
+ gem 'guard-rspec'
9
+ gem 'pry'
10
+ gem 'terminal-notifier-guard' if `uname` =~ /Darwin/
11
+
12
+ gem 'jquery-rails'
13
+ gem 'turbolinks'
14
+ end
data/Guardfile ADDED
@@ -0,0 +1,9 @@
1
+ guard :rspec, cmd: 'bundle exec rspec' do
2
+ watch(%r{^spec/.+_spec\.rb$})
3
+
4
+ watch(%r{^lib/(.+)\.rb$}) { |m| "spec/lib/#{m[1]}_spec.rb" }
5
+ watch(%r{^tools/(.+)\.rb$}) { |m| "spec/tools/#{m[1]}_spec.rb" }
6
+
7
+ watch(%r{^controllers/(.+)\.rb$}) { |m| "spec/controllers/#{m[1]}_spec.rb" }
8
+ end
9
+
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2014 Hendra Uzia
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,29 @@
1
+ # Rspec::Authorization
2
+
3
+ RSpec matcher for declarative_authorization. A neat way of asserting declarative_authorization's rules inside controller using RSpec matcher.
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ ```ruby
10
+ gem 'rspec-authorization'
11
+ ```
12
+
13
+ And then execute:
14
+
15
+ $ bundle
16
+
17
+ Or install it yourself as:
18
+
19
+ $ gem install rspec-authorization
20
+
21
+ ## Contributing
22
+
23
+ 1. Fork it ( https://github.com/hendrauzia/rspec-authorization/fork )
24
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
25
+ 3. Setup rails test app (`bundle exec rake setup`)
26
+ 3. Test your changes (`bundle exec rake spec`)
27
+ 5. Commit your changes (`git commit -am 'Add some feature'`)
28
+ 6. Push to the branch (`git push origin my-new-feature`)
29
+ 7. Create a new Pull Request
data/Rakefile ADDED
@@ -0,0 +1,13 @@
1
+ $LOAD_PATH << File.expand_path('../tools', __FILE__)
2
+
3
+ require 'rspec/core/rake_task'
4
+ require "bundler/gem_tasks"
5
+
6
+ # Default directory to look is `/spec`
7
+ # Run with `rake spec`
8
+ RSpec::Core::RakeTask.new(:spec)
9
+ task default: :spec
10
+
11
+ Dir["tasks/*.rake"].each do |task|
12
+ import task
13
+ end
@@ -0,0 +1,9 @@
1
+ require "rspec/rails"
2
+ require "rspec/authorization/adapters"
3
+ require "rspec/authorization/matchers"
4
+ require "rspec/authorization/version"
5
+
6
+ module RSpec
7
+ module Authorization
8
+ end
9
+ end
@@ -0,0 +1,10 @@
1
+ require "rspec/authorization/adapters/example"
2
+ require "rspec/authorization/adapters/group"
3
+ require "rspec/authorization/adapters/request"
4
+ require "rspec/authorization/adapters/route"
5
+
6
+ module RSpec::Authorization
7
+ module Adapters
8
+ end
9
+ end
10
+
@@ -0,0 +1,28 @@
1
+ module RSpec::Authorization
2
+ module Adapters
3
+ class Example
4
+ attr_reader :group, :example
5
+
6
+ def initialize(group)
7
+ @group = group
8
+ @example = RSpec::Core::Example.new(group, "", {})
9
+
10
+ set_example_group_instance
11
+ end
12
+
13
+ def run
14
+ run_before_example
15
+ end
16
+
17
+ private
18
+
19
+ def set_example_group_instance
20
+ @example.instance_variable_set :@example_group_instance, group.new
21
+ end
22
+
23
+ def run_before_example
24
+ @example.send :run_before_example
25
+ end
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,14 @@
1
+ module RSpec::Authorization
2
+ module Adapters
3
+ class Group
4
+ class << self
5
+ def new(klass)
6
+ RSpec::Core::ExampleGroup.describe klass do
7
+ include RSpec::Rails::ControllerExampleGroup
8
+ end
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
14
+
@@ -0,0 +1,57 @@
1
+ module RSpec::Authorization
2
+ module Adapters
3
+ class Request
4
+ attr_reader :klass, :action, :role, :group, :route, :response
5
+
6
+ def initialize(klass, action, role)
7
+ @klass, @action, @role = klass, action, role
8
+ @group, @route = Group.new(klass), Route.new(action)
9
+
10
+ stub_current_user
11
+
12
+ setup_response_retrieval
13
+ dispatch
14
+ end
15
+
16
+ private
17
+
18
+ def response_setter
19
+ lambda { |r| @response = r }
20
+ end
21
+
22
+ def role_symbols
23
+ [role]
24
+ end
25
+
26
+ def stub_current_user
27
+ roles = role_symbols
28
+
29
+ group.before do
30
+ user = double(:user, role_symbols: roles)
31
+ allow(controller).to receive(:current_user).and_return(user)
32
+ end
33
+ end
34
+
35
+ def setup_response_retrieval
36
+ args = route
37
+ setter = response_setter
38
+
39
+ group.before do
40
+ begin
41
+ send *args
42
+ rescue ActiveRecord::RecordNotFound
43
+ response.status = 404
44
+ end
45
+
46
+ setter.call(response)
47
+ end
48
+ end
49
+
50
+ def dispatch
51
+ example = Example.new(group)
52
+ example.run
53
+ end
54
+ end
55
+ end
56
+ end
57
+
@@ -0,0 +1,40 @@
1
+ module RSpec::Authorization
2
+ module Adapters
3
+ class Route
4
+ attr_reader :action
5
+
6
+ DICTIONARIES = {
7
+ index: :get,
8
+ show: :get,
9
+ new: :get,
10
+ create: :post,
11
+ edit: :get,
12
+ update: :patch,
13
+ destroy: :delete
14
+ }
15
+
16
+ PARAMS = {
17
+ show: { id: 1 },
18
+ edit: { id: 1 },
19
+ update: { id: 1 },
20
+ destroy: { id: 1 }
21
+ }
22
+
23
+ def initialize(action)
24
+ @action = action
25
+ end
26
+
27
+ def params
28
+ PARAMS[action]
29
+ end
30
+
31
+ def verb
32
+ DICTIONARIES.fetch(action)
33
+ end
34
+
35
+ def to_a
36
+ [verb, action, params]
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,10 @@
1
+ require 'rspec/authorization/matchers/have_permission_for'
2
+
3
+ module RSpec::Authorization
4
+ module Matchers
5
+ end
6
+ end
7
+
8
+ RSpec.configure do |config|
9
+ config.include RSpec::Authorization::Matchers::HavePermissionFor, type: :controller
10
+ end
@@ -0,0 +1,46 @@
1
+ module RSpec::Authorization
2
+ module Matchers
3
+ module HavePermissionFor
4
+ def have_permission_for(role)
5
+ HavePermissionFor.new(role)
6
+ end
7
+
8
+ # @private
9
+ class HavePermissionFor
10
+ include Adapters
11
+
12
+ attr_reader :controller, :role, :action
13
+
14
+ def initialize(role)
15
+ @role = role
16
+ @action = :index
17
+ end
18
+
19
+ def to(action)
20
+ @action = action
21
+ self
22
+ end
23
+
24
+ def matches?(controller)
25
+ @controller = controller
26
+
27
+ request = Request.new(controller.class, action, role)
28
+ request.response.status != 403
29
+ end
30
+
31
+ def failure_message
32
+ "Expected #{controller.class} to have permission for #{role} to #{action}"
33
+ end
34
+
35
+ def failure_message_when_negated
36
+ "Did not expect #{controller.class} to have permission for #{role} to #{action}"
37
+ end
38
+
39
+ def description
40
+ "have permission for #{role} on #{action}"
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
46
+
@@ -0,0 +1,5 @@
1
+ module Rspec
2
+ module Authorization
3
+ VERSION = "0.0.1"
4
+ end
5
+ end
@@ -0,0 +1,28 @@
1
+ lib = File.expand_path('../lib', __FILE__)
2
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
3
+ require 'rspec/authorization/version'
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = "rspec-authorization"
7
+ spec.version = Rspec::Authorization::VERSION
8
+ spec.authors = ["Hendra Uzia"]
9
+ spec.email = ["hendra.uzia@gmail.com"]
10
+ spec.summary = %q{RSpec matcher for declarative_authorization.}
11
+ spec.description = %q{A neat way of asserting declarative_authorization's rules inside controller using RSpec matcher.}
12
+ spec.homepage = "https://github.com/hendrauzia/rspec-authorization"
13
+ spec.license = "MIT"
14
+
15
+ spec.files = `git ls-files -z`.split("\x0")
16
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
17
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
18
+ spec.require_paths = ["lib"]
19
+
20
+ spec.add_runtime_dependency "declarative_authorization"
21
+ spec.add_runtime_dependency "rspec-rails"
22
+
23
+ spec.add_development_dependency "bundler", "~> 1.7"
24
+ spec.add_development_dependency "rails", "~> 4.0"
25
+ spec.add_development_dependency "rake", "~> 10.0"
26
+ spec.add_development_dependency "rspec-its"
27
+ spec.add_development_dependency "sqlite3"
28
+ end
data/spec/.keep ADDED
File without changes
@@ -0,0 +1,11 @@
1
+ require 'rails_helper'
2
+
3
+ describe PostsController do
4
+ it { is_expected.to have_permission_for(:user).to(:index) }
5
+ it { is_expected.to have_permission_for(:user).to(:new) }
6
+ it { is_expected.to have_permission_for(:user).to(:create) }
7
+ it { is_expected.to have_permission_for(:user).to(:show) }
8
+ it { is_expected.to have_permission_for(:user).to(:edit) }
9
+ it { is_expected.to have_permission_for(:user).to(:update) }
10
+ it { is_expected.to have_permission_for(:user).to(:destroy) }
11
+ end
@@ -0,0 +1,26 @@
1
+ require 'rails_helper'
2
+
3
+ include RSpec::Authorization::Adapters
4
+
5
+ describe Example do
6
+ let(:klass) { GroupTestClass }
7
+ let(:group) { Group.new(klass) }
8
+ let(:example) { Example.new(group) }
9
+
10
+ subject { example }
11
+
12
+ its(:group) { is_expected.to eq group }
13
+ its(:example) { is_expected.to be_a_kind_of RSpec::Core::Example }
14
+
15
+ context "private" do
16
+ describe "#set_example_group_instance" do
17
+ before { example.send :set_example_group_instance }
18
+ specify { expect(example.example.instance_variable_get :@example_group_instance).to be_a_kind_of group }
19
+ end
20
+
21
+ describe "#run_before_example" do
22
+ before { expect(example.example).to receive(:run_before_example).and_return(true) }
23
+ specify { expect(example.example.send :run_before_example).to be_present }
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,13 @@
1
+ require 'rails_helper'
2
+
3
+ include RSpec::Authorization::Adapters
4
+
5
+ describe Group do
6
+ let(:klass) { GroupTestClass }
7
+ let(:group) { Group.new(klass) }
8
+
9
+ describe ".new" do
10
+ subject { group }
11
+ its(:described_class) { is_expected.to eq GroupTestClass }
12
+ end
13
+ end
@@ -0,0 +1,30 @@
1
+ require 'rails_helper'
2
+
3
+ include RSpec::Authorization::Adapters
4
+
5
+ describe Request do
6
+ let(:klass) { PostsController }
7
+ let(:action) { :index }
8
+ let(:role) { :user }
9
+ let(:request) { Request.new(klass, action, role) }
10
+
11
+ subject { request }
12
+
13
+ its(:klass) { is_expected.to eq klass }
14
+ its(:action) { is_expected.to eq action }
15
+ its(:role) { is_expected.to eq role }
16
+
17
+ context "private" do
18
+ describe "#response_setter" do
19
+ let(:response_setter) { request.send :response_setter }
20
+
21
+ before { response_setter.call(:response) }
22
+
23
+ its(:response) { is_expected.to eq :response }
24
+ end
25
+
26
+ describe "#role_symbols" do
27
+ specify { expect(request.send(:role_symbols)).to include role }
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,94 @@
1
+ require 'rails_helper'
2
+
3
+ include RSpec::Authorization::Adapters
4
+
5
+ describe Route do
6
+ let(:route) { Route.new(:action) }
7
+
8
+ subject { route }
9
+ its(:action) { is_expected.to eq :action }
10
+
11
+ describe "#params" do
12
+ def param_of(action)
13
+ Route.new(action).params
14
+ end
15
+
16
+ context "without params" do
17
+ context "index" do
18
+ specify { expect(param_of(:index)).not_to be_present }
19
+ end
20
+
21
+ context "new" do
22
+ specify { expect(param_of(:new)).not_to be_present }
23
+ end
24
+
25
+ context "create" do
26
+ specify { expect(param_of(:create)).not_to be_present }
27
+ end
28
+ end
29
+
30
+ context "with params" do
31
+ context "show" do
32
+ specify { expect(param_of(:show)).to be_present }
33
+ end
34
+
35
+ context "edit" do
36
+ specify { expect(param_of(:edit)).to be_present }
37
+ end
38
+
39
+ context "update" do
40
+ specify { expect(param_of(:update)).to be_present }
41
+ end
42
+
43
+ context "destroy" do
44
+ specify { expect(param_of(:destroy)).to be_present }
45
+ end
46
+ end
47
+ end
48
+
49
+ describe "#verb" do
50
+ def verb_of(action)
51
+ Route.new(action).verb
52
+ end
53
+
54
+ context "RESTful routes" do
55
+ context "index" do
56
+ specify { expect(verb_of(:index)).to eq :get }
57
+ end
58
+
59
+ context "show" do
60
+ specify { expect(verb_of(:show)).to eq :get }
61
+ end
62
+
63
+ context "new" do
64
+ specify { expect(verb_of(:new)).to eq :get }
65
+ end
66
+
67
+ context "create" do
68
+ specify { expect(verb_of(:create)).to eq :post }
69
+ end
70
+
71
+ context "edit" do
72
+ specify { expect(verb_of(:edit)).to eq :get }
73
+ end
74
+
75
+ context "update" do
76
+ specify { expect(verb_of(:update)).to eq :patch }
77
+ end
78
+
79
+ context "detroy" do
80
+ specify { expect(verb_of(:destroy)).to eq :delete }
81
+ end
82
+ end
83
+ end
84
+
85
+ describe "#to_a" do
86
+ before do
87
+ allow(route).to receive(:verb).and_return(:verb)
88
+ allow(route).to receive(:action).and_return(:action)
89
+ allow(route).to receive(:params).and_return(:params)
90
+ end
91
+
92
+ specify { expect(route.to_a).to eq [:verb, :action, :params] }
93
+ end
94
+ end
@@ -0,0 +1,55 @@
1
+ require 'rails/version'
2
+
3
+ ENV['RAILS_ENV'] ||= 'test'
4
+ ENV['RAILS_ROOT'] ||= File.expand_path("../.rails/rails-#{::Rails::VERSION::STRING}", __FILE__)
5
+
6
+ require 'spec_helper'
7
+ require "#{ENV['RAILS_ROOT']}/config/environment"
8
+ require 'rspec/rails'
9
+ require 'rspec/authorization'
10
+
11
+ # Add additional requires below this line. Rails is not loaded until this point!
12
+
13
+ # Requires supporting ruby files with custom matchers and macros, etc, in
14
+ # spec/support/ and its subdirectories. Files matching `spec/**/*_spec.rb` are
15
+ # run as spec files by default. This means that files in spec/support that end
16
+ # in _spec.rb will both be required and run as specs, causing the specs to be
17
+ # run twice. It is recommended that you do not name files matching this glob to
18
+ # end with _spec.rb. You can configure this pattern with the --pattern
19
+ # option on the command line or in ~/.rspec, .rspec or `.rspec-local`.
20
+ #
21
+ # The following line is provided for convenience purposes. It has the downside
22
+ # of increasing the boot-up time by auto-requiring all files in the support
23
+ # directory. Alternatively, in the individual `*_spec.rb` files, manually
24
+ # require only the support files necessary.
25
+ #
26
+ # Dir[Rails.root.join("spec/support/**/*.rb")].each { |f| require f }
27
+
28
+ # Checks for pending migrations before tests are run.
29
+ # If you are not using ActiveRecord, you can remove this line.
30
+ ActiveRecord::Migration.maintain_test_schema!
31
+
32
+ RSpec.configure do |config|
33
+ # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
34
+ config.fixture_path = "#{::Rails.root}/spec/fixtures"
35
+ #
36
+ # If you're not using ActiveRecord, or you'd prefer not to run each of your
37
+ # examples within a transaction, remove the following line or assign false
38
+ # instead of true.
39
+ config.use_transactional_fixtures = true
40
+
41
+ # # RSpec Rails can automatically mix in different behaviours to your tests
42
+ # based on their file location, for example enabling you to call `get` and
43
+ # `post` in specs under `spec/controllers`.
44
+ #
45
+ # You can disable this behaviour by removing the line below, and instead
46
+ # explicitly tag your specs with their type, e.g.:
47
+ #
48
+ # RSpec.describe UsersController, :type => :controller do
49
+ # # ...
50
+ # end
51
+ #
52
+ # The different available types are documented in the features, such as in
53
+ # https://relishapp.com/rspec/rspec-rails/docs
54
+ config.infer_spec_type_from_file_location!
55
+ end
@@ -0,0 +1,92 @@
1
+ require 'rspec/its'
2
+
3
+ $LOAD_PATH << File.expand_path('../../tools', __FILE__)
4
+ $LOAD_PATH << File.expand_path('../support', __FILE__)
5
+
6
+ require 'group_test_class'
7
+
8
+ # This file was generated by the `rails generate rspec:install` command. Conventionally, all
9
+ # specs live under a `spec` directory, which RSpec adds to the `$LOAD_PATH`.
10
+ # The generated `.rspec` file contains `--require spec_helper` which will cause this
11
+ # file to always be loaded, without a need to explicitly require it in any files.
12
+ #
13
+ # Given that it is always loaded, you are encouraged to keep this file as
14
+ # light-weight as possible. Requiring heavyweight dependencies from this file
15
+ # will add to the boot time of your test suite on EVERY test run, even for an
16
+ # individual file that may not need all of that loaded. Instead, consider making
17
+ # a separate helper file that requires the additional dependencies and performs
18
+ # the additional setup, and require it from the spec files that actually need it.
19
+ #
20
+ # The `.rspec` file also contains a few flags that are not defaults but that
21
+ # users commonly want.
22
+ #
23
+ # See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
24
+ RSpec.configure do |config|
25
+ # rspec-expectations config goes here. You can use an alternate
26
+ # assertion/expectation library such as wrong or the stdlib/minitest
27
+ # assertions if you prefer.
28
+ config.expect_with :rspec do |expectations|
29
+ # This option will default to `true` in RSpec 4. It makes the `description`
30
+ # and `failure_message` of custom matchers include text for helper methods
31
+ # defined using `chain`, e.g.:
32
+ # be_bigger_than(2).and_smaller_than(4).description
33
+ # # => "be bigger than 2 and smaller than 4"
34
+ # ...rather than:
35
+ # # => "be bigger than 2"
36
+ expectations.include_chain_clauses_in_custom_matcher_descriptions = true
37
+ end
38
+
39
+ # rspec-mocks config goes here. You can use an alternate test double
40
+ # library (such as bogus or mocha) by changing the `mock_with` option here.
41
+ config.mock_with :rspec do |mocks|
42
+ # Prevents you from mocking or stubbing a method that does not exist on
43
+ # a real object. This is generally recommended, and will default to
44
+ # `true` in RSpec 4.
45
+ mocks.verify_partial_doubles = true
46
+ end
47
+
48
+ # The settings below are suggested to provide a good initial experience
49
+ # with RSpec, but feel free to customize to your heart's content.
50
+ =begin
51
+ # These two settings work together to allow you to limit a spec run
52
+ # to individual examples or groups you care about by tagging them with
53
+ # `:focus` metadata. When nothing is tagged with `:focus`, all examples
54
+ # get run.
55
+ config.filter_run :focus
56
+ config.run_all_when_everything_filtered = true
57
+
58
+ # Limits the available syntax to the non-monkey patched syntax that is recommended.
59
+ # For more details, see:
60
+ # - http://myronmars.to/n/dev-blog/2012/06/rspecs-new-expectation-syntax
61
+ # - http://teaisaweso.me/blog/2013/05/27/rspecs-new-message-expectation-syntax/
62
+ # - http://myronmars.to/n/dev-blog/2014/05/notable-changes-in-rspec-3#new__config_option_to_disable_rspeccore_monkey_patching
63
+ config.disable_monkey_patching!
64
+
65
+ # Many RSpec users commonly either run the entire suite or an individual
66
+ # file, and it's useful to allow more verbose output when running an
67
+ # individual spec file.
68
+ if config.files_to_run.one?
69
+ # Use the documentation formatter for detailed output,
70
+ # unless a formatter has already been configured
71
+ # (e.g. via a command-line flag).
72
+ config.default_formatter = 'doc'
73
+ end
74
+
75
+ # Print the 10 slowest examples and example groups at the
76
+ # end of the spec run, to help surface which specs are running
77
+ # particularly slow.
78
+ config.profile_examples = 10
79
+
80
+ # Run specs in random order to surface order dependencies. If you find an
81
+ # order dependency and want to debug it, you can fix the order by providing
82
+ # the seed, which is printed after each run.
83
+ # --seed 1234
84
+ config.order = :random
85
+
86
+ # Seed global randomization in this process using the `--seed` CLI option.
87
+ # Setting this allows you to use `--seed` to deterministically reproduce
88
+ # test failures related to randomization by passing the same `--seed` value
89
+ # as the one that triggered the failure.
90
+ Kernel.srand config.seed
91
+ =end
92
+ end
@@ -0,0 +1,2 @@
1
+ class GroupTestClass
2
+ end
@@ -0,0 +1,98 @@
1
+ require 'spec_helper'
2
+ require 'rails_test_app'
3
+
4
+ describe RailsTestApp do
5
+ let(:test_app) { RailsTestApp.new(:version) }
6
+ let(:dummy_file) { 'tmp/dummy-rails-test-app' }
7
+
8
+ describe ".new" do
9
+ subject(:test_app) { RailsTestApp.new("4.1.6", "--skip-javascript") }
10
+
11
+ its(:path) { is_expected.to include("4.1.6") }
12
+ its(:options) { is_expected.to include("--skip-javascript") }
13
+ its(:create_command) { is_expected.to include("4.1.6") }
14
+ its(:destroy_command) { is_expected.to include("4.1.6") }
15
+ end
16
+
17
+ describe "#create" do
18
+ before { allow(test_app).to receive(:create_command).and_return("touch #{dummy_file}") }
19
+ before { allow(test_app).to receive(:template_param) }
20
+ before { allow(test_app).to receive(:option) }
21
+ after { `rm -rf #{dummy_file}` }
22
+
23
+ context "path does not exists" do
24
+ before { allow(test_app).to receive(:exists?).and_return(false) }
25
+
26
+ it { expect(test_app.create).to be_truthy }
27
+ end
28
+
29
+ context "path exists" do
30
+ before { allow(test_app).to receive(:exists?).and_return(true) }
31
+
32
+ it { expect(test_app.create).to be_falsy }
33
+ end
34
+ end
35
+
36
+ describe "#destroy" do:w
37
+ before { `touch #{dummy_file}` }
38
+ before { allow(test_app).to receive(:destroy_command).and_return("rm -rf #{dummy_file}") }
39
+
40
+ context "path does not exists" do
41
+ before { allow(test_app).to receive(:exists?).and_return(false) }
42
+
43
+ it { expect(test_app.destroy).to be_falsy }
44
+ end
45
+
46
+ context "path exists" do
47
+ before { allow(test_app).to receive(:exists?).and_return(true) }
48
+
49
+ it { expect(test_app.destroy).to be_truthy }
50
+ end
51
+ end
52
+
53
+ describe "#exists?" do
54
+ let(:spec_path) { "spec/" }
55
+ let(:void_path) { "does-not-exist" }
56
+
57
+ context "path does not exists" do
58
+ before { allow(test_app).to receive(:path).and_return(void_path) }
59
+
60
+ it { expect(test_app.exists?).to be_falsy }
61
+ end
62
+
63
+ context "path exists" do
64
+ before { allow(test_app).to receive(:path).and_return(spec_path) }
65
+
66
+ it { expect(test_app.exists?).to be_truthy }
67
+ end
68
+ end
69
+
70
+ describe "#option" do
71
+ let(:options) { %i(a b) }
72
+ before { allow(test_app).to receive(:options).and_return(options) }
73
+
74
+ it { expect(test_app.option).to eq "a b" }
75
+ end
76
+
77
+ describe "#template" do
78
+ context "template is not assigned" do
79
+ let(:default_template) { 'default-template' }
80
+ before { stub_const("RailsTestApp::DEFAULT_TEMPLATE", default_template) }
81
+
82
+ it { expect(test_app.template).to eq default_template }
83
+ end
84
+
85
+ context "template is assigned" do
86
+ let(:a_template) { 'a-template' }
87
+ before { test_app.template = a_template }
88
+
89
+ it { expect(test_app.template).to eq a_template }
90
+ end
91
+ end
92
+
93
+ describe "#template_param" do
94
+ before { allow(test_app).to receive(:template).and_return('a-template') }
95
+
96
+ it { expect(test_app.template_param).to eq '--template=a-template' }
97
+ end
98
+ end
data/tasks/clean.rake ADDED
@@ -0,0 +1,8 @@
1
+ require 'rails/version'
2
+ require 'rails_test_app'
3
+
4
+ desc "Cleanup test rails apps"
5
+ task :clean do
6
+ rails = RailsTestApp.new(Rails::VERSION::STRING)
7
+ puts "#{rails.path} has been deleted" if rails.destroy
8
+ end
data/tasks/reset.rake ADDED
@@ -0,0 +1,6 @@
1
+ desc "Reset test rails app to clean state"
2
+ task :reset do
3
+ %i(clean setup).each do |task|
4
+ Rake::Task[task].invoke
5
+ end
6
+ end
data/tasks/setup.rake ADDED
@@ -0,0 +1,11 @@
1
+ require 'rails/version'
2
+ require 'rails_test_app'
3
+
4
+ desc "Create a test rails app for the specs to run against"
5
+ task :setup do
6
+ system('rm -rf config')
7
+
8
+ rails = RailsTestApp.new(Rails::VERSION::STRING)
9
+ puts "#{rails.path} exists!" unless rails.create
10
+ end
11
+
@@ -0,0 +1,38 @@
1
+ class RailsTestApp
2
+ attr_reader :path, :create_command, :destroy_command, :options
3
+ attr_writer :template
4
+
5
+ DEFAULT_TEMPLATE = "tools/rails_test_app/template.rb"
6
+
7
+ def initialize(version, *options)
8
+ @path = "spec/.rails/rails-#{version}"
9
+ @options = ( %w(--skip-bundle --skip-test-unit --skip-gemfile) + options ).uniq
10
+
11
+ @create_command = "bundle exec rails new #{path}"
12
+ @destroy_command = "rm -rf #{path}"
13
+ end
14
+
15
+ def create
16
+ system("#{create_command} #{template_param} #{option}") unless exists?
17
+ end
18
+
19
+ def exists?
20
+ Dir.exists?(path)
21
+ end
22
+
23
+ def destroy
24
+ system(destroy_command) if exists?
25
+ end
26
+
27
+ def template
28
+ @template || DEFAULT_TEMPLATE
29
+ end
30
+
31
+ def template_param
32
+ "--template=#{template}"
33
+ end
34
+
35
+ def option
36
+ options.join(" ")
37
+ end
38
+ end
@@ -0,0 +1,40 @@
1
+ generate "authorization:install --create-user"
2
+
3
+ rules = "config/authorization_rules.rb"
4
+
5
+ run "mkdir ../../../config"
6
+ run "ln -s ../spec/.rails/rails-#{Rails::VERSION::STRING}/#{rules} ../../../#{rules}"
7
+
8
+ generate "scaffold post --skip-assets --skip-helper"
9
+ generate "migration AddUserIdToPosts user:references"
10
+
11
+ rake "db:migrate"
12
+ run "bundle exec rake db:migrate RAILS_ENV=test"
13
+
14
+ first_line = /\A.*/
15
+ last_line = /^.*\Z/
16
+
17
+ inject_into_file "app/models/post.rb", %q{
18
+ belongs_to :user
19
+ }, after: first_line
20
+
21
+ inject_into_file "app/models/user.rb", %q{
22
+ has_many :posts
23
+ }, after: first_line
24
+
25
+ inject_into_file "config/authorization_rules.rb", %q{
26
+ role :user do
27
+ has_permission_on :posts, to: :manage
28
+ end
29
+ }, after: first_line
30
+
31
+ inject_into_file "app/controllers/application_controller.rb", %q{
32
+ def current_user
33
+ User.where(id: session[:user_id]).presence
34
+ end
35
+ }, before: last_line
36
+
37
+ inject_into_file "app/controllers/posts_controller.rb", %q{
38
+ filter_resource_access
39
+ }, after: first_line
40
+
metadata ADDED
@@ -0,0 +1,187 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: rspec-authorization
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Hendra Uzia
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-11-05 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: declarative_authorization
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rspec-rails
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: bundler
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '1.7'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '1.7'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rails
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '4.0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '4.0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rake
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: '10.0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: '10.0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: rspec-its
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ - !ruby/object:Gem::Dependency
98
+ name: sqlite3
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ description: A neat way of asserting declarative_authorization's rules inside controller
112
+ using RSpec matcher.
113
+ email:
114
+ - hendra.uzia@gmail.com
115
+ executables: []
116
+ extensions: []
117
+ extra_rdoc_files: []
118
+ files:
119
+ - ".editorconfig"
120
+ - ".gitignore"
121
+ - ".rspec"
122
+ - ".ruby-version"
123
+ - Gemfile
124
+ - Guardfile
125
+ - LICENSE.txt
126
+ - README.md
127
+ - Rakefile
128
+ - lib/rspec/authorization.rb
129
+ - lib/rspec/authorization/adapters.rb
130
+ - lib/rspec/authorization/adapters/example.rb
131
+ - lib/rspec/authorization/adapters/group.rb
132
+ - lib/rspec/authorization/adapters/request.rb
133
+ - lib/rspec/authorization/adapters/route.rb
134
+ - lib/rspec/authorization/matchers.rb
135
+ - lib/rspec/authorization/matchers/have_permission_for.rb
136
+ - lib/rspec/authorization/version.rb
137
+ - rspec-authorization.gemspec
138
+ - spec/.keep
139
+ - spec/controllers/posts_controller_spec.rb
140
+ - spec/lib/rspec/authorization/adapters/example_spec.rb
141
+ - spec/lib/rspec/authorization/adapters/group_spec.rb
142
+ - spec/lib/rspec/authorization/adapters/request_spec.rb
143
+ - spec/lib/rspec/authorization/adapters/route_spec.rb
144
+ - spec/rails_helper.rb
145
+ - spec/spec_helper.rb
146
+ - spec/support/group_test_class.rb
147
+ - spec/tools/rails_test_app_spec.rb
148
+ - tasks/clean.rake
149
+ - tasks/reset.rake
150
+ - tasks/setup.rake
151
+ - tools/rails_test_app.rb
152
+ - tools/rails_test_app/template.rb
153
+ homepage: https://github.com/hendrauzia/rspec-authorization
154
+ licenses:
155
+ - MIT
156
+ metadata: {}
157
+ post_install_message:
158
+ rdoc_options: []
159
+ require_paths:
160
+ - lib
161
+ required_ruby_version: !ruby/object:Gem::Requirement
162
+ requirements:
163
+ - - ">="
164
+ - !ruby/object:Gem::Version
165
+ version: '0'
166
+ required_rubygems_version: !ruby/object:Gem::Requirement
167
+ requirements:
168
+ - - ">="
169
+ - !ruby/object:Gem::Version
170
+ version: '0'
171
+ requirements: []
172
+ rubyforge_project:
173
+ rubygems_version: 2.2.2
174
+ signing_key:
175
+ specification_version: 4
176
+ summary: RSpec matcher for declarative_authorization.
177
+ test_files:
178
+ - spec/.keep
179
+ - spec/controllers/posts_controller_spec.rb
180
+ - spec/lib/rspec/authorization/adapters/example_spec.rb
181
+ - spec/lib/rspec/authorization/adapters/group_spec.rb
182
+ - spec/lib/rspec/authorization/adapters/request_spec.rb
183
+ - spec/lib/rspec/authorization/adapters/route_spec.rb
184
+ - spec/rails_helper.rb
185
+ - spec/spec_helper.rb
186
+ - spec/support/group_test_class.rb
187
+ - spec/tools/rails_test_app_spec.rb