unexceptional 0.0.0 → 0.0.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 (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/unexceptional.rb +46 -22
  3. metadata +2 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 843955cd99c06a932f0594cc96ffa64488cd596a
4
- data.tar.gz: 38523fd3cd5282fa9bcd44ad8dd6048ed4f94089
3
+ metadata.gz: 2a58647357380db24012ea25d40324d424945a1b
4
+ data.tar.gz: 4bf5b4de747ad3997d294bed098d50ef93edf01b
5
5
  SHA512:
6
- metadata.gz: 4188134219b235eba0f0dc541adc67b360ac723f31d8be8e945202cb1afa9d4f088f3e2a760272da71be0b624fae767a7704995d580dc578441feb6865e085b1
7
- data.tar.gz: fd32c477e1a02bb7317fb51e87d1b9cc00cf956ab4cc3479bac8a93689968d07bf7ab75c351d65033e86a4534ab37b1eea97973276eff4d773eed19b69ac8c8c
6
+ metadata.gz: 81babf8e262b1eb60f465c1fc448b92743078ec02906926c8ac4d8b920151d9710d9b51118fc66c075b835d536f9562f837ca6aa83b41e008e57c48ed5759389
7
+ data.tar.gz: 4c98a50902b60294a98dd1b2b33bddd37c443c6bb42038ab6bd268849f439cb8503b5615c6163c89dcde189aa33cb7dab1f67432f185b0dbbbdadafa5f5e6e43
data/lib/unexceptional.rb CHANGED
@@ -1,21 +1,21 @@
1
1
  module Unexceptional
2
2
  class Result
3
- # Pass true or false and an error value. If the first argument is true, returns an ok
4
- # Result. If the first argument is false, returns an err Result wrapping the error
5
- # value.
3
+ # Pass true or false and an error value. If the first argument is `true`, returns an
4
+ # ok `Result`. If the first argument is false, returns an err `Result` wrapping the
5
+ # error value.
6
6
  def self.check(condition, error)
7
7
  condition ? ok : err(error)
8
8
  end
9
9
 
10
- # Returns a new Result respresenting failure. Optionally pass a wrapped result value.
10
+ # Returns a new `Result` respresenting failure. Accepts an optional error value.
11
11
  def self.err(err)
12
12
  new false, nil, err
13
13
  end
14
14
 
15
15
  # Pass a block and a collection. The block must accept a member of the collection and
16
- # return a Result.
16
+ # return a `Result`.
17
17
  #
18
- # If all members succeed, returns a Result wrapping all the mapped members:
18
+ # If all members succeed, returns a `Result` wrapping all the mapped members:
19
19
  #
20
20
  # Result.map([1, 2]) do |i|
21
21
  # Result.ok i * 2
@@ -47,14 +47,14 @@ module Unexceptional
47
47
  )
48
48
  end
49
49
 
50
- # Returns a new Result respresenting success. Optionally pass a wrapped result value.
50
+ # Returns a new `Result` respresenting success. Accepts an optional result value.
51
51
  def self.ok(val = nil)
52
52
  new true, val, nil
53
53
  end
54
54
 
55
- # Given a block, runs an ActiveRecord transaction. The block must return a Result. If
56
- # the Result is an error, rolls back the transaction. Either way, returns the Result.
57
- # You must call `require 'active_record` before you call this method.
55
+ # Given a block, runs an ActiveRecord transaction. The block must return a `Result`.
56
+ # If the `Result` is an error, rolls back the transaction. Either way, returns the
57
+ # `Result`. You must call `require 'active_record'` before you call this method.
58
58
  def self.transaction
59
59
  unless defined?(ActiveRecord)
60
60
  raise 'ActiveRecord is not defined'
@@ -70,8 +70,8 @@ module Unexceptional
70
70
  end
71
71
 
72
72
  # Tries to run a list of procs, aborting on the first failure, if any. Each proc must
73
- # return a Result--either ok or err. Aborts on the first err, if any, returning the
74
- # failed Result. If all procs return ok, returns the last Result.
73
+ # return a `Result`--either ok or err. Aborts on the first err, if any, returning the
74
+ # failed `Result`. If all procs return ok, returns the last `Result`.
75
75
  #
