From 25f42dbdb4eca05c95bb3a5053c5730939cb2abf Mon Sep 17 00:00:00 2001 From: Nathan Bardoux <4719911+nbcraft@users.noreply.github.com> Date: Mon, 3 Oct 2022 13:18:00 -0700 Subject: [PATCH] Fix PrepareDefault#callable! default check with false --- .../dispatchers/prepare_default.rb | 4 +-- spec/invalid_default_spec.rb | 34 +++++++++++++++++-- 2 files changed, 34 insertions(+), 4 deletions(-) diff --git a/lib/dry/initializer/dispatchers/prepare_default.rb b/lib/dry/initializer/dispatchers/prepare_default.rb index c8d7fe4..fb4ec2d 100644 --- a/lib/dry/initializer/dispatchers/prepare_default.rb +++ b/lib/dry/initializer/dispatchers/prepare_default.rb @@ -20,7 +20,7 @@ def call(default: nil, optional: nil, **options) private def callable!(default) - return unless default + return if default.nil? # handles false case better than `unless default` return default if default.respond_to?(:call) return callable(default.to_proc) if default.respond_to?(:to_proc) @@ -38,7 +38,7 @@ def check_arity!(default) def invalid!(default) raise TypeError, "The #{default.inspect} should be" \ - " either convertable to proc with no arguments," \ + " either convertible to proc with no arguments," \ " or respond to #call without arguments." end end diff --git a/spec/invalid_default_spec.rb b/spec/invalid_default_spec.rb index b53bc37..31389e8 100644 --- a/spec/invalid_default_spec.rb +++ b/spec/invalid_default_spec.rb @@ -1,6 +1,12 @@ # frozen_string_literal: true RSpec.describe "invalid default value assignment" do + shared_examples "it has a TypeError" do + it "raises TypeError" do + expect { subject }.to raise_error TypeError + end + end + subject do class Test::Foo extend Dry::Initializer @@ -9,7 +15,31 @@ class Test::Foo end end - it "raises TypeError" do - expect { subject }.to raise_error TypeError + it_behaves_like "it has a TypeError" + + context "when default is false" do + subject do + class Test::Foo + extend Dry::Initializer + + param :foo, default: false + end + end + + it_behaves_like "it has a TypeError" + end + + context "when default is a lambda returning false" do + subject do + class Test::Foo + extend Dry::Initializer + + param :foo, default: -> { false } + end + end + + it "does not raise TypeError" do + expect { subject }.not_to raise_error + end end end