rspec-sleeping_king_studios 2.0.0.beta.0 → 2.0.0.beta.1

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 (47) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +84 -13
  3. data/DEVELOPMENT.md +16 -0
  4. data/README.md +203 -100
  5. data/lib/rspec/sleeping_king_studios/all.rb +4 -0
  6. data/lib/rspec/sleeping_king_studios/configuration.rb +42 -0
  7. data/lib/rspec/sleeping_king_studios/examples/all.rb +5 -0
  8. data/lib/rspec/sleeping_king_studios/examples/property_examples.rb +58 -0
  9. data/lib/rspec/sleeping_king_studios/examples/rspec_matcher_examples.rb +105 -0
  10. data/lib/rspec/sleeping_king_studios/examples/shared_example_group.rb +62 -0
  11. data/lib/rspec/sleeping_king_studios/examples.rb +8 -0
  12. data/lib/rspec/sleeping_king_studios/matchers/active_model/all.rb +5 -0
  13. data/lib/rspec/sleeping_king_studios/matchers/active_model/have_errors/error_expectation.rb +0 -1
  14. data/lib/rspec/sleeping_king_studios/matchers/active_model/have_errors/message_expectation.rb +1 -2
  15. data/lib/rspec/sleeping_king_studios/matchers/active_model/have_errors.rb +75 -24
  16. data/lib/rspec/sleeping_king_studios/matchers/active_model.rb +6 -3
  17. data/lib/rspec/sleeping_king_studios/matchers/all.rb +5 -0
  18. data/lib/rspec/sleeping_king_studios/matchers/base_matcher.rb +20 -1
  19. data/lib/rspec/sleeping_king_studios/matchers/built_in/all.rb +5 -0
  20. data/lib/rspec/sleeping_king_studios/matchers/built_in/be_kind_of.rb +16 -10
  21. data/lib/rspec/sleeping_king_studios/matchers/built_in/include.rb +14 -9
  22. data/lib/rspec/sleeping_king_studios/matchers/built_in/respond_to.rb +45 -31
  23. data/lib/rspec/sleeping_king_studios/matchers/built_in.rb +5 -3
  24. data/lib/rspec/sleeping_king_studios/matchers/core/all.rb +5 -0
  25. data/lib/rspec/sleeping_king_studios/matchers/core/be_boolean.rb +11 -4
  26. data/lib/rspec/sleeping_king_studios/matchers/core/construct.rb +56 -32
  27. data/lib/rspec/sleeping_king_studios/matchers/core/have_property.rb +59 -29
  28. data/lib/rspec/sleeping_king_studios/matchers/core/have_reader.rb +31 -22
  29. data/lib/rspec/sleeping_king_studios/matchers/core/have_writer.rb +21 -55
  30. data/lib/rspec/sleeping_king_studios/matchers/core.rb +5 -3
  31. data/lib/rspec/sleeping_king_studios/matchers/shared/match_parameters.rb +1 -3
  32. data/lib/rspec/sleeping_king_studios/matchers/shared/match_property.rb +52 -0
  33. data/lib/rspec/sleeping_king_studios/matchers.rb +10 -3
  34. data/lib/rspec/sleeping_king_studios/version.rb +22 -1
  35. data/lib/rspec/sleeping_king_studios.rb +7 -1
  36. metadata +38 -16
  37. data/lib/rspec/sleeping_king_studios/matchers/active_model/have_errors/require.rb +0 -7
  38. data/lib/rspec/sleeping_king_studios/matchers/active_model/require.rb +0 -8
  39. data/lib/rspec/sleeping_king_studios/matchers/built_in/require.rb +0 -7
  40. data/lib/rspec/sleeping_king_studios/matchers/core/require.rb +0 -7
  41. data/lib/rspec/sleeping_king_studios/matchers/meta/fail_with_actual.rb +0 -107
  42. data/lib/rspec/sleeping_king_studios/matchers/meta/pass_with_actual.rb +0 -95
  43. data/lib/rspec/sleeping_king_studios/matchers/meta/require.rb +0 -7
  44. data/lib/rspec/sleeping_king_studios/matchers/meta.rb +0 -5
  45. data/lib/rspec/sleeping_king_studios/matchers/require.rb +0 -12
  46. data/lib/rspec/sleeping_king_studios/matchers/shared/require.rb +0 -7
  47. data/lib/rspec/sleeping_king_studios/require.rb +0 -7
