rspec-grape-entity 0.1.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 +7 -0
- data/.github/workflows/rspec.yml +26 -0
- data/.github/workflows/rubocop.yml +30 -0
- data/.gitignore +17 -0
- data/.rspec +3 -0
- data/.rubocop.yml +13 -0
- data/Gemfile +13 -0
- data/LICENSE +21 -0
- data/LICENSE.txt +21 -0
- data/README.md +695 -0
- data/Rakefile +12 -0
- data/bin/console +15 -0
- data/bin/setup +8 -0
- data/lib/rspec-grape-entity.rb +3 -0
- data/lib/rspec_grape_entity/describe_exposure.rb +125 -0
- data/lib/rspec_grape_entity/dsl.rb +16 -0
- data/lib/rspec_grape_entity/its_exposure.rb +72 -0
- data/lib/rspec_grape_entity/matchers/be_a_exposure_type_matcher.rb +33 -0
- data/lib/rspec_grape_entity/matchers/be_merged_matcher.rb +21 -0
- data/lib/rspec_grape_entity/matchers/be_safe_matcher.rb +21 -0
- data/lib/rspec_grape_entity/matchers/be_using_class_matcher.rb +21 -0
- data/lib/rspec_grape_entity/matchers/have_conditions_met_matcher.rb +36 -0
- data/lib/rspec_grape_entity/matchers/have_formatting_matcher.rb +39 -0
- data/lib/rspec_grape_entity/matchers/have_key_matcher.rb +21 -0
- data/lib/rspec_grape_entity/matchers/have_root_matcher.rb +33 -0
- data/lib/rspec_grape_entity/matchers/include_documentation_matcher.rb +26 -0
- data/lib/rspec_grape_entity/matchers/matcher_helpers.rb +24 -0
- data/lib/rspec_grape_entity/matchers/override_exposure_matcher.rb +21 -0
- data/lib/rspec_grape_entity/version.rb +5 -0
- data/lib/rspec_grape_entity.rb +28 -0
- data/rspec-grape-entity.gemspec +37 -0
- data/spec/describe_exposure_spec.rb +29 -0
- data/spec/entities/test_entity_spec.rb +150 -0
- data/spec/its_exposure_spec.rb +16 -0
- data/spec/matchers/be_a_exposure_type_matcher_spec.rb +106 -0
- data/spec/matchers/be_merged_matcher_spec.rb +19 -0
- data/spec/matchers/be_safe_matcher_spec.rb +19 -0
- data/spec/matchers/be_using_class_matcher_spec.rb +15 -0
- data/spec/matchers/have_conditions_met_matcher_spec.rb +40 -0
- data/spec/matchers/have_formatting_matcher_spec.rb +25 -0
- data/spec/matchers/have_key_matcher_spec.rb +23 -0
- data/spec/matchers/have_root_matcher_spec.rb +47 -0
- data/spec/matchers/include_documentation_matcher_spec.rb +31 -0
- data/spec/matchers/matcher_helpers_spec.rb +76 -0
- data/spec/matchers/override_exposure_matcher_spec.rb +19 -0
- data/spec/spec_helper.rb +21 -0
- data/spec/support/test_entity.rb +23 -0
- data/spec/support/user_entity.rb +12 -0
- metadata +181 -0
data/bin/setup
ADDED
@@ -0,0 +1,125 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module DescribeExposure
|
7
|
+
# Creates a group named by the entity exposure `attribute`.
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
#
|
11
|
+
# class MyEntity < Grape::Entity
|
12
|
+
# expose :size, safe: true
|
13
|
+
# expose :name do
|
14
|
+
# expose :first_name, as: :first
|
15
|
+
# expose :last_name, as: :last
|
16
|
+
# end
|
17
|
+
# end
|
18
|
+
#
|
19
|
+
# # This ...
|
20
|
+
# describe MyEntity, type: :entity do
|
21
|
+
# describe_exposure :size do
|
22
|
+
# ...
|
23
|
+
# end
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# # ... generates the same runtime structure as this:
|
27
|
+
# describe MyEntity, type: :entity do
|
28
|
+
# describe "size" do
|
29
|
+
# let(:entity) { described_class }
|
30
|
+
# let(:exposure) { entity.find_exposure :size }
|
31
|
+
#
|
32
|
+
# ...
|
33
|
+
# end
|
34
|
+
# end
|
35
|
+
#
|
36
|
+
# The attribute can be a `Symbol` or a `String`. Given a `String`
|
37
|
+
# with dots, the result is as though you concatenated that `String`
|
38
|
+
# onto the entities nested exposures.
|
39
|
+
#
|
40
|
+
# @example
|
41
|
+
#
|
42
|
+
# describe MyEntity, type: :entity do
|
43
|
+
# describe_exposure "name.first_name" do
|
44
|
+
# ...
|
45
|
+
# end
|
46
|
+
# end
|
47
|
+
#
|
48
|
+
# With an implicit exposure, `is_expected` can be used as an alternative
|
49
|
+
# to `should` (e.g. for one-liner use).
|
50
|
+
#
|
51
|
+
# @example
|
52
|
+
#
|
53
|
+
# describe MyEntity do
|
54
|
+
# describe_exposure :size do
|
55
|
+
# it { should be_safe }
|
56
|
+
# it { is_expected.to be_safe }
|
57
|
+
# end
|
58
|
+
# end
|
59
|
+
def describe_exposure(attribute, *options, &block)
|
60
|
+
raise "Block not given" unless block_given?
|
61
|
+
|
62
|
+
options << {} unless options.last.is_a?(Hash)
|
63
|
+
describe_caller = options.last.fetch(:caller) do
|
64
|
+
caller.reject { |file_line| file_line =~ %r{/lib/rspec_grape_entity/describe_exposure} }
|
65
|
+
end
|
66
|
+
|
67
|
+
parent_described_class = described_class
|
68
|
+
|
69
|
+
describe attribute, caller: describe_caller do
|
70
|
+
include RSpec::Grape::Entity::Matchers::BeAExposureTypeMatcher
|
71
|
+
include RSpec::Grape::Entity::Matchers::BeMergedMatcher
|
72
|
+
include RSpec::Grape::Entity::Matchers::BeSafeMatcher
|
73
|
+
include RSpec::Grape::Entity::Matchers::BeUsingClassMatcher
|
74
|
+
include RSpec::Grape::Entity::Matchers::HaveConditionsMetMatcher
|
75
|
+
include RSpec::Grape::Entity::Matchers::HaveFormattingMatcher
|
76
|
+
include RSpec::Grape::Entity::Matchers::HaveKeyMatcher
|
77
|
+
include RSpec::Grape::Entity::Matchers::IncludeDocumentationMatcher
|
78
|
+
include RSpec::Grape::Entity::Matchers::OverrideExposureMatcher
|
79
|
+
|
80
|
+
let(:described_class) { parent_described_class }
|
81
|
+
let(:entity) { described_class } unless method_defined? :entity
|
82
|
+
|
83
|
+
let(:__attribute_exposure) do
|
84
|
+
exposure_chain = attribute.to_s.split(".")
|
85
|
+
exposure = entity.find_exposure exposure_chain.shift.to_sym
|
86
|
+
exposure_chain.inject(exposure) do |inner_exposure, attr|
|
87
|
+
inner_exposure.find_nested_exposure attr.to_sym
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
# rubocop:disable Lint/NestedMethodDefinition
|
92
|
+
def is_expected
|
93
|
+
expect(__attribute_exposure)
|
94
|
+
end
|
95
|
+
|
96
|
+
def will(matcher = nil, message = nil)
|
97
|
+
raise ArgumentError, "`will` only supports block expectations" unless matcher.supports_block_expectations?
|
98
|
+
|
99
|
+
expect { __attribute_exposure }.to matcher, message
|
100
|
+
end
|
101
|
+
|
102
|
+
def will_not(matcher = nil, message = nil)
|
103
|
+
unless matcher.supports_block_expectations?
|
104
|
+
raise ArgumentError, "`will_not` only supports block expectations"
|
105
|
+
end
|
106
|
+
|
107
|
+
expect { __attribute_exposure }.to_not matcher, message
|
108
|
+
end
|
109
|
+
|
110
|
+
def should(matcher = nil, message = nil)
|
111
|
+
RSpec::Expectations::PositiveExpectationHandler.handle_matcher(__attribute_exposure, matcher, message)
|
112
|
+
end
|
113
|
+
|
114
|
+
def should_not(matcher = nil, message = nil)
|
115
|
+
RSpec::Expectations::NegativeExpectationHandler.handle_matcher(__attribute_exposure, matcher, message)
|
116
|
+
end
|
117
|
+
# rubocop:enable Lint/NestedMethodDefinition
|
118
|
+
|
119
|
+
instance_eval(&block)
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
124
|
+
end
|
125
|
+
end
|
@@ -0,0 +1,72 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module ItsExposure
|
7
|
+
# Creates a nested example group named by the entity exposure `attribute`,
|
8
|
+
# and then generates an example using the submitted block.
|
9
|
+
#
|
10
|
+
# @example
|
11
|
+
#
|
12
|
+
# class MyEntity < Grape::Entity
|
13
|
+
# expose :size, safe: true
|
14
|
+
# expose :name do
|
15
|
+
# expose :first_name, as: :first
|
16
|
+
# expose :last_name, as: :last
|
17
|
+
# end
|
18
|
+
# end
|
19
|
+
#
|
20
|
+
# # This ...
|
21
|
+
# describe MyEntity do
|
22
|
+
# its_exposure(:size) { is_expected.to be_safe }
|
23
|
+
# end
|
24
|
+
#
|
25
|
+
# # ... generates the same runtime structure as this:
|
26
|
+
# describe MyEntity do
|
27
|
+
# describe "size" do
|
28
|
+
# let(:entity) { described_class }
|
29
|
+
#
|
30
|
+
# it "is_expected.to be_safe" do
|
31
|
+
# exposure = entity.find_exposure :size
|
32
|
+
# expect(exposure).to be_safe
|
33
|
+
# end
|
34
|
+
# end
|
35
|
+
# end
|
36
|
+
#
|
37
|
+
# The attribute can be a `Symbol` or a `String`. Given a `String`
|
38
|
+
# with dots, the result is as though you concatenated that `String`
|
39
|
+
# onto the entities nested exposures.
|
40
|
+
#
|
41
|
+
# @example
|
42
|
+
#
|
43
|
+
# describe MyEntity do
|
44
|
+
# its_exposure("name.first_name") { should have_key :first }
|
45
|
+
# end
|
46
|
+
#
|
47
|
+
# With an implicit exposure, `is_expected` can be used as an alternative
|
48
|
+
# to `should` (e.g. for one-liner use).
|
49
|
+
#
|
50
|
+
# @example
|
51
|
+
#
|
52
|
+
# describe MyEntity do
|
53
|
+
# its_exposure(:size) { is_expected.to eq(0) }
|
54
|
+
# end
|
55
|
+
def its_exposure(attribute, *options, &block)
|
56
|
+
its_caller = caller.reject { |file_line| file_line =~ %r{/lib/rspec_grape_entity/its_exposure} }
|
57
|
+
|
58
|
+
describe_exposure attribute, caller: its_caller do
|
59
|
+
options << {} unless options.last.is_a?(Hash)
|
60
|
+
options.last.merge!(caller: its_caller)
|
61
|
+
|
62
|
+
if block
|
63
|
+
example(nil, *options, &block)
|
64
|
+
else
|
65
|
+
example(nil, *options) { is_expected.not_to be_nil }
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module BeAExposureTypeMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
EXPOSURE_TYPES = %i[block delegator formatter_block formatter nesting represent].freeze
|
11
|
+
|
12
|
+
matcher :be_a_exposure_type do |expected|
|
13
|
+
include MatcherHelpers
|
14
|
+
|
15
|
+
match { |actual| actual.is_a? exposure_type(expected) }
|
16
|
+
description { "be exposure type #{expected}" }
|
17
|
+
failure_message { |actual| "expect that #{actual} to be a #{expected} exposure" }
|
18
|
+
end
|
19
|
+
|
20
|
+
EXPOSURE_TYPES.each do |type|
|
21
|
+
matcher :"be_a_#{type}_exposure" do
|
22
|
+
include MatcherHelpers
|
23
|
+
|
24
|
+
match { |actual| actual.is_a? exposure_type(type) }
|
25
|
+
description { "be a #{type} exposure" }
|
26
|
+
failure_message { |actual| "expect that #{actual} to be a #{type} exposure" }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module BeMergedMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :be_merged do
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| exposure_attribute(actual, :for_merge) }
|
14
|
+
description { "be merged" }
|
15
|
+
failure_message { |actual| "expect that #{actual} would merge contents" }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module BeSafeMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :be_safe do
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| exposure_attribute(actual, :is_safe) }
|
14
|
+
description { "be safe" }
|
15
|
+
failure_message { |actual| "expect that #{actual} to be safe" }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module BeUsingClassMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :be_using_class do |expected|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| expect(exposure_attribute(actual, :using_class)).to be expected }
|
14
|
+
description { "be using entity class #{entity_class_name expected}" }
|
15
|
+
failure_message { |actual| "expect that #{actual} would be using class #{entity_class_name expected}" }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module HaveConditionsMetMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :have_conditions_met do |object|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match do |actual|
|
14
|
+
entity_instance = entity.new object
|
15
|
+
actual.conditions_met? entity_instance, options
|
16
|
+
end
|
17
|
+
|
18
|
+
description { "have the conditions met" }
|
19
|
+
|
20
|
+
failure_message do |actual|
|
21
|
+
"expect that #{actual} would have the conditions met for object #{object} with options #{options}"
|
22
|
+
end
|
23
|
+
|
24
|
+
chain :with_options do |options|
|
25
|
+
@options = options
|
26
|
+
end
|
27
|
+
|
28
|
+
def options
|
29
|
+
@options ||= {}
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module HaveFormattingMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :have_formatting do |expected|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match do |actual|
|
14
|
+
if actual.is_a? ::Grape::Entity::Exposure::FormatterBlockExposure
|
15
|
+
instance = entity.new object
|
16
|
+
actual.value(instance, {}) == expected
|
17
|
+
else
|
18
|
+
exposure_attribute(actual, :format_with) == expected
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
description { "have the formatting #{expected}" }
|
23
|
+
|
24
|
+
failure_message do |actual|
|
25
|
+
if actual.is_a? ::Grape::Entity::Exposure::FormatterBlockExposure
|
26
|
+
instance = entity.new object
|
27
|
+
"expect that \"#{actual.value instance, {}}\" would have the formatting \"#{expected}\""
|
28
|
+
else
|
29
|
+
"expect that \"#{actual}\" would have the formatting \"#{expected}\""
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
chain :with_object, :object
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module HaveKeyMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :have_key do |expected|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| exposure_attribute(actual, :key) == expected }
|
14
|
+
description { "have the key #{expected}" }
|
15
|
+
failure_message { |actual| "expect that #{actual} would have the key #{expected}" }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module HaveRootMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :have_root do |plural|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match do |actual|
|
14
|
+
actual_plural = actual.root_element :collection_root
|
15
|
+
actual_singular = actual.root_element :root
|
16
|
+
|
17
|
+
values_match?(plural, actual_plural) &&
|
18
|
+
values_match?(singular, actual_singular)
|
19
|
+
end
|
20
|
+
|
21
|
+
description { "have the formatting #{expected}" }
|
22
|
+
|
23
|
+
failure_message do |actual|
|
24
|
+
"expect that \"#{actual}\" would have the root collection \"#{plural}\" and root \"#{singular}\""
|
25
|
+
end
|
26
|
+
|
27
|
+
chain :with_singular, :singular
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module IncludeDocumentationMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :include_documentation do |expected|
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| expect(documentation(actual)).to include expected }
|
14
|
+
match_when_negated { |actual| expect(documentation(actual)).to_not include expected }
|
15
|
+
description { "include documentation #{expected}" }
|
16
|
+
failure_message { |actual| "expect #{documentation actual} would include the documentation #{expected}" }
|
17
|
+
|
18
|
+
def documentation(actual)
|
19
|
+
exposure_attribute(actual, :documentation) || {}
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module MatcherHelpers
|
8
|
+
def entity_class_name(entity)
|
9
|
+
entity.try(:name) || entity.class.name
|
10
|
+
end
|
11
|
+
|
12
|
+
def exposure_attribute(exposure, name)
|
13
|
+
exposure.send name
|
14
|
+
end
|
15
|
+
|
16
|
+
def exposure_type(type)
|
17
|
+
type = type.to_s.split("_").map { |w| w[0].upcase + w[1..] }.join
|
18
|
+
Object.const_get "Grape::Entity::Exposure::#{type}Exposure"
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RSpec
|
4
|
+
module Grape
|
5
|
+
module Entity
|
6
|
+
module Matchers
|
7
|
+
module OverrideExposureMatcher
|
8
|
+
extend RSpec::Matchers::DSL
|
9
|
+
|
10
|
+
matcher :override_exposure do
|
11
|
+
include MatcherHelpers
|
12
|
+
|
13
|
+
match { |actual| exposure_attribute(actual, :override) }
|
14
|
+
description { "override exposure" }
|
15
|
+
failure_message { |actual| "expect that #{actual} would override exposure" }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "grape-entity"
|
4
|
+
require "rspec/expectations"
|
5
|
+
|
6
|
+
require_relative "rspec_grape_entity/matchers/matcher_helpers"
|
7
|
+
require_relative "rspec_grape_entity/matchers/be_a_exposure_type_matcher"
|
8
|
+
require_relative "rspec_grape_entity/matchers/be_merged_matcher"
|
9
|
+
require_relative "rspec_grape_entity/matchers/be_safe_matcher"
|
10
|
+
require_relative "rspec_grape_entity/matchers/be_using_class_matcher"
|
11
|
+
require_relative "rspec_grape_entity/matchers/have_conditions_met_matcher"
|
12
|
+
require_relative "rspec_grape_entity/matchers/have_formatting_matcher"
|
13
|
+
require_relative "rspec_grape_entity/matchers/have_key_matcher"
|
14
|
+
require_relative "rspec_grape_entity/matchers/have_root_matcher"
|
15
|
+
require_relative "rspec_grape_entity/matchers/include_documentation_matcher"
|
16
|
+
require_relative "rspec_grape_entity/matchers/override_exposure_matcher"
|
17
|
+
require_relative "rspec_grape_entity/describe_exposure"
|
18
|
+
require_relative "rspec_grape_entity/its_exposure"
|
19
|
+
require_relative "rspec_grape_entity/dsl"
|
20
|
+
require_relative "rspec_grape_entity/version"
|
21
|
+
|
22
|
+
RSpec.configure do |rspec|
|
23
|
+
rspec.extend RSpec::Grape::Entity::DescribeExposure, type: :grape_entity
|
24
|
+
rspec.extend RSpec::Grape::Entity::ItsExposure, type: :grape_entity
|
25
|
+
rspec.include RSpec::Grape::Entity::Matchers::HaveRootMatcher, type: :grape_entity
|
26
|
+
rspec.backtrace_exclusion_patterns << %r{/lib/rspec_grape_entity/describe_exposure}
|
27
|
+
rspec.backtrace_exclusion_patterns << %r{/lib/rspec_grape_entity/its_exposure}
|
28
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
lib = File.expand_path("../lib", __FILE__)
|
4
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
5
|
+
require "rspec_grape_entity/version"
|
6
|
+
|
7
|
+
Gem::Specification.new do |spec|
|
8
|
+
spec.name = "rspec-grape-entity"
|
9
|
+
spec.version = RSpecGrapeEntity::VERSION
|
10
|
+
spec.platform = Gem::Platform::RUBY
|
11
|
+
spec.authors = ["James Fawks"]
|
12
|
+
spec.email = ["jefawks3@gmail.com"]
|
13
|
+
spec.summary = "RSpec extension gem for grape-entity"
|
14
|
+
spec.description = 'Provides "it_exposes" and "describe_exposure" methods to test Grape Entities'
|
15
|
+
spec.homepage = "https://github.com/jefawks3/rspec-grape-entity"
|
16
|
+
spec.license = "MIT"
|
17
|
+
|
18
|
+
spec.metadata = {
|
19
|
+
"bug_tracker_uri" => "https://github.com/jefawks3/rspec-grape-entity/issues",
|
20
|
+
"changelog_uri" => "https://github.com/jefawks3/rspec-grape-entity/releases",
|
21
|
+
"documentation_uri" => "https://github.com/jefawks3/rspec-grape-entity",
|
22
|
+
"source_code_uri" => "https://github.com/jefawks3/rspec-grape-entity"
|
23
|
+
}
|
24
|
+
|
25
|
+
spec.required_ruby_version = ">= 2.7.0"
|
26
|
+
|
27
|
+
spec.add_runtime_dependency "grape-entity", ">= 0.10.0"
|
28
|
+
spec.add_runtime_dependency "rspec-core", ">= 3.0.0"
|
29
|
+
spec.add_runtime_dependency "rspec-expectations", ">= 3.0.0"
|
30
|
+
|
31
|
+
spec.add_development_dependency "bundler", "> 1.3.0"
|
32
|
+
spec.add_development_dependency "rake", "~> 13.0.0"
|
33
|
+
|
34
|
+
spec.files = `git ls-files`.split("\n")
|
35
|
+
spec.test_files = `git ls-files -- {test,spec}/*`.split("\n")
|
36
|
+
spec.require_paths = ["lib"]
|
37
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "spec_helper"
|
4
|
+
|
5
|
+
RSpec.describe RSpec::Grape::Entity::DescribeExposure do
|
6
|
+
extend RSpec::Grape::Entity::DescribeExposure
|
7
|
+
|
8
|
+
let(:entity) { TestEntity }
|
9
|
+
|
10
|
+
describe_exposure :id do
|
11
|
+
it { is_expected.to be_a Grape::Entity::Exposure::DelegatorExposure }
|
12
|
+
end
|
13
|
+
|
14
|
+
describe_exposure "id" do
|
15
|
+
it { is_expected.to be_a Grape::Entity::Exposure::DelegatorExposure }
|
16
|
+
end
|
17
|
+
|
18
|
+
describe_exposure "unknown" do
|
19
|
+
it { is_expected.to be_nil }
|
20
|
+
end
|
21
|
+
|
22
|
+
describe_exposure "permissions.read" do
|
23
|
+
it { is_expected.to be_a Grape::Entity::Exposure::DelegatorExposure }
|
24
|
+
end
|
25
|
+
|
26
|
+
describe_exposure "unknown.unknown" do
|
27
|
+
it { expect { __attribute_exposure }.to raise_error NoMethodError }
|
28
|
+
end
|
29
|
+
end
|