optional 0.0.3 → 0.0.4

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.
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- optional (0.0.2)
4
+ optional (0.0.4)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
@@ -32,4 +32,8 @@ module None
32
32
  def to_s
33
33
  "None"
34
34
  end
35
+
36
+ def merge other
37
+ other
38
+ end
35
39
  end
@@ -14,7 +14,7 @@ module Option
14
14
  private
15
15
 
16
16
  def from_array(values)
17
- values.empty? ? None : Some[values.first]
17
+ values.empty? ? None : Some[*values]
18
18
  end
19
19
 
20
20
  def from_value(value)
@@ -7,13 +7,32 @@ module Option
7
7
  self
8
8
  end
9
9
 
10
+ def to_ary
11
+ to_a
12
+ end
13
+
14
+ def flatten
15
+ from_array to_ary.flatten
16
+ end
17
+
18
+ def juxt(*methods)
19
+ map { |v| methods.map { |m| v.send(m) } }
20
+ end
21
+
22
+ def map_through(*methods)
23
+ methods.reduce(self) { |acc, m| acc.map(&m) }
24
+ end
25
+
10
26
  def map
11
27
  from_array super
12
28
  end
13
29
  alias_method :collect, :map
14
- alias_method :flat_map, :map
15
30
  alias_method :collect_concat, :map
16
31
 
32
+ def flat_map(&block)
33
+ map(&block).flatten
34
+ end
35
+
17
36
  def detect
18
37
  from_value super
19
38
  end
@@ -28,8 +47,8 @@ module Option
28
47
  from_array super
29
48
  end
30
49
 
31
- def reject
32
- from_array super
50
+ def reject(*args, &block)
51
+ from_array to_a.reject(*args, &block)
33
52
  end
34
53
 
35
54
  def reduce(*args, &block)
@@ -7,8 +7,8 @@ class Some
7
7
  @value = value
8
8
  end
9
9
 
10
- def each
11
- yield value
10
+ def each &block
11
+ value.is_a?(Array) ? value.each(&block) : block.call(value)
12
12
  end
13
13
 
14
14
  def none?(&block)
@@ -35,8 +35,15 @@ class Some
35
35
  self
36
36
  end
37
37
 
38
+ def merge(other, &block)
39
+ other.match do |m|
40
+ m.some { |v| block.nil? ? Some[*value, v] : Some[block.call(value, v)] }
41
+ m.none { self }
42
+ end
43
+ end
44
+
38
45
  def to_s
39
- "Some[#{value}]"
46
+ "Some[#{value.inspect}]"
40
47
  end
41
48
 
42
49
  def self.[](*values)
@@ -1,6 +1,6 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = 'optional'
3
- s.version = '0.0.3'
3
+ s.version = '0.0.4'
4
4
  s.date = '2013-04-19'
5
5
  s.summary = "Optional values with pattern matching"
6
6
  s.description = "Make nils go bye bye with Options!"
@@ -41,4 +41,12 @@ describe None do
41
41
  it "prints as None" do
42
42
  None.to_s.should eq "None"
43
43
  end
44
+
45
+ it "can be merged with another none" do
46
+ None.merge(None).should be_none
47
+ end
48
+
49
+ it "can be merged with a some" do
50
+ None.merge(Some[cat]).should eq Some[cat]
51
+ end
44
52
  end
@@ -3,6 +3,12 @@ require 'spec_helper'
3
3
  describe Option::Enumerable do
4
4
 
5
5
  let (:cat) { Cat.new("MOGGIE!") }
6
+ let (:dog) { Dog.new("DOGGIE!") }
7
+
8
+ it "makes radek less sad :-(" do
9
+ Some[4].each { |e| e.should be_a Fixnum }
10
+ Some[4,5].each { |e| e.should be_a Fixnum }
11
+ end
6
12
 
7
13
  describe "#do" do
8
14
  it "allows ops with side effects to be performed using the value as part of a method chain" do
