attribute_cartographer 0.0.5 → 0.0.6

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.
data/README CHANGED
@@ -21,32 +21,29 @@ Then run:
21
21
  include AttributeCartographer
22
22
 
23
23
  # one-way mapping
24
- map :a
25
- map :b, ->(v) { v.downcase }
26
- map :e, :f, ->(v) { v.downcase }
24
+ map "UnchangedKey" # map a single key, value untouched
25
+ map %w{ UnchangedKey1 UnchangedKey2 } # same as above, but for multiple in a single statement
27
26
 
28
- map :O, ->(k,v) { [k.downcase, v.downcase] }
27
+ map "SameKeyNewValue", ->(v) { v.downcase } # maps the key, using the lambda for the value
28
+ map %w{ SameKeyNewValue1 SameKeyNewValue2 }, ->(v) { v.upcase } # same as above, but for multiple in a single statement
29
29
 
30
- map [:i, :j, :k]
31
- map [:l, :m, :n], ->(v) { v.upcase }
30
+ map "OldKey", "new_key", ->(v) { v.downcase } # maps the left key to the right key, using the lambda for the value
31
+ map "DowncasedKeyAndValue", ->(k,v) { [k.downcase, v.downcase] } # maps the key and value using the lambda for both
32
+ map %w{ NewKeyAndValue1 NewKeyAndValue2 }, ->(k,v) { [k.downcase, v.downcase] } # same as the example above, but for multiple in a single statement
32
33
 
33
34
  # two-way mapping
34
- map :c, :d
35
- map :g, :h, ->(v) { v.downcase }, ->(v) { v.upcase }
35
+ map "AnotherOldKey", "another_new_key" # map the left key to the right key and vice-versa, value untouched
36
+ map "ThisKey", "to_this_key", ->(v) { v.downcase }, ->(v) { v.upcase } # map the left key to the right key with the first lambda,
37
+ # and the right key to the left key with the second lambda
36
38
 
37
- map [:P, :Q, :R], ->(k,v) { [k.downcase, v.downcase] }
38
39
  end
39
40
 
40
- Mapper.new(a: 2, b: "STRING")
41
+ Mapper.new("UnchangedKey" => "UnchangedValue", "OldKey" => "OldValue") # etc.
41
42
 
42
- For each mapping defined, an instance method is created that returns the mapped
43
- value. This can be mapped directly, with a lambda to map the value or key and
44
- value, with an explicit key mapping and lambda value mapping (with an optional
45
- reverse-value map lambda), with a directly-mapped array, a directly-mapped array
46
- with value mapping, or with an array with keys and values mapped with lambdas.
47
-
48
- Mapper#original_attributes is the original hash passed in
49
- Mapper#mapped_attributes is a hash representing the mapped keys and their mapped values
43
+ For each mapping defined, an entry in mapped_attributes will be made using the
44
+ logic defined in the mapping. You also get another method, original_attributes,
45
+ that retains the entire hash that was passed to #initialize, whether the keys
46
+ were mapped or not.
50
47
 
51
48
  == REQUIREMENTS
52
49
 
@@ -16,6 +16,7 @@ module AttributeCartographer
16
16
 
17
17
  passthrough = ->(v) { v }
18
18
  f1 ||= passthrough
19
+ f2 ||= passthrough
19
20
 
20
21
  if Array === from
21
22
  if f1.arity == 1
@@ -26,15 +27,14 @@ module AttributeCartographer
26
27
  else
27
28
  raise AttributeCartographer::InvalidArgumentError if to && f1.arity == 2
28
29
 
29
- to ||= from
30
- @mapper[from] = (f1.arity == 1 ? [to, f1] : f1)
31
- @mapper[to] = [from, (f2 ? f2 : passthrough)] if to != from
30
+ @mapper[from] = (f1.arity == 1 ? [to || from, f1] : f1)
31
+ @mapper[to] = [from, f2] if to && (f1 == f2 || f2 != passthrough)
32
32
  end
33
33
  end
34
34
  end
35
35
 
36
36
  module InstanceMethods
37
- def initialize attributes
37
+ def initialize attributes = {}
38
38
  @_original_attributes = attributes
39
39
  @_mapped_attributes = {}
40
40
 
@@ -67,7 +67,6 @@ module AttributeCartographer
67
67
  mapped_key, value = mapping.call(key, attributes[key])
68
68
  end
69
69
 
70
- self.send :define_singleton_method, mapped_key, ->{ value }
71
70
  @_mapped_attributes[mapped_key] = value
72
71
  end
73
72
  end
@@ -1,3 +1,3 @@
1
1
  module AttributeCartographer
2
- VERSION = "0.0.5" unless defined?(::AttributeCartographer::VERSION)
2
+ VERSION = "0.0.6" unless defined?(::AttributeCartographer::VERSION)
3
3
  end
@@ -12,96 +12,122 @@ describe AttributeCartographer do
12
12
  }
13
13
 
14
14
  describe "#initialize" do
