Skip to content

Commit

Permalink
Merge pull request #15 from Kaligo/feature/guard-passing-constructor
Browse files Browse the repository at this point in the history
Add ResultMonad::GuardClause#pass method which can be used to pass guards
  • Loading branch information
Drenmi authored Jul 7, 2021
2 parents ea79c14 + 3af906f commit 4831248
Show file tree
Hide file tree
Showing 7 changed files with 48 additions and 8 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
# Changelog

## 0.7.1

### New features

- Add `ResultMonad::GuardClause#pass` method which can be used to pass guards.

## 0.7.0

### New features
Expand Down
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -314,7 +314,7 @@ class Foo

def call
guard :bar_guard
guard { baz_guard }
qux = guard { baz_guard }
end

private
Expand All @@ -329,9 +329,9 @@ class Foo

def baz_guard
if qux?
error(errors: ["Qux failed."])
pass("Qux")
else
success
error(errors: ["Qux failed."])
end
end
end
Expand Down
10 changes: 9 additions & 1 deletion lib/stimpack/result_monad/guard_clause.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@

module Stimpack
module ResultMonad
PassResult = Result.new(:klass, :errors, :_value, keyword_init: true)

# This module adds a `#guard` method, which can be used inside a `#call`
# to declare a step which, if it fails, breaks the flow of the method and
# propagates the error result.
Expand Down Expand Up @@ -58,7 +60,13 @@ def guard(label = nil, &block)

raise GuardFailed, result if result.failed?

result
result.unwrap!
end

# A standardized result object which can be used to pass guards.
#
def pass(value = nil)
PassResult.new(klass: self.class, errors: nil, _value: value)
end

def self.included(klass)
Expand Down
9 changes: 9 additions & 0 deletions lib/stimpack/result_monad/result.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
module Stimpack
module ResultMonad
class Result < Struct
class UnwrapError < StandardError; end

def successful?
errors.nil?
end
Expand All @@ -11,6 +13,13 @@ def failed?
!successful?
end

def unwrap!
raise UnwrapError, "Can not unwrap a failed result." if failed?
return if klass.blank_result?

public_send(result_key)
end

def inspect
if successful?
"<#{klass}:successful #{result_key} : #{self[result_key].inspect}>"
Expand Down
2 changes: 1 addition & 1 deletion lib/stimpack/version.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# frozen_string_literal: true

module Stimpack
VERSION = "0.7.0"
VERSION = "0.7.1"
end
13 changes: 10 additions & 3 deletions spec/stimpack/result_monad/guard_clause_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,10 @@ def self.to_s

def call
guard :foo
guard { bar }
bar_result = guard { bar }
baz_result = guard { baz }

success(foo: "bar")
success(foo: bar_result + baz_result)
end

private
Expand All @@ -41,6 +42,10 @@ def foo
def bar
# Stubbed in test cases.
end

def baz
pass("Baz")
end
end
end

Expand All @@ -56,7 +61,8 @@ def bar
double(
Stimpack::ResultMonad::Result,
failed?: false,
errors: []
unwrap!: "Foo",
errors: nil
)
end

Expand Down Expand Up @@ -86,6 +92,7 @@ def bar
end

it { expect(instance.()).to be_successful }
it { expect(instance.().foo).to eq("FooBaz") }
end

context "when a guard fails" do
Expand Down
10 changes: 10 additions & 0 deletions spec/stimpack/result_monad/result_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,14 @@ def self.to_s
it { expect(instance.error_result(errors: "Oops!").inspect).to eq("<Foo:failed errors : \"Oops!\">") }
end
end

describe "#unwrap!" do
context "when result is successful" do
it { expect(instance.success_result(foo: "bar").unwrap!).to eq("bar") }
end

context "when result is failed" do
it { expect { instance.error_result(errors: "Oops!").unwrap! }.to raise_error(described_class::UnwrapError) }
end
end
end

0 comments on commit 4831248

Please sign in to comment.