76
76
  # Result.try(
77
77
  # -> { Result.ok 2 },
@@ -93,18 +93,32 @@ module Unexceptional
93
93
  # ->((a, b)) { Result.ok a + b }
94
94
  # )
95
95
  # # => Result.ok(3)
96
+ #
97
+ # If you need to initialize a lot of objects along the way, passing them through the
98
+ # various procs via pattern-matching can be unwieldy. In that case, you can use the
99
+ # `#set` method along with instance variables:
100
+ #
101
+ # Result.try(
102
+ # -> { @a = Result.ok 2 },
103
+ # -> { @b = Result.ok @a * 3 },
104
+ # -> { Result.ok(@b * 4) }
105
+ # )
106
+ # # => Result.ok(24)
96
107
  def self.try(*procs)
97
108
  if procs.empty?
98
109
  raise 'Must past at least one proc to Result.try'
99
110
  end
111
+ ctx = TryContext.new
100
112
  procs.inject(nil) do |last_result, proc|
101
113
  if last_result.nil?
102
- proc.call
114
+ ctx.instance_exec(&proc)
115
+ elsif !last_result.is_a?(Result)
116
+ raise "Each proc in Result.try must return a Result, but proc returned #{last_result.inspect}"
103
117
  elsif last_result.ok?
104
118
  if proc.parameters.length == 0
105
- proc.call
119
+ ctx.instance_exec(&proc)
106
120
  else
107
- proc.call last_result.unwrap
121
+ ctx.instance_exec(last_result.unwrap, &proc)
108
122
  end
109
123
  else
110
124
  last_result
@@ -112,14 +126,14 @@ module Unexceptional
112
126
  end
113
127
  end
114
128
 
115
- # If this Result is an err, returns self:
129
+ # If this `Result` is an err, returns self:
116
130
  #
117
131
  # Result
118
132
  # .err(:uh_oh)
119
133
  # .and_then { 'This block never executes' }
120
134
  # # => Result.err(:uh_oh)
121
135
  #
122
- # If this Result is ok, then the behavior depends on what you passed to `and_then`:
136
+ # If this `Result` is ok, then the behavior depends on what you passed to `and_then`:
123
137
  #
124
138
  # # Passing a single argument:
125
139
  # Result
@@ -152,19 +166,19 @@ module Unexceptional
152
166
  end
153
167
  end
154
168
 
155
- # Yields this Result if this Result is an err.
169
+ # Yields this `Result` if this `Result` is an err.
156
170
  def if_err
157
171
  yield self.err if !@ok
158
172
  self
159
173
  end
160
174
 
161
- # Yields this Result if this Result is ok.
175
+ # Yields this `Result` if this Result is ok.
162
176
  def if_ok
163
177
  yield self.val if @ok
164
178
  self
165
179
  end
166
180
 
167
- # Returns the wrapped err value. Raises if this Result is ok.
181
+ # Returns the inner err value. Raises if this `Result` is ok.
168
182
  def err
169
183
  if !@ok
170
184
  @err
@@ -183,13 +197,13 @@ module Unexceptional
183
197
  @val = val
184
198
  @err = err
185
199
  end
186
-
200
+
187
201
  # Returns true if this Result is ok, false if this Result is an err.
188
202
  def ok?
189
203
  @ok
190
204
  end
191
205
 
192
- # Returns the wrapped success value. Raises if this Result is an err.
206
+ # Returns the inner success value. Raises if this Result is an err.
193
207
  def unwrap
194
208
  if @ok
195
209
  @val
@@ -197,5 +211,15 @@ module Unexceptional
197
211
  raise "Called #unwrap on error: #{@err.inspect}"
198
212
  end
199
213
  end
214
+ alias_method :ok, :unwrap
215
+ end
216
+
217
+ class TryContext #:nodoc:
218
+ def set(var, result)
219
+ if result.ok?
220
+ instance_variable_set '@' + var.to_s, result.unwrap
221
+ end
222
+ result
223
+ end
200
224
  end
201
225
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: unexceptional
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.0
4
+ version: 0.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jarrett Colby
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-09 00:00:00.000000000 Z
11
+ date: 2016-03-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: minitest