deterministic 0.3.0 → 0.4.0
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.
- checksums.yaml +4 -4
- data/README.md +22 -7
- data/lib/deterministic/maybe.rb +35 -7
- data/lib/deterministic/version.rb +1 -1
- data/spec/lib/deterministic/maybe_spec.rb +37 -9
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 16ab904730d38a8b5b0e3b3a2e6a8e40f3bf68fa
|
4
|
+
data.tar.gz: 29b690c3723bfcce5c2cfe40fcc03db7059aee5f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8042eed9f812f6570fbfa18dfdb2f5245d53bbd2419dbc44fdefb7a760d5da575b19064ced2723bc82724fd4866767728951e73e89ccb3a157a1912db1d89690
|
7
|
+
data.tar.gz: 62e5ec295f1d1535b77cb271def694ecd8d22291e0ed39ad6f708539273cc8dca03ea81af277375f139690b1e912cef4da30f0a251d3063534bec27c9c7ac4cd
|
data/README.md
CHANGED
@@ -193,16 +193,30 @@ end # => Success(2)
|
|
193
193
|
The simplest NullObject wrapper there can be. It adds `#some?` and `#none?` to `Object` though.
|
194
194
|
|
195
195
|
```ruby
|
196
|
-
maybe
|
197
|
-
|
196
|
+
require 'deterministic/maybe' # you need to do this explicitly
|
197
|
+
Maybe(nil).foo # => None
|
198
|
+
Maybe(nil).foo.bar # => None
|
199
|
+
Mmaybe({a: 1})[:a] # => 1
|
198
200
|
|
199
|
-
|
201
|
+
Maybe(nil).none? # => true
|
202
|
+
Maybe({}).none? # => false
|
200
203
|
|
201
|
-
|
202
|
-
|
204
|
+
Maybe(nil).some? # => false
|
205
|
+
Maybe({}).some? # => true
|
206
|
+
```
|
207
|
+
|
208
|
+
## Mimic
|
209
|
+
|
210
|
+
If you want a custom NullObject which mimicks another class
|
211
|
+
|
212
|
+
```ruby
|
213
|
+
class Mimick
|
214
|
+
def test; end
|
215
|
+
end
|
203
216
|
|
204
|
-
|
205
|
-
|
217
|
+
null = Maybe.mimick(Mimick)
|
218
|
+
null.test # => None
|
219
|
+
null.foo # => NoMethodError
|
206
220
|
```
|
207
221
|
|
208
222
|
## Inspirations
|
@@ -211,6 +225,7 @@ maybe({}).some? # => true
|
|
211
225
|
* [Pithyless' rumblings](https://gist.github.com/pithyless/2216519)
|
212
226
|
* [either by rsslldnphy](https://github.com/rsslldnphy/either)
|
213
227
|
* [Functors, Applicatives, And Monads In Pictures](http://adit.io/posts/2013-04-17-functors,_applicatives,_and_monads_in_pictures.html)
|
228
|
+
* [Naught by avdi](https://github.com/avdi/naught/)
|
214
229
|
|
215
230
|
## Installation
|
216
231
|
|
data/lib/deterministic/maybe.rb
CHANGED
@@ -1,13 +1,40 @@
|
|
1
1
|
# The simplest NullObject there can be
|
2
2
|
class None
|
3
|
-
|
4
|
-
|
3
|
+
class << self
|
4
|
+
def method_missing(m, *args)
|
5
|
+
if m == :new
|
6
|
+
super
|
7
|
+
else
|
8
|
+
None.instance.send(m, *args)
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
def instance
|
13
|
+
@instance ||= new([])
|
14
|
+
end
|
15
|
+
|
16
|
+
def mimic(klas)
|
17
|
+
new(klas.instance_methods(false))
|
18
|
+
end
|
19
|
+
end
|
20
|
+
private_class_method :new
|
21
|
+
|
22
|
+
def initialize(methods)
|
23
|
+
@methods = methods
|
5
24
|
end
|
6
25
|
|
7
|
-
#
|
26
|
+
# implicit conversions
|
27
|
+
def to_str
|
28
|
+
''
|
29
|
+
end
|
30
|
+
|
31
|
+
def to_ary
|
32
|
+
[]
|
33
|
+
end
|
8
34
|
|
9
|
-
def method_missing(*args)
|
10
|
-
self
|
35
|
+
def method_missing(m, *args)
|
36
|
+
return self if respond_to?(m)
|
37
|
+
super
|
11
38
|
end
|
12
39
|
|
13
40
|
def none?
|
@@ -19,7 +46,8 @@ class None
|
|
19
46
|
end
|
20
47
|
|
21
48
|
def respond_to?(m)
|
22
|
-
true
|
49
|
+
return true if @methods.empty? || @methods.include?(m)
|
50
|
+
super
|
23
51
|
end
|
24
52
|
end
|
25
53
|
|
@@ -33,6 +61,6 @@ class Object
|
|
33
61
|
end
|
34
62
|
end
|
35
63
|
|
36
|
-
def
|
64
|
+
def Maybe(obj)
|
37
65
|
obj.nil? ? None.instance : obj
|
38
66
|
end
|
@@ -3,17 +3,45 @@ require 'deterministic/maybe'
|
|
3
3
|
|
4
4
|
describe 'maybe' do
|
5
5
|
it "does something" do
|
6
|
-
expect(
|
7
|
-
expect(
|
8
|
-
expect(
|
9
|
-
expect(
|
10
|
-
expect(
|
11
|
-
expect(
|
12
|
-
expect(
|
13
|
-
expect(
|
6
|
+
expect(Maybe(nil).foo).to be_none
|
7
|
+
expect(Maybe(nil).foo.bar.baz).to be_none
|
8
|
+
expect(Maybe(nil).fetch(:a)).to be_none
|
9
|
+
expect(Maybe(1)).to be_some
|
10
|
+
expect(Maybe({a: 1}).fetch(:a)).to eq 1
|
11
|
+
expect(Maybe({a: 1})[:a]).to eq 1
|
12
|
+
expect(Maybe("a").upcase).to eq "A"
|
13
|
+
expect(Maybe("a")).not_to be_none
|
14
14
|
end
|
15
15
|
|
16
|
-
it
|
16
|
+
it "None is a Singleton" do
|
17
|
+
expect(None.instance).to be_a None
|
18
|
+
expect { None.new }.to raise_error(NoMethodError, "private method `new' called for None:Class")
|
19
|
+
end
|
20
|
+
|
21
|
+
it "implicit conversions" do
|
22
|
+
null = Maybe(nil)
|
23
|
+
expect(null.to_str).to eq ""
|
24
|
+
expect(null.to_ary).to eq []
|
25
|
+
expect("" + null).to eq ""
|
26
|
+
|
27
|
+
a, b, c = null
|
28
|
+
expect(a).to be_nil
|
29
|
+
expect(b).to be_nil
|
30
|
+
expect(c).to be_nil
|
31
|
+
end
|
32
|
+
|
33
|
+
it "explicit conversions" do
|
17
34
|
expect(None.to_s).to eq 'None'
|
18
35
|
end
|
36
|
+
|
37
|
+
it "mimic, only return None on specific methods of another class" do
|
38
|
+
class MimicTest
|
39
|
+
def test
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
mimic = None.mimic(MimicTest)
|
44
|
+
expect(mimic.test).to be_none
|
45
|
+
expect { mimic.foo }.to raise_error(NoMethodError)
|
46
|
+
end
|
19
47
|
end
|