@@ -12,10 +18,16 @@ describe Option::Enumerable do
12
18
  end
13
19
  end
14
20
 
21
+ describe "#map_through" do
22
+ it "allows mapping through multiple methods" do
23
+ Some[cat, dog].map_through(:name, :chars, :first).should eq Some["M", "D"]
24
+ end
25
+ end
26
+
15
27
  describe "#map" do
16
28
 
17
29
  it "maps a some to a some" do
18
- Some[cat].map(&:name).should eq Some["MOGGIE!"]
30
+ Some[cat, dog].map(&:name).should eq Some["MOGGIE!", "DOGGIE!"]
19
31
  end
20
32
 
21
33
  it "also works for collect" do
@@ -43,6 +55,32 @@ describe Option::Enumerable do
43
55
  end
44
56
  end
45
57
 
58
+ describe "#flat_map" do
59
+ it 'works as expected over an array of options' do
60
+ [None, Some[3], None, Some[2]].flat_map do |x|
61
+ x.map(&:succ)
62
+ end.should eq [4,3]
63
+ end
64
+
65
+ it 'also works for a some that returns a nested some' do
66
+ x = Some[stub(y: Some[4])]
67
+ x.flat_map(&:y).should eq Some[4]
68
+ end
69
+ end
70
+
71
+ describe "#juxt" do
72
+ it "collects the results of calling the passed methods" do
73
+
74
+ Some[cat].juxt(:name, :class).should eq Some["MOGGIE!", Cat]
75
+
76
+ Some[1,2,3].juxt(:pred, :succ).should eq Some[[0, 2], [1, 3], [2, 4]]
77
+ end
78
+
79
+ it "also works for nil" do
80
+ None.juxt(:name, :class).should be_none
81
+ end
82
+ end
83
+
46
84
  describe "#detect" do
47
85
  it "returns none if called on a none" do
48
86
  None.detect{ |pet| pet.name == "MOGGIE!" }.should be_none
@@ -116,6 +154,10 @@ describe Option::Enumerable do
116
154
  it "also works as inject" do
117
155
  Some[4].inject(:+).should eq 4
118
156
  end
157
+
158
+ it "also works within the some" do
159
+ Some[3,4,5].reduce(:+).should eq 12
160
+ end
119
161
  end
120
162
 
121
163
  describe "#none?" do
@@ -131,4 +173,14 @@ describe Option::Enumerable do
131
173
  Some[4].reject(&:odd?).should eq Some[4]
132
174
  end
133
175
  end
176
+
177
+ describe "#flatten" do
178
+ it "flattens an array of options" do
179
+ Some[4].flatten.should eq Some[4]
180
+ [None, Some[4], Some[2], None].flatten.should eq [4,2]
181
+ Some[None, Some[4], Some[2], Some[1], None].flatten.should eq Some[4,2,1]
182
+ Some[None, None].flatten.should eq None
183
+ end
184
+ end
185
+
134
186
  end
@@ -45,4 +45,23 @@ describe Some do
45
45
  it "prints as Some[value]" do
46
46
  Some[4].to_s.should eq "Some[4]"
47
47
  end
48
+
49
+ describe '#merge' do
50
+ it 'can be merged with another some' do
51
+ Some[3].merge(Some[4]).should eq Some[3,4]
52
+ end
53
+
54
+ it 'can be merged with another merged some' do
55
+ Some[3, 4].merge(Some[5]).should eq Some[3, 4, 5]
56
+ end
57
+
58
+ it 'can be merged with another some using an operation' do
59
+ Some[3].merge(Some[4], &:+).should eq Some[7]
60
+ end
61
+
62
+ it 'can be merged with a none' do
63
+ Some[3].merge(None, &:+).should eq Some[3]
64
+ end
65
+ end
66
+
48
67
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: optional
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.3
4
+ version: 0.0.4
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors: