rspec-expectations
rspec-expectations copied to clipboard
`end_with` takes the assumption that the receiver is a hash, or string.
[14] pry(<REMOVED>)> rtn.class # => Pathutil
[15] pry(<REMOVED>)> rtn.end_with?("/hello") # => true
[16] pry(<REMOVED>)> expect(rtn).to end_with("/hello")
RSpec::Expectations::ExpectationNotMetError
# => : expected #<Pathutil:/hello> to end with "/hello", but it cannot
# be indexed using #[]
start_with and end_with don't assume the receiver is a hash; they assume the receiver is an object that implements the [] indexing operator so that the matcher can directly access the elements at the start (using [0], [0, 5], etc for start_with) or at the end (using [-1], [-5, 5], etc for end_with). In fact, the start_with and end_with matchers don't work on hashes, as there internal ordering, where it exists (e.g. MRI 1.9+), is not exposed by the [] operator.
Anyhow, if you want it to work with an object of your own, you can implement [] on it, and the matcher should "just work". start_with and end_with have never checked a predicate like start_with? or end_with?. I think it would be reasonable to do so. Do you want to open a PR adding that?
Something like ?
# @api private
# @return [String]
def failure_message
super.tap do |msg|
if @actual_does_not_have_ordered_elements
msg << ", but it does not have ordered elements"
elsif !actual.respond_to?(:start_with?)
msg << ", but #{actual.inspect} does not respond to start_with?"
elsif !actual.respond_to?(:end_with?)
msg << ", but #{actual.inspect} does not respond to end_with?"
elsif !actual.respond_to?(:[])
msg << ", but it cannot be indexed using #[]"
end
end
end
@TravisSpangle - the fix for this is going to require a change the match logic (so that if the object responds to the appropriate predicate method, it is used), as well as a change to failure_message so that when the predicate approach was used, the failure message mentions it.
(And sorry about the delayed response...)
Closing due to inactivity during the monorepo migration, and I feel the original access modifier reasoning still stands