From c6b4e226666dd484ced2446225cc9fe565cb4f11 Mon Sep 17 00:00:00 2001 From: Michael Miller Date: Tue, 5 Feb 2019 12:47:50 -0700 Subject: [PATCH] Add `have_key` matcher --- README.md | 2 +- src/spectator/dsl/matcher_dsl.cr | 17 +++++++++++++++ src/spectator/matchers/have_key_matcher.cr | 25 ++++++++++++++++++++++ 3 files changed, 43 insertions(+), 1 deletion(-) create mode 100644 src/spectator/matchers/have_key_matcher.cr diff --git a/README.md b/README.md index 6580b95..96ed95f 100644 --- a/README.md +++ b/README.md @@ -114,7 +114,7 @@ In no particular order, features that have been implemented and are planned: - [X] Equality matchers - `eq`, `ne`, `be ==`, `be !=` - [X] Comparison matchers - `be <`, `be <=`, `be >`, `be >=`, `be_within[.of]`, `be_close` - [X] Type matchers - `be_a` - - [ ] Collection matchers - `contain`, `have`, `contain_exactly[.in_order|.in_any_order]`, `match_array[.in_order|.in_any_order]`, `start_with`, `end_with`, `be_empty`, `has_key`, `has_value`, `all`, `all_satisfy` + - [ ] Collection matchers - `contain`, `have`, `contain_exactly[.in_order|.in_any_order]`, `match_array[.in_order|.in_any_order]`, `start_with`, `end_with`, `be_empty`, `have_key`, `have_value`, `all`, `all_satisfy` - [X] Truthy matchers - `be`, `be_true`, `be_truthy`, `be_false`, `be_falsey`, `be_nil` - [ ] Error matchers - `raise_error` - [ ] Yield matchers - `yield_control[.times]`, `yield_with_args[.times]`, `yield_with_no_args[.times]`, `yield_successive_args` diff --git a/src/spectator/dsl/matcher_dsl.cr b/src/spectator/dsl/matcher_dsl.cr index 6d3a5f4..bb16312 100644 --- a/src/spectator/dsl/matcher_dsl.cr +++ b/src/spectator/dsl/matcher_dsl.cr @@ -395,6 +395,23 @@ module Spectator::DSL ::Spectator::Matchers::HaveMatcher.new({{expected.splat.stringify}}, {{expected}}) end + # Indicates that some set, such as a `Hash`, has a given key. + # The `has_key?` method is used for this check. + # + # Examples: + # ``` + # expect({foo: "bar"}).to have_key(:foo) + # expect({"lucky" => 7}).to have_key("lucky") + # ``` + macro have_key(expected) + ::Spectator::Matchers::HasKeyMatcher.new({{expected.stringify}}, {{expected}}) + end + + # ditto + macro has_key(expected) + have_key({{expected}}) + end + # Indicates that some value should have a set of attributes matching some conditions. # A list of named arguments are expected. # The names correspond to the attributes in the instance to check. diff --git a/src/spectator/matchers/have_key_matcher.cr b/src/spectator/matchers/have_key_matcher.cr new file mode 100644 index 0000000..7aeb283 --- /dev/null +++ b/src/spectator/matchers/have_key_matcher.cr @@ -0,0 +1,25 @@ +require "./value_matcher" + +module Spectator::Matchers + # Matcher that tests whether a `Hash` (or similar type) has a given key. + # The set is checked with the `has_key?` method. + struct HaveKeyMatcher(ExpectedType) < ValueMatcher(ExpectedType) + # Determines whether the matcher is satisfied with the value given to it. + # True is returned if the match was successful, false otherwise. + def match?(partial) + partial.actual.has_key?(expected) + end + + # Describes the condition that satisfies the matcher. + # This is informational and displayed to the end-user. + def message(partial) + "Expected #{partial.label} to have key #{label}" + end + + # Describes the condition that won't satsify the matcher. + # This is informational and displayed to the end-user. + def negated_message(partial) + "Expected #{partial.label} to not have key #{label}" + end + end +end