@@ -0,0 +1,58 @@
1
+ # lib/rspec/sleeping_king_studios/examples/property_examples.rb
2
+
3
+ require 'rspec/sleeping_king_studios/examples'
4
+ require 'rspec/sleeping_king_studios/examples/shared_example_group'
5
+ require 'rspec/sleeping_king_studios/matchers/core/have_reader'
6
+ require 'rspec/sleeping_king_studios/matchers/core/have_writer'
7
+ require 'sleeping_king_studios/tools/object_tools'
8
+
9
+ module RSpec::SleepingKingStudios::Examples::PropertyExamples
10
+ extend RSpec::SleepingKingStudios::Examples::SharedExampleGroup
11
+
12
+ UNDEFINED_PROPERTY_EXPECTATION = Object.new.freeze
13
+
14
+ shared_examples 'has reader' do |property, expected_value = UNDEFINED_PROPERTY_EXPECTATION|
15
+ it "has reader :#{property}" do
16
+ object = defined?(instance) ? instance : subject
17
+
18
+ expect(object).to have_reader(property)
19
+
20
+ next if expected_value == UNDEFINED_PROPERTY_EXPECTATION
21
+
22
+ actual_value = instance.send property
23
+
24
+ if expected_value.is_a?(Proc)
25
+ args = [self, expected_value]
26
+ args.push actual_value unless 0 == expected_value.arity
27
+
28
+ expected_value = SleepingKingStudios::Tools::ObjectTools.apply *args
29
+ end # if
30
+
31
+ case expected_value
32
+ when ->(obj) { obj.respond_to?(:matches?) }
33
+ expect(actual_value).to expected_value
34
+ when true, false
35
+ expected_value
36
+ else
37
+ expect(actual_value).to be == expected_value
38
+ end # case
39
+ end # it
40
+ end # shared_examples
41
+ alias_shared_examples 'should have reader', 'has reader'
42
+
43
+ shared_examples 'has writer' do |property|
44
+ it "has writer :#{property}=" do
45
+ object = defined?(instance) ? instance : subject
46
+
47
+ expect(object).to have_writer(property)
48
+ end # it
49
+ end # shared_examples
50
+ alias_shared_examples 'should have writer', 'has writer'
51
+
52
+ shared_examples 'has property' do |property, expected_value = UNDEFINED_PROPERTY_EXPECTATION|
53
+ include_examples 'has reader', property, expected_value
54
+
55
+ include_examples 'has writer', property
56
+ end # shared_examples
57
+ alias_shared_examples 'should have property', 'has property'
58
+ end # module
@@ -0,0 +1,105 @@
1
+ # lib/rspec/sleeping_king_studios/examples/rspec_matcher_examples.rb
2
+
3
+ require 'rspec/sleeping_king_studios/examples'
4
+ require 'rspec/sleeping_king_studios/examples/shared_example_group'
5
+ require 'rspec/sleeping_king_studios/matchers/base_matcher'
6
+
7
+ module RSpec::SleepingKingStudios::Examples::RSpecMatcherExamples
8
+ extend RSpec::SleepingKingStudios::Examples::SharedExampleGroup
9
+
10
+ shared_examples 'passes with a positive expectation' do
11
+ let(:matcher_being_examined) { defined?(instance) ? instance : subject }
12
+
13
+ it 'passes with a positive expectation' do
14
+ expect(matcher_being_examined.matches? actual).to be true
15
+ end # it
16
+ end # shared_examples
17
+ alias_shared_examples 'should pass with a positive expectation', 'passes with a positive expectation'
18
+
19
+ shared_examples 'fails with a positive expectation' do
20
+ let(:matcher_being_examined) { defined?(instance) ? instance : subject }
21
+
22
+ it 'fails with a positive expectation' do
23
+ expect(matcher_being_examined.matches? actual).to be false
24
+ end # it
25
+
26
+ it 'has a failure message with a positive expectation' do
27
+ if defined?(failure_message)
28
+ matcher_being_examined.matches?(actual)
29
+
30
+ expected = failure_message.is_a?(String) ?
31
+ Regexp.new(Regexp.escape(failure_message)) :
32
+ failure_message
33
+
34
+ expect(matcher_being_examined.failure_message).to match expected
35
+ else
36
+ message = <<-MESSAGE
37
+ expected to match #{matcher_being_examined.class}#failure_message, but the expected
38
+ value was undefined. Define a failure message using
39
+ let(:failure_message) or set
40
+ config.handle_missing_failure_message_with to :ignore or :pending.
41
+ MESSAGE
42
+ message = message.split("\n").map(&:strip).join(' ')
43
+ case RSpec.configuration.sleeping_king_studios.examples.handle_missing_failure_message_with
44
+ when :pending
45
+ skip message
46
+ when :exception
47
+ raise StandardError.new message
48
+ end # case
49
+ end # if
50
+ end # it
51
+ end # shared_examples
52
+ alias_shared_examples 'should fail with a positive expectation', 'fails with a positive expectation'
53
+
54
+ shared_examples 'passes with a negative expectation' do
55
+ let(:matcher_being_examined) { defined?(instance) ? instance : subject }
56
+
57
+ it 'passes with a negative expectation' do
58
+ if matcher_being_examined.respond_to?(:does_not_match?)
59
+ expect(matcher_being_examined.does_not_match? actual).to be true
60
+ else
61
+ expect(matcher_being_examined.matches? actual).to be false
62
+ end # if-else
63
+ end # it
64
+ end # shared_examples
65
+ alias_shared_examples 'should pass with a negative expectation', 'passes with a negative expectation'
66
+
67
+ shared_examples 'fails with a negative expectation' do
68
+ let(:matcher_being_examined) { defined?(instance) ? instance : subject }
69
+
70
+ it 'fails with a negative expectation' do
71
+ if matcher_being_examined.respond_to?(:does_not_match?)
72
+ expect(matcher_being_examined.does_not_match? actual).to be false
73
+ else
74
+ expect(matcher_being_examined.matches? actual).to be true
75
+ end # if-else
76
+ end # it
77
+
78
+ it 'has a failure message with a negative expectation' do
79
+ if defined?(failure_message_when_negated)
80
+ matcher_being_examined.respond_to?(:does_not_match?) ? matcher_being_examined.does_not_match?(actual) : matcher_being_examined.matches?(actual)
81
+
82
+ expected = failure_message_when_negated.is_a?(String) ?
83
+ Regexp.new(Regexp.escape(failure_message_when_negated)) :
84
+ failure_message_when_negated
85
+
86
+ expect(matcher_being_examined.failure_message_when_negated).to match expected
87
+ else
88
+ message = <<-MESSAGE
89
+ expected to match #{matcher_being_examined.class}#failure_message_when_negated, but
90
+ the expected value was undefined. Define a failure message using
91
+ let(:failure_message_when_negated) or set
92
+ config.handle_missing_failure_message_with to :ignore or :pending.
93
+ MESSAGE
94
+ message = message.split("\n").map(&:strip).join(' ')
95
+ case RSpec.configuration.sleeping_king_studios.examples.handle_missing_failure_message_with
96
+ when :pending
97
+ skip message
98
+ when :exception
99
+ raise StandardError.new message
100
+ end # case
101
+ end # if
102
+ end # it
103
+ end # shared_examples
104
+ alias_shared_examples 'should fail with a negative expectation', 'fails with a negative expectation'
105
+ end # module
@@ -0,0 +1,62 @@
1
+ # lib/rspec/sleeping_king_studios/examples/shared_example_group.rb
2
+
3
+ require 'rspec/sleeping_king_studios/examples'
4
+
5
+ module RSpec::SleepingKingStudios::Examples
6
+ module SharedExampleGroup
7
+ # Aliases a defined shared example group, allowing it to be accessed using
8
+ # a new name. The example group must be defined in the current context
9
+ # using `shared_examples`. The aliases must be defined before including the
10
+ # module into an example group, or they will not be available in the
11
+ # example group.
12
+ #
13
+ # @param [String] new_name The new name to alias the shared example group
14
+ # as.
15
+ # @param [String] old_name The name under which the shared example group is
16
+ # currently defined.
17
+ def alias_shared_examples new_name, old_name
18
+ proc = shared_example_groups[self][old_name]
19
+
20
+ self.shared_examples new_name, &proc
21
+ end # method alias_shared_examples
22
+
23
+ # @api private
24
+ def included other
25
+ merge_shared_example_groups other
26
+ end # method included
27
+
28
+ # @overload shared_examples(name, &block)
29
+ # @param [String] name Identifer to use when looking up this shared group.
30
+ # @param block Used to create the shared example group definition.
31
+ # @overload shared_examples(name, metadata, &block)
32
+ # @param [String] name Identifer to use when looking up this shared group.
33
+ # @param metadata [Array<Symbol>, Hash] Metadata to attach to this group;
34
+ # any example group with matching metadata will automatically include
35
+ # this shared example group.
36
+ # @param block Used to create the shared example group definition.
37
+ #
38
+ # Defines a shared example group within the context of the current module.
39
+ # Unlike a top-level example group defined using RSpec#shared_examples,
40
+ # these examples are not globally available, and must be mixed into an
41
+ # example group by including the module. The shared examples must be
42
+ # defined before including the module, or they will not be available in the
43
+ # example group.
44
+ def shared_examples name, *metadata_args, &block
45
+ RSpec.world.shared_example_group_registry.add(self, name, *metadata_args, &block)
46
+ end # method shared_examples
47
+
48
+ private
49
+
50
+ # @api private
51
+ def merge_shared_example_groups other
52
+ shared_example_groups[self].each do |name, proc|
53
+ RSpec.world.shared_example_group_registry.add(other, name, &proc)
54
+ end # each
55
+ end # method merge_shared_example_groups
56
+
57
+ # @api private
58
+ def shared_example_groups
59
+ RSpec.world.shared_example_group_registry.send :shared_example_groups
60
+ end # method shared_example_groups
61
+ end # module
62
+ end # module
@@ -0,0 +1,8 @@
1
+ # lib/rspec/sleeping_king_studios/examples.rb
2
+
3
+ require 'rspec/sleeping_king_studios'
4
+
5
+ module RSpec::SleepingKingStudios
6
+ # Pregenerated example groups for use with RSpec.
7
+ module Examples; end
8
+ end # module
@@ -0,0 +1,5 @@
1
+ # lib/rspec/sleeping_king_studios/matchers/active_model/all.rb
2
+
3
+ Dir[File.join File.dirname(__FILE__), '*.rb'].each do |file|
4
+ require file
5
+ end # end each
@@ -1,6 +1,5 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/active_model/have_errors/error_expectation.rb
2
2
 
3
- require 'rspec/sleeping_king_studios/matchers/base_matcher'
4
3
  require 'rspec/sleeping_king_studios/matchers/active_model/have_errors/message_expectation'
5
4
 
6
5
  module RSpec::SleepingKingStudios::Matchers::ActiveModel::HaveErrors
@@ -1,7 +1,6 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/active_model/have_errors/message_expectation.rb
2
2
 
3
- require 'rspec/sleeping_king_studios/matchers/base_matcher'
4
- require 'rspec/sleeping_king_studios/matchers/active_model/have_errors/require'
3
+ require 'rspec/sleeping_king_studios/matchers/active_model'
5
4
 
6
5
  module RSpec::SleepingKingStudios::Matchers::ActiveModel::HaveErrors
7
6
  # Stores an expectation of receiving a specified error message.
@@ -1,15 +1,19 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/active_model/have_errors.rb
2
2
 
3
3
  require 'rspec/sleeping_king_studios/matchers/base_matcher'
4
- require 'rspec/sleeping_king_studios/matchers/active_model/require'
4
+ require 'rspec/sleeping_king_studios/matchers/active_model'
5
5
  require 'rspec/sleeping_king_studios/matchers/active_model/have_errors/error_expectation'
6
+ require 'sleeping_king_studios/tools/enumerable_tools'
7
+ require 'sleeping_king_studios/tools/string_tools'
6
8
 
7
9
  module RSpec::SleepingKingStudios::Matchers::ActiveModel
8
10
  # Matcher for testing ActiveModel object validations.
9
- #
11
+ #
10
12
  # @since 1.0.0
11
13
  class HaveErrorsMatcher < RSpec::SleepingKingStudios::Matchers::BaseMatcher
12
14
  include RSpec::SleepingKingStudios::Matchers::ActiveModel::HaveErrors
15
+ include SleepingKingStudios::Tools::EnumerableTools
16
+ include SleepingKingStudios::Tools::StringTools
13
17
 
14
18
  def initialize
15
19
  super
@@ -19,12 +23,55 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
19
23
  @error_expectations = []
20
24
  end # constructor
21
25
 
26
+ # Generates a description of the matcher expectation.
27
+ #
28
+ # @return [String] The matcher description.
29
+ def description
30
+ message = 'have errors'
31
+
32
+ attribute_messages = @error_expectations.select(&:expected).map do |expectation|
33
+ attribute_message = ":#{expectation.attribute}"
34
+
35
+ error_messages = expectation.messages.select(&:expected).map do |message_expectation|
36
+ %{"#{message_expectation.message}"}
37
+ end # map
38
+
39
+ unless error_messages.empty?
40
+ attribute_message << " with #{pluralize(error_messages.count, 'message', 'messages')} #{humanize_list error_messages}"
41
+ end # unless
42
+
43
+ attribute_message
44
+ end # each
45
+ message << " on #{attribute_messages.join(", and on ")}" unless attribute_messages.empty?
46
+
47
+ message
48
+ end # method description
49
+
50
+ # Checks if the object can be validated, whether the object is valid, and
51
+ # checks the errors on the object against the expected errors and messages
52
+ # from #on and #with_message, if any.
53
+ #
54
+ # @param [Object] actual the object to test against the matcher
55
+ #
56
+ # @return [Boolean] true if the object responds to :valid? and is valid
57
+ # or object.errors does not match the specified errors and messages (if
58
+ # any); otherwise false
59
+ #
60
+ # @see #matches?
61
+ def does_not_match? actual
62
+ @negative_expectation = true
63
+
64
+ return false unless @validates = actual.respond_to?(:valid?)
65
+
66
+ !matches?(actual)
67
+ end # method does_not_match?
68
+
22
69
  # Checks if the object can be validated, whether the object is valid, and