15
- context "with nothing mapped" do
16
- it "does not try to map anything when map was not called" do
17
- lambda { klass.new(a: :b) }.should_not raise_error
18
- end
19
- end
20
15
 
21
- context "with attributes that don't match mapped values" do
22
- before { klass.map :a, :b, ->(v) { v + 1 } }
23
16
 
24
- it "doesn't map attributes when no mappable attribute was passed in" do
25
- lambda { klass.new(c: :d).b }.should raise_error(NoMethodError)
26
- end
17
+ it "doesn't require an argument" do
18
+ lambda { klass.new }.should_not raise_error
27
19
  end
28
20
  end
29
21
 
30
22
  describe "#original_attributes" do
31
- it "returns any attributes given to initialize" do
23
+ it "is the attributes given on initialize" do
32
24
  klass.new(a: :b).original_attributes.should == { a: :b }
33
25
  end
34
26
  end
35
27
 
36
28
  describe "#mapped_attributes" do
37
- before { klass.map :a, :b, ->(v) { v + 1 } }
29
+ subject { klass.new(attributes).mapped_attributes }
30
+
31
+ context "with no mapping" do
32
+ let(:attributes) { { "Attribute" => "Value" } }
33
+
34
+ it { should be_empty }
35
+ end
36
+
37
+ context "with a mapping" do
38
+ before { klass.map "Attribute", "attribute" }
39
+
40
+ context "and no attributes to map" do
41
+ let(:attributes) { {} }
42
+
43
+ it { should be_empty }
44
+ end
38
45
 
39
- it "returns any attributes mapped by the mapper" do
40
- klass.new(a: 1).mapped_attributes.should == { b: 2 }
46
+ context "and attributes to map" do
47
+ let(:attributes) { { "Attribute" => "Value" } }
48
+
49
+ it { should == { "attribute" => "Value" } }
50
+ end
41
51
  end
42
52
  end
43
53
 
44
54
  describe ".map" do
45
55
  context "with a single argument" do
46
56
  context "and no lambda" do
47
- before { klass.map :a }
57
+ before { klass.map "Attribute" }
48
58
 
49
- it "creates an instance method matching the key name" do
50
- klass.new(:a => :a_value).a.should == :a_value
59
+ it "creates an entry in mapped_attributes matching the key name" do
60
+ klass.new("Attribute" => "Value").mapped_attributes["Attribute"].should == "Value"
51
61
  end
52
62
  end
53
63
 
54
64
  context "and a 1-arity lambda" do
55
- before { klass.map :a, ->(v) { v.downcase } }
65
+ before { klass.map "Attribute", ->(v) { v.downcase } }
56
66
 
57
- it "creates an instance method matching the key name, mapping the value with the lambda" do
58
- klass.new(:a => "STRING").a.should == "string"
67
+ it "creates an entry in mapped_attributes matching the key name, mapping the value with the lambda" do
68
+ klass.new("Attribute" => "Value").mapped_attributes["Attribute"].should == "value"
59
69
  end
60
70
  end
61
71
 
62
72
  context "and a 2-arity lambda" do
63
- before { klass.map :A, ->(k,v) { [k.downcase, v.downcase] } }
73
+ before { klass.map "Attribute", ->(k,v) { [k.downcase, v.downcase] } }
64
74
 
65
- it "maps the key and value using the lambda and creates an instance method accordingly" do
66
- klass.new(A: "STRING").a.should == "string"
75
+ it "creates an entry in mapped_attributes using the lambda for the key and value" do
76
+ klass.new("Attribute" => "Value").mapped_attributes["attribute"].should == "value"
67
77
  end
68
78
 
69
79
  it "doesn't raise an error when the attributes hash is missing a mapped key" do
70
- lambda { klass.new(c: 2) }.should_not raise_error
80
+ lambda { klass.new("OtherAttribute" => "OtherValue") }.should_not raise_error
71
81
  end
72
82
  end
73
83
  end
74
84
 
75
85
  context "with two arguments" do
76
86
  context "and no lambda" do
77
- before { klass.map :a, :b }
87
+ before { klass.map "Attribute", "attribute" }
78
88
 
79
- it "maps the from to the to" do
80
- klass.new(:a => :a_value).mapped_attributes[:b].should == :a_value
89
+ context "with attributes matching the left key, passing the value through" do
90
+ it "maps the left key to the right key" do
91
+ klass.new("Attribute" => "Value").mapped_attributes["attribute"].should == "Value"
92
+ end
81
93
  end
82
94
 
83
- it "maps the to to the from" do
84
- klass.new(:b => :b_value).mapped_attributes[:a].should == :b_value
95
+ context "with attributes matching the right key, passing the value through" do
96
+ it "maps the right key to the left key" do
97
+ klass.new("attribute" => "Value").mapped_attributes["Attribute"].should == "Value"
98
+ end
85
99
  end
86
100
  end
87
101
 
88
102
  context "and a single lambda" do
89
- before { klass.map :a, :b, ->(v) { v.downcase } }
103
+ before { klass.map "Attribute", "attribute", ->(v) { v.downcase } }
90
104
 
