matic 0.1.1 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG.md CHANGED
@@ -1,3 +1,8 @@
1
+ = 0.2.0
2
+
3
+ * Changed Matic.field to Matic.fields
4
+ * Added support for short field names
5
+
1
6
  = 0.1.0
2
7
 
3
8
  * Initial release
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- matic (0.1.1)
4
+ matic (0.2.0)
5
5
  activemodel (~> 3.0.0)
6
6
  activesupport (~> 3.0.0)
7
7
  mongomatic (~> 0.6.0)
data/README.md CHANGED
@@ -1,31 +1,54 @@
1
1
  # Matic
2
2
 
3
- Matic adds attribute accessors and dirty tracking to Mongomatic.
3
+ Matic adds attribute accessors and dirty tracking to Mongomatic and
4
+ optionally shortens field names to optimize storing and indexing.
4
5
 
5
6
  ## Examples
6
7
 
7
8
  class Person < Mongomatic::Base
8
9
  include Matic
9
10
 
10
- field :name
11
+ fields :first_name,
12
+ :last_name
11
13
  end
12
14
 
13
15
  person = Person.new
14
- person.name = "John Doe"
16
+ person.first_name = "John"
15
17
 
16
- person.name_changed?
18
+ person.first_name_changed?
17
19
  => true
18
20
 
19
- person.changes["name"]
20
- => [nil, "John Doe"]
21
+ person.changes["first_name"]
22
+ => [nil, "John"]
21
23
 
22
24
  person.insert
23
25
 
24
- person.name_changed?
26
+ person.first_name_changed?
25
27
  => false
26
28
 
27
- person.changes["name"]
29
+ person.changes["first_name"]
28
30
  => nil
29
31
 
30
- person.previous_changes["name"]
31
- => [nil, "John Doe"]
32
+ person.previous_changes["first_name"]
33
+ => [nil, "John"]
34
+
35
+ This is a model with short field names:
36
+
37
+ class Person < Mongomatic::Base
38
+ include Matic
39
+
40
+ fields :first_name => 'f',
41
+ :last_name => 'l'
42
+
43
+ end
44
+
45
+ person = Person.new
46
+
47
+ person.first_name = "John"
48
+ person.last_name = "Doe"
49
+
50
+ person.insert
51
+ => #<Person:0x000001023cea30
52
+ @doc=
53
+ {"f"=>"John", "l" => "Doe", "_id"=>BSON::ObjectId('4cdd1b0c6aa2b112e1000001')}
54
+ ...>
data/lib/matic.rb CHANGED
@@ -9,33 +9,31 @@ module Matic
9
9
  self.name.tableize
10
10
  end
11
11
 
12
- def field(attr_name)
13
- generate_attribute_methods(attr_name)
12
+ def fields(*attrs)
13
+ if attrs.first.is_a? Hash
14
+ attrs.first.each { |k, v| define_accessor(k, v) }
15
+ define_attribute_methods(attrs.first.keys)
16
+ else
17
+ attrs.each { |k, v| define_accessor(k, v) }
18
+ define_attribute_methods(attrs)
19
+ end
20
+ end
21
+
22
+ private
23
+
24
+ def define_accessor(attr_name, attr_field=nil)
25
+ attr_field ||= attr_name
14
26
 
15
27
  define_method(attr_name) do
16
- self[attr_name.to_s]
28
+ self[attr_field.to_s]
17
29
  end
18
30
 
19
31
  define_method("#{attr_name}=") do |val|
20
- unless val == self[attr_name.to_s]
32
+ unless val == self[attr_field.to_s]
21
33
  eval("#{attr_name}_will_change!")
22
34
  end
23
35
 
24
- self[attr_name.to_s] = val
25
- end
26
- end
27
-
28
- private
29
-
30
- def generate_attribute_methods(attr_name)
31
- attribute_method_matchers.each do |matcher|
32
- method_name = matcher.method_name(attr_name)
33
-
34
- generated_attribute_methods.module_eval <<-STR, __FILE__, __LINE__ + 1
35
- def #{method_name}(*args)
36
- send(:#{matcher.method_missing_target}, '#{attr_name}', *args)
37
- end
38
- STR
36
+ self[attr_field.to_s] = val
39
37
  end
40
38
  end
41
39
  end
@@ -44,18 +42,10 @@ module Matic
44
42
  clear_changes if super
45
43
  end
46
44
 
47
- def insert!(opts={})
48
- insert(opts.merge(:safe => true))
49
- end
50
-
51
45
  def update(opts={}, update_doc=@doc)
52
46
  clear_changes if super
53
47
  end
54
48
 
55
- def update!(opts={}, update_doc=@doc)
56
- update(opts.merge(:safe => true), update_doc)
57
- end
58
-
59
49
  def save
60
50
  is_new ? insert : update
61
51
  end
data/lib/matic/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Matic
2
- VERSION = "0.1.1"
2
+ VERSION = "0.2.0"
3
3
  end
data/spec/matic_spec.rb CHANGED
@@ -1,137 +1,184 @@
1
1
  require "spec_helper"
2
2
 
3
- describe "A matic model" do
3
+ describe "a mongomatic model that includes matic" do
4
4
 
5
5
  let(:person) { Person.new }
6
+ let(:book) { Book.new }
6
7
 
7
8
  it "has a collection first_name" do
8
9
  person.class.collection_name.should eql "people"
9
10
  end
10
11
 
11
- describe ".field" do
12
- it "defines a getter" do
13
- person["first_name"] = "John"
12
+ describe ".fields" do
14
13
 
15
- person.first_name.should eql "John"
16
- lambda { person.foo }.should raise_error NoMethodError
17
- end
14
+ context "when it is passed an array" do
18
15
 
19
- it "defines a setter" do
20
- person.first_name = "John"
16
+ it "defines a getter" do
17
+ person["first_name"] = "John"
21
18
 
22
- person["first_name"].should eql "John"
23
- lambda { person.foo= "bar" }.should raise_error NoMethodError
24
- end
25
- end
19
+ person.first_name.should eql "John"
20
+ lambda { person.foo }.should raise_error NoMethodError
21
+ end
22
+
23
+ it "defines a setter" do
24
+ person.first_name = "John"
26
25
 
27
- context "dirty tracking" do
26
+ person["first_name"].should eql "John"
27
+ lambda { person.foo= "bar" }.should raise_error NoMethodError
28
+ end
29
+
30
+ end
28
31
 
29
- shared_examples_for "a dirty-tracking command" do
32
+ context "when it is passed a hash" do
30
33
 
31
- it "marks a current change as previous" do
32
- person.first_name_changed?.should be_false
33
- person.previous_changes["first_name"].should eql [nil, "John"]
34
+ it "defines a getter" do
35
+ book["i"] = "9780485113358"
36
+ book.isbn.should eql "9780485113358"
34
37
 
35
- person.last_name_changed?.should be_false
36
- person.previous_changes["last_name"].should eql [nil, "Doe"]
38
+ book["a"] = ["Gilles Deleuze"]
39
+ book.authors.should eql ["Gilles Deleuze"]
37
40
  end
38
41
 
39
- it "does callbacks" do
40
- person.instance_variable_get(:@called_back).should be_true
42
+ it "defines a setter" do
43
+ book.isbn = "9780485113358"
44
+ book["i"].should eql "9780485113358"
45
+
46
+ book.authors = ["Gilles Deleuze"]
47
+ book["a"].should eql ["Gilles Deleuze"]
41
48
  end
42
49
 
50
+ it "stores documents with short field names" do
51
+ book.isbn = "9780485113358"
52
+ book.insert
53
+
54
+ book.instance_variable_get(:@doc).should have_key 'i'
55
+ end
43
56
  end
44
57
 
45
- shared_examples_for "a dirty object" do
58
+ end
46
59
 
47
- it "tells if an attribute changed" do
48
- person.first_name_changed?.should be_true
49
- person.last_name_changed?.should be_true
50
- end
60
+ shared_examples_for "a dirty-tracking command" do
51
61
 
52
- it "remembers changes to an attribute" do
53
- person.changes["first_name"].should eql [nil, "John"]
54
- person.changes["last_name"].should eql [nil, "Doe"]
55
- end
62
+ it "marks a current change as previous" do
63
+ person.first_name_changed?.should be_false
64
+ person.previous_changes["first_name"].should eql [nil, "John"]
56
65
 
66
+ person.last_name_changed?.should be_false
67
+ person.previous_changes["last_name"].should eql [nil, "Doe"]
57
68
  end
58
69
 
59
- context "when object is new" do
70
+ it "does callbacks" do
71
+ person.instance_variable_get(:@called_back).should be_true
72
+ end
60
73
 
61
- before do
62
- person.first_name = "John"
63
- person.last_name = "Doe"
64
- end
74
+ end
75
+
76
+ describe "a dirty-tracking setter" do
65
77
 
66
- it_behaves_like "a dirty object"
78
+ context "when an attribute is set" do
67
79
 
68
- describe "#insert" do
80
+ context "and its value has changed" do
69
81
 
70
- before { person.insert }
82
+ before do
83
+ person.first_name = "John"
84
+ end
71
85
 
72
- it_behaves_like "a dirty-tracking command"
86
+ it "marks the attribute as changed" do
87
+ person.first_name_changed?.should be_true
88
+ end
89
+
90
+ it "remembers changes to the attribute" do
91
+ person.changes["first_name"].should eql [nil, "John"]
92
+ end
73
93
 
74
94
  end
75
95
 
76
- describe "#insert!" do
96
+ context "and its value has not changed" do
77
97
 
78
- before { person.insert! }
98
+ before do
99
+ person.first_name = nil
100
+ end
79
101
 
80
- it_behaves_like "a dirty-tracking command"
102
+ it "does not mark the attribute as changed" do
103
+ person.first_name_changed?.should be_false
104
+ end
81
105
 
82
106
  end
83
107
 
84
- describe "#save" do
108
+ end
85
109
 
86
- before { person.save }
110
+ end
87
111
 
88
- it_behaves_like "a dirty-tracking command"
112
+ context "when object is new" do
89
113
 
90
- end
114
+ before do
115
+ person.first_name = "John"
116
+ person.last_name = "Doe"
117
+ end
118
+
119
+ describe "#insert" do
120
+
121
+ before { person.insert }
122
+
123
+ it_behaves_like "a dirty-tracking command"
91
124
 
92
125
  end
93
126
 
94
- context "when object is not new" do
127
+ describe "#insert!" do
95
128
 
96
- before do
97
- person.insert
98
- person.instance_variable_set(:@called_back, false)
99
- person.first_name = "John"
100
- person.last_name = "Doe"
101
- end
129
+ before { person.insert! }
102
130
 
103
- it_behaves_like "a dirty object"
131
+ it_behaves_like "a dirty-tracking command"
104
132
 
105
- describe "#update" do
133
+ end
106
134
 
107
- before { person.update }
135
+ describe "#save" do
108
136
 
109
- it_behaves_like "a dirty-tracking command"
137
+ before { person.save }
110
138
 
111
- end
139
+ it_behaves_like "a dirty-tracking command"
112
140
 
113
- describe "#update!" do
141
+ end
114
142
 
115
- before { person.update! }
143
+ end
116
144
 
117
- it_behaves_like "a dirty-tracking command"
145
+ context "when object is not new" do
118
146
 
119
- end
147
+ before do
148
+ person.insert
149
+ person.instance_variable_set(:@called_back, false)
150
+ person.first_name = "John"
151
+ person.last_name = "Doe"
152
+ end
153
+
154
+ describe "#update" do
155
+
156
+ before { person.update }
157
+
158
+ it_behaves_like "a dirty-tracking command"
120
159
 
121
160
  end
122
161
 
123
- context "when object is not valid" do
162
+ describe "#update!" do
124
163
 
125
- before do
126
- person.stub!(:valid?).and_return(false)
127
- person.first_name = "John"
128
- end
164
+ before { person.update! }
129
165
 
130
- it "does not clear changes" do
131
- person.save
132
- person.first_name_changed?.should be_true
133
- end
166
+ it_behaves_like "a dirty-tracking command"
167
+
168
+ end
169
+
170
+ end
171
+
172
+ context "when an invalid object is saved" do
173
+
174
+ before do
175
+ person.stub!(:valid?).and_return(false)
176
+ person.first_name = "John"
177
+ end
134
178
 
179
+ it "does not clear changes" do
180
+ person.save
181
+ person.first_name_changed?.should be_true
135
182
  end
136
183
 
137
184
  end
@@ -0,0 +1,8 @@
1
+ class Book < Mongomatic::Base
2
+ include Matic
3
+
4
+ fields :title => 't',
5
+ :authors => 'a',
6
+ :publisher => 'p',
7
+ :isbn => 'i'
8
+ end
@@ -1,8 +1,8 @@
1
1
  class Person < Mongomatic::Base
2
2
  include Matic
3
3
 
4
- field :first_name
5
- field :last_name
4
+ fields :first_name,
5
+ :last_name
6
6
 
7
7
  private
8
8
 
metadata CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 0
7
- - 1
8
- - 1
9
- version: 0.1.1
7
+ - 2
8
+ - 0
9
+ version: 0.2.0
10
10
  platform: ruby
11
11
  authors:
12
12
  - Hakan Ensari
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2010-11-11 00:00:00 +00:00
18
+ date: 2010-11-12 00:00:00 +00:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
@@ -130,6 +130,7 @@ files:
130
130
  - lib/matic/version.rb
131
131
  - matic.gemspec
132
132
  - spec/matic_spec.rb
133
+ - spec/models/book.rb
133
134
  - spec/models/person.rb
134
135
  - spec/spec_helper.rb
135
136
  - spec/support/mongomatic.rb
@@ -168,6 +169,7 @@ specification_version: 3
168
169
  summary: Mongomatic with attribute accessors and dirty tracking
169
170
  test_files:
170
171
  - spec/matic_spec.rb
172
+ - spec/models/book.rb
171
173
  - spec/models/person.rb
172
174
  - spec/spec_helper.rb
173
175
  - spec/support/mongomatic.rb