23
70
  # checks the errors on the object against the expected errors and messages
24
71
  # from #on and #with_message, if any.
25
- #
72
+ #
26
73
  # @param [Object] actual the object to test against the matcher
27
- #
74
+ #
28
75
  # @return [Boolean] true if the object responds to :valid?, is not valid,
29
76
  # and object.errors matches the specified errors and messages (if any);
30
77
  # otherwise false
@@ -39,55 +86,56 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
39
86
 
40
87
  # Adds an error expectation. If the actual object does not have an error on
41
88
  # the specified attribute, #matches? will return false.
42
- #
89
+ #
43
90
  # @param [String, Symbol] attribute
44
- #
91
+ #
45
92
  # @return [HaveErrorsMatcher] self
46
- #
93
+ #
47
94
  # @example Setting an error expectation
48
95
  # expect(actual).to have_errors.on(:foo)
49
96
  def on attribute
50
97
  @error_expectations << ErrorExpectation.new(attribute)
51
-
98
+
52
99
  self
53
100
  end # method on
54
101
 
55
102
  # Adds a message expectation for the most recently added error attribute.
56
103
  # If the actual object does not have an error on the that attribute with
57
104
  # the specified message, #matches? will return false.
58
- #
105
+ #
59
106
  # @param [String, Regexp] message the expected error message. If a string,
60
107
  # matcher will check for an exact match; if a regular expression, matcher
61
108
  # will check if the message matches the regexp
62
- #
109
+ #
63
110
  # @raise [ArgumentError] if no error attribute has been added
64
- #
111
+ #
65
112
  # @return [HaveErrorsMatcher] self
66
- #
113
+ #
67
114
  # @example Setting an error and a message expectation
68
115
  # expect(actual).to have_errors.on(:foo).with("can't be blank")
69
- #
116
+ #
70
117
  # @see #on
71
118
  def with_message message
72
119
  raise ArgumentError.new "no attribute specified for error message" if
73
120
  @error_expectations.empty?
74
-
121
+
75
122
  @error_expectations.last.messages << MessageExpectation.new(message)
76
-
123
+
77
124
  self
78
125
  end # method with_message
79
126
 
80
127
  # Adds a set of message expectations for the most recently added error
81
128
  # attribute.
82
- #
129
+ #
83
130
  # @param [Array<String, Regexp>] messages
84
- #
131
+ #
85
132
  # @see #with_message
86
133
  def with_messages *messages
87
134
  messages.each do |message| self.with_message(message); end
88
-
135
+
89
136
  self
90
137
  end # method with_message
138
+ alias_method :with, :with_messages
91
139
 
92
140
  # @see BaseMatcher#failure_message
93
141
  def failure_message
@@ -109,14 +157,17 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
109
157
  # @see BaseMatcher#failure_message_when_negated
110
158
  def failure_message_when_negated
111
159
  # Failure cases:
160
+ # * object is not a model ("to respond to valid")
112
161
  # * expected one or more errors, received one or more ("not to have
113
162
  # errors")
114
163
  # * expected one or more messages on attribute, received one or more
115
164
  # ("not to have errors on")
116
165
  # * expected specific messages on attribute, received all ("not to have
117
166
  # errors on")
118
-
119
- if expected_errors.empty?
167
+
168
+ if !@validates
169
+ "expected #{@actual.inspect} to respond to :valid?"
170
+ elsif expected_errors.empty?
120
171
  return "expected #{@actual.inspect} not to have errors#{received_errors_message}"
121
172
  else
122
173
  return "expected #{@actual.inspect} not to have errors#{expected_errors_message}#{received_errors_message}"
@@ -124,7 +175,7 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
124
175
  end # method failure_message_when_negated
125
176
 
126
177
  private
127
-
178
+
128
179
  def attributes_have_errors?
129
180
  # Iterate through the received errors and match them against the expected
130
181
  # errors and messages.
@@ -155,7 +206,7 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
155
206
  else
156
207
  error_expectation.messages << MessageExpectation.new(message, false, true)
157
208
  end # if-else
158
- end # each
209
+ end # each
159
210
  end # unless
160
211
  else
161
212
  error_expectation = ErrorExpectation.new attribute, false, true
@@ -175,7 +226,7 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
175
226
  error_expectation.expected
176
227
  end # select
177
228
  end # method expected_errors
178
-
229
+
179
230
  def missing_errors
180
231
  @error_expectations.select do |error_expectation|
181
232
  error_expectation.expected && !error_expectation.received
@@ -197,7 +248,7 @@ module RSpec::SleepingKingStudios::Matchers::ActiveModel
197
248
  def expected_errors_message
198
249
  "\n expected errors:" + expected_errors.map do |error_expectation|
199
250
  "\n #{error_expectation.attribute}: " + (error_expectation.messages.empty? ?
200
- "(any)" :
251
+ "(#{@negative_expectation ? 'none' : 'any'})" :
201
252
  error_expectation.messages.expected.map(&:message).map(&:inspect).join(", "))
202
253
  end.join # map
203
254
  end # method expected_errors_message
@@ -1,5 +1,8 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/active_model.rb
2
2
 