91
- it "creates an instance method matching the key name, mapping the value with the lambda" do
92
- klass.new(:a => "STRING").b.should == "string"
105
+ context "with attributes matching the left key" do
106
+ it "maps the left key to the right key using the lambda to alter the value" do
107
+ klass.new("Attribute" => "Value").mapped_attributes["attribute"].should == "value"
108
+ end
109
+ end
110
+
111
+ context "with attributes matching the right key" do
112
+ it "doesn't map the right key as it's a one-way mapping" do
113
+ klass.new("attribute" => "value").mapped_attributes["Attribute"].should be_nil
114
+ end
93
115
  end
94
116
  end
95
117
 
96
118
  context "and two lambdas" do
97
- before { klass.map :a, :b, ->(v) { v.downcase }, ->(v) { v.upcase } }
119
+ before { klass.map "Attribute", "attribute", ->(v) { v.downcase }, ->(v) { v.upcase } }
98
120
 
99
- it "creates an instance method matching the second key name, mapping the value with the first lambda" do
100
- klass.new(a: "STRING").b.should == "string"
121
+ context "with attributes matching the left key" do
122
+ it "maps the left key to the right key, using the first lambda to map the value" do
123
+ klass.new("Attribute" => "Value").mapped_attributes["attribute"].should == "value"
124
+ end
101
125
  end
102
126
 
103
- it "creates an instance method matching the first key name, mapping the value with the second lambda" do
104
- klass.new(b: "string").a.should == "STRING"
127
+ context "with attributes matching the right key, passing the value through" do
128
+ it "maps the right key to the left key, using the second lambda to map the value" do
129
+ klass.new("attribute" => "value").mapped_attributes["Attribute"].should == "VALUE"
130
+ end
105
131
  end
106
132
  end
107
133
 
@@ -113,38 +139,25 @@ describe AttributeCartographer do
113
139
  end
114
140
 
115
141
  context "with an array" do
116
- context "with no lambda" do
117
- before { klass.map [:a, :b] }
142
+ let(:attributes) { { "Attribute1" => "Value1", "Attribute2" => "Value2" } }
143
+ subject { klass.new(attributes).mapped_attributes }
118
144
 
119
- it "creates a method named for each key" do
120
- instance = klass.new(a: :a_value, b: :b_value)
121
- instance.a.should == :a_value
122
- instance.b.should == :b_value
123
- end
145
+ context "and no lambda" do
146
+ before { klass.map %w{ Attribute1 Attribute2 } }
124
147
 
125
- it "doesn't raise an error when the attributes hash is missing a mapped key" do
126
- lambda { klass.new(a: :a_value).b }.should raise_error(NoMethodError)
127
- end
148
+ it { should == attributes }
128
149
  end
129
150
 
130
151
  context "and a 1-arity lambda" do
131
- before { klass.map [:a, :b], ->(v) { v.downcase } }
152
+ before { klass.map %w{ Attribute1 Attribute2 }, ->(v) { v.downcase } }
132
153
 
133
- it "creates a method named for each key using the lambda to map the values" do
134
- instance = klass.new(a: "STRING1", b: "STRING2")
135
- instance.a.should == "string1"
136
- instance.b.should == "string2"
137
- end
154
+ it { should == { "Attribute1" => "value1", "Attribute2" => "value2" } }
138
155
  end
139
156
 
140
157
  context "and a 2-arity lambda" do
141
- before { klass.map [:A, :B], ->(k,v) { [k.downcase, v.downcase] } }
158
+ before { klass.map %w{ Attribute1 Attribute2 }, ->(k,v) { [k.downcase, v.downcase] } }
142
159
 
143
- it "maps the key and value using the lambda and creates an instance method accordingly" do
144
- instance = klass.new(A: "ASTRING", B: "BSTRING")
145
- instance.a.should == "astring"
146
- instance.b.should == "bstring"
147
- end
160
+ it { should == { "attribute1" => "value1", "attribute2" => "value2" } }
148
161
  end
149
162
  end
150
163
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: attribute_cartographer
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 0.0.6
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,11 +9,11 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2011-05-25 00:00:00.000000000Z
12
+ date: 2011-06-16 00:00:00.000000000Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rspec
16
- requirement: &2153280180 !ruby/object:Gem::Requirement
16
+ requirement: &2153467360 !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ! '>='
@@ -21,7 +21,7 @@ dependencies:
21
21
  version: '2.5'
22
22
  type: :development
23
23
  prerelease: false
24
- version_requirements: *2153280180
24
+ version_requirements: *2153467360
25
25
  description: AttributeCartographer allows you to map an attributes hash into similarly
26
26
  or differently named methods, using an optional lambda to map the values as well.
27
27
  email:
@@ -62,7 +62,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
62
62
  version: '0'
63
63
  requirements: []
64
64
  rubyforge_project:
65
- rubygems_version: 1.8.2
65
+ rubygems_version: 1.8.4
66
66
  signing_key:
67
67
  specification_version: 3
68
68
  summary: Map an attributes hash to methods on Ruby object while transforming the values