3
- Dir[File.join File.dirname(__FILE__), 'active_model', '*.rb'].each do |file|
4
- require file
5
- end # end each
3
+ require 'rspec/sleeping_king_studios/matchers'
4
+
5
+ module RSpec::SleepingKingStudios::Matchers
6
+ # Matchers for ActiveModel object validation testing.
7
+ module ActiveModel; end
8
+ end # module
@@ -0,0 +1,5 @@
1
+ # lib/rspec/sleeping_king_studios/matchers/all.rb
2
+
3
+ %w(active_model built_in core).each do |dir_name|
4
+ require File.join File.dirname(__FILE__), dir_name, 'all'
5
+ end # each
@@ -1,6 +1,6 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/base_matcher.rb
2
2
 
3
- require 'rspec/sleeping_king_studios/matchers/require'
3
+ require 'rspec/sleeping_king_studios/matchers'
4
4
 
5
5
  module RSpec::SleepingKingStudios::Matchers
6
6
  # Minimal implementation of the RSpec matcher interface.
@@ -20,6 +20,17 @@ module RSpec::SleepingKingStudios::Matchers
20
20
  "#{name_to_sentence}#{to_sentence @expected}"
21
21
  end # method description
22
22
 
23
+ # Inverse of #matches? method.
24
+ #
25
+ # @param [Object] actual the object to test against the matcher
26
+ #
27
+ # @return [Boolean] false if the object matches, otherwise true
28
+ #
29
+ # @see #matches?
30
+ def does_not_match? actual
31
+ !matches?(actual)
32
+ end # method does_not_match?
33
+
23
34
  # Tests the actual object to see if it matches the defined condition(s).
24
35
  # Invoked by RSpec expectations.
25
36
  #
@@ -28,6 +39,7 @@ module RSpec::SleepingKingStudios::Matchers
28
39
  # @return [Boolean] true if the object matches, otherwise false
29
40
  def matches? actual
30
41
  @actual = actual
42
+
31
43
  true
32
44
  end # method matches?
33
45
 
@@ -42,5 +54,12 @@ module RSpec::SleepingKingStudios::Matchers
42
54
  def failure_message_when_negated
43
55
  "expected #{@actual.inspect} not to #{description}"
44
56
  end # method failure_message_when_negated
57
+
58
+ private
59
+
60
+ # @api private
61
+ def name_to_sentence
62
+ 'match'
63
+ end # method name_to_sentence
45
64
  end # class
46
65
  end # module
@@ -0,0 +1,5 @@
1
+ # lib/rspec/sleeping_king_studios/matchers/built_in/all.rb
2
+
3
+ Dir[File.join File.dirname(__FILE__), '*.rb'].each do |file|
4
+ require file
5
+ end # end each
@@ -1,17 +1,27 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/built_in/be_kind_of.rb
2
2
 
3
- require 'rspec/sleeping_king_studios/matchers/built_in/require'
3
+ require 'rspec/sleeping_king_studios/matchers/built_in'
4
+ require 'sleeping_king_studios/tools/enumerable_tools'
4
5
 
5
6
  module RSpec::SleepingKingStudios::Matchers::BuiltIn
6
7
  class BeAKindOfMatcher < RSpec::Matchers::BuiltIn::BeAKindOf
8
+ include SleepingKingStudios::Tools::EnumerableTools
9
+
10
+ # Generates a description of the matcher expectation.
11
+ #
12
+ # @return [String] The matcher description.
13
+ def description
14
+ message = "be #{type_string}"
15
+ end # method description
16
+
7
17
  # Checks if the object matches one of the specified types. Allows an
8
18
  # expected value of nil as a shortcut for expecting an instance of
9
19
  # NilClass.
10
- #
20
+ #
11
21
  # @param [Module, nil, Array<Module, nil>] expected the type or types to
12
22
  # check the object against
13
23
  # @param [Object] actual the object to check
14
- #
24
+ #
15
25
  # @return [Boolean] true if the object matches one of the specified types,
16
26
  # otherwise false
17
27
  def match expected, actual
@@ -22,14 +32,14 @@ module RSpec::SleepingKingStudios::Matchers::BuiltIn
22
32
  def failure_message
23
33
  "expected #{@actual.inspect} to be #{type_string}"
24
34
  end # method failure_message
25
-
35
+
26
36
  # @see BaseMatcher#failure_message_when_negated
27
37
  def failure_message_when_negated
28
38
  "expected #{@actual.inspect} not to be #{type_string}"
29
39
  end # method failure_message_when_negated
30
40
 
31
41
  private
32
-
42
+
33
43
  def match_type? expected
34
44
  case
35
45
  when expected.nil?
@@ -46,11 +56,7 @@ module RSpec::SleepingKingStudios::Matchers::BuiltIn
46
56
  when @expected.nil?
47
57
  @expected.inspect
48
58
  when @expected.is_a?(Enumerable) && 1 < @expected.count
49
- if 2 == expected.count
50
- "a #{expected.first.inspect} or #{expected.last.inspect}"
51
- else
52
- "a #{expected[0..-2].map(&:inspect).join(", ")}, or #{expected.last.inspect}"
53
- end # if-else
59
+ "a #{humanize_list @expected.map { |value| value.nil? ? 'nil' : value }, :last_separator => ' or '}"
54
60
  else
55
61
  "a #{expected}"
56
62
  end # case
@@ -1,12 +1,12 @@
1
1
  # lib/rspec/sleeping_king_studios/matchers/built_in/be_kind_of.rb
2
2
 
3
- require 'rspec/sleeping_king_studios/matchers/built_in/require'
3
+ require 'rspec/sleeping_king_studios/matchers/built_in'
4
4
 
5
5
  module RSpec::SleepingKingStudios::Matchers::BuiltIn
6
6
  class IncludeMatcher < RSpec::Matchers::BuiltIn::Include
7
7
  # @param [Array<Hash, Proc, Object>] expected the items expected to be
8
8
  # matched by the actual object
9
- #
9
+ #
10
10
  # @yield if a block is provided, the block is converted to a proc and
11
11
  # appended to the item expectations
12
12
  # @yieldparam [Object] item an item from the actual object; yield(item)
@@ -14,6 +14,7 @@ module RSpec::SleepingKingStudios::Matchers::BuiltIn
14
14
  # predicate
15
15
  def initialize *expected, &block
16
16
  expected << block if block_given?
17
+
17
18
  super *expected
18
19
  end # constructor
19
20
 
@@ -31,19 +32,27 @@ module RSpec::SleepingKingStudios::Matchers::BuiltIn
31
32
 
32
33
  # @see BaseMatcher#failure_message
33
34
  def failure_message
34
- return "expected #{@actual.inspect} to respond to :include?" if false === @includes
35
+ message = super
36
+
37
+ message << ", but it does not respond to `include?`" unless actual.respond_to?(:include?) || message =~ /does not respond to/
35
38
 
36
- super
39
+ message
37
40
  end # method failure_message_for_should
38
41
 
39
42
  # @see BaseMatcher#failure_message_when_negated
40
43
  def failure_message_when_negated
41
- super
44
+ message = super
45
+
46
+ message << ", but it does not respond to `include?`" unless actual.respond_to?(:include?) || message =~ /does not respond to/
47
+
48
+ message
42
49
  end # method
43
50
 
44
51
  private
45
52
 
46
53
  def perform_match(predicate, hash_subset_predicate)
54
+ return false unless actual.respond_to?(:include?)
55
+
47
56
  expected.__send__(predicate) do |expected_item|
48
57
  if comparing_proc?(expected_item)
49
58
  actual_matches_proc?(expected_item)
@@ -59,10 +68,6 @@ module RSpec::SleepingKingStudios::Matchers::BuiltIn
59
68
  end
60
69
  end
61
70
 
62
- def actual_collection_includes? expected_item
63
- (@includes = actual.respond_to?(:include?)) && super
64
- end # method actual_collection_includes?
65
-
66
71
  def actual_matches_proc? expected_item
67
72
  !!actual.detect(&expected_item)
68
73
  end # method actual_matches_proc?