og 0.20.0 → 0.21.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (53) hide show
  1. data/CHANGELOG +796 -664
  2. data/INSTALL +24 -24
  3. data/README +39 -32
  4. data/Rakefile +41 -42
  5. data/benchmark/bench.rb +36 -36
  6. data/doc/AUTHORS +15 -12
  7. data/doc/LICENSE +3 -3
  8. data/doc/RELEASES +311 -243
  9. data/doc/config.txt +1 -1
  10. data/examples/mysql_to_psql.rb +15 -15
  11. data/examples/run.rb +92 -92
  12. data/install.rb +7 -17
  13. data/lib/og.rb +76 -75
  14. data/lib/og/collection.rb +203 -160
  15. data/lib/og/entity.rb +168 -169
  16. data/lib/og/errors.rb +5 -5
  17. data/lib/og/manager.rb +179 -178
  18. data/lib/og/mixin/hierarchical.rb +107 -107
  19. data/lib/og/mixin/optimistic_locking.rb +36 -36
  20. data/lib/og/mixin/orderable.rb +148 -148
  21. data/lib/og/mixin/timestamped.rb +8 -8
  22. data/lib/og/mixin/tree.rb +124 -124
  23. data/lib/og/relation.rb +237 -213
  24. data/lib/og/relation/belongs_to.rb +5 -5
  25. data/lib/og/relation/has_many.rb +60 -58
  26. data/lib/og/relation/joins_many.rb +93 -47
  27. data/lib/og/relation/refers_to.rb +25 -21
  28. data/lib/og/store.rb +210 -207
  29. data/lib/og/store/filesys.rb +79 -79
  30. data/lib/og/store/kirby.rb +263 -258
  31. data/lib/og/store/memory.rb +261 -261
  32. data/lib/og/store/mysql.rb +288 -284
  33. data/lib/og/store/psql.rb +261 -244
  34. data/lib/og/store/sql.rb +873 -720
  35. data/lib/og/store/sqlite.rb +177 -175
  36. data/lib/og/store/sqlserver.rb +204 -214
  37. data/lib/og/types.rb +1 -1
  38. data/lib/og/validation.rb +57 -57
  39. data/lib/vendor/mysql.rb +376 -376
  40. data/lib/vendor/mysql411.rb +10 -10
  41. data/test/og/mixin/tc_hierarchical.rb +59 -59
  42. data/test/og/mixin/tc_optimistic_locking.rb +40 -40
  43. data/test/og/mixin/tc_orderable.rb +67 -67
  44. data/test/og/mixin/tc_timestamped.rb +19 -19
  45. data/test/og/store/tc_filesys.rb +46 -46
  46. data/test/og/tc_inheritance.rb +81 -81
  47. data/test/og/tc_join.rb +67 -0
  48. data/test/og/tc_polymorphic.rb +49 -49
  49. data/test/og/tc_relation.rb +57 -30
  50. data/test/og/tc_select.rb +49 -0
  51. data/test/og/tc_store.rb +345 -337
  52. data/test/og/tc_types.rb +11 -11
  53. metadata +11 -18
@@ -9,152 +9,176 @@ module Og
9
9
 
10
10
  class Relation
11
11
 
12
- attr_accessor :options
13
-
14
- attr_accessor :is_polymorphic
15
-
16
- # A generalized initialize method for all relations.
17
- # Contains common setup code.
18
-
19
- def initialize(args, options = {})
20
- @options = options
21
- @options.update(args.pop) if args.last.is_a?(Hash)
22
-
23
- if args.empty? or (not (args.last.is_a?(Class) or args.last.is_a?(Symbol)))
24
- raise 'Class of target not defined'
25
- end
26
-
27
- @options[:target_class] = args.pop
28
-
29
- if target_class == Object
30
- # If the target class is just an Object mark that class
31
- # as a polymorphic parent class.
32
- # This class acts as template
33
- # to generate customized versions of this class.
34
-
35
- owner_class.meta(:polymorphic, owner_class)
36
- elsif target_class.respond_to?(:metadata) and target_class.metadata.polymorphic
37
- # If the target class is polymorphic, create a specialized
38
- # version of the class enclosed in the owner namespace.
39
-
40
- target_dm = target_class.to_s.demodulize
41
- owner_class.module_eval %{
42
- class #{owner_class}::#{target_dm} < #{target_class}
43
- end
44
- }
45
- eval %{
46
- @options[:target_class] = #{owner_class}::#{target_dm}
47
- }
48
- end
49
-
50
- target_name = if collection
51
- :target_plural_name
52
- else
53
- :target_singular_name
54
- end
55
-
56
- # Inflect the relation name.
57
-
58
- unless args.empty?
59
- @options[target_name] = args.first
60
- else
61
- @options[target_name] = if collection
62
- target_class.to_s.demodulize.underscore.downcase.plural.intern
63
- else
64
- target_class.to_s.demodulize.underscore.downcase.intern
65
- end
66
- end
67
-
68
- @options[:name] = options[target_name]
69
- end
70
-
71
- def [](key)
72
- @options[key]
73
- end
74
-
75
- def []=(key, val)
76
- @options[key] = val
77
- end
78
-
79
- # Is the relation polymorphic?
80
-
81
- def polymorphic?
82
- target_class == Object
83
- end
84
-
85
- #--
86
- # gmosx, TODO: remove, this is not really needed.
87
- #++
88
-
89
- def resolve_options
90
- @options[:owner_pk], @options[:owner_pkclass] = owner_class.primary_key
91
- if target_class.respond_to?(:primary_key)
92
- @options[:target_pk], @options[:target_pkclass] = target_class.primary_key
93
- end
94
- end
95
-
96
- # To avoid forward declarations, references to undefined
97
- # (at the time of the creation of the relation) classes are
98
- # stored as symbols. These symbols are resolved by this
99
- # method.
100
- #--
101
- # FIXME: do something more elegant here.
102
- #++
103
-
104
- def resolve_target
105
- if target_class.is_a?(Symbol)
106
- c = owner_class.name.dup
107
- c = "::" + c unless c =~ /::/
108
- c.gsub!(/::.*$/, '::')
109
- c << target_class.to_s
110
- begin
111
- klass = constant(c)
112
- rescue
113
- unless c == target_class
114
- c = target_class
115
- retry
116
- end
117
- end
118
- @options[:target_class] = klass
119
- end
120
- end
121
-
122
- # Resolve a polymorphic target class.
123
- # Overrided in subclasses.
124
-
125
- def resolve_polymorphic
126
- end
127
-
128
- # This method is implemented in subclasses.
129
-
130
- def enchant
131
- end
132
-
133
- # Access the hash values as methods.
134
-
135
- def method_missing(sym, *args)
136
- return @options[sym]
137
- end
138
-
139
- class << self
140
-
141
- def resolve(klass, action)
142
- if klass.__meta[:relations]
143
- for relation in klass.__meta[:relations]
144
- relation.send(action)
145
- end
146
- end
147
- end
148
-
149
- def enchant(klass)
150
- if klass.__meta[:relations]
151
- for relation in klass.__meta[:relations]
152
- relation.enchant unless relation.target_class == Object
153
- end
154
- end
155
- end
156
-
157
- end
12
+ attr_accessor :options
13
+
14
+ attr_accessor :is_polymorphic
15
+
16
+ # A generalized initialize method for all relations.
17
+ # Contains common setup code.
18
+
19
+ def initialize(args, options = {})
20
+ @options = options
21
+ @options.update(args.pop) if args.last.is_a?(Hash)
22
+
23
+ if args.empty? or (not (args.last.is_a?(Class) or args.last.is_a?(Symbol)))
24
+ raise 'Class of target not defined'
25
+ end
26
+
27
+ @options[:target_class] = args.pop
28
+
29
+ if target_class == Object
30
+ # If the target class is just an Object mark that class
31
+ # as a polymorphic parent class.
32
+ # This class acts as template
33
+ # to generate customized versions of this class.
34
+
35
+ owner_class.meta(:polymorphic, owner_class)
36
+ elsif target_class.respond_to?(:metadata) and target_class.metadata.polymorphic
37
+ # If the target class is polymorphic, create a specialized
38
+ # version of the class enclosed in the owner namespace.
39
+
40
+ target_dm = target_class.to_s.demodulize
41
+ owner_class.module_eval %{
42
+ class #{owner_class}::#{target_dm} < #{target_class}
43
+ end
44
+ }
45
+ eval %{
46
+ @options[:target_class] = #{owner_class}::#{target_dm}
47
+ }
48
+ end
49
+
50
+ target_name = if collection
51
+ :target_plural_name
52
+ else
53
+ :target_singular_name
54
+ end
55
+
56
+ # Inflect the relation name.
57
+
58
+ unless args.empty?
59
+ @options[target_name] = args.first
60
+ else
61
+ @options[target_name] = if collection
62
+ target_class.to_s.demodulize.underscore.downcase.plural.intern
63
+ else
64
+ target_class.to_s.demodulize.underscore.downcase.intern
65
+ end
66
+ end
67
+
68
+ @options[:name] = options[target_name]
69
+ end
70
+
71
+ def [](key)
72
+ @options[key]
73
+ end
74
+
75
+ def []=(key, val)
76
+ @options[key] = val
77
+ end
78
+
79
+ # Is the relation polymorphic?
80
+
81
+ def polymorphic?
82
+ target_class == Object
83
+ end
84
+
85
+ #--
86
+ # gmosx, TODO: remove, this is not really needed.
87
+ #++
88
+
89
+ def resolve_options
90
+ @options[:owner_pk], @options[:owner_pkclass] = owner_class.primary_key
91
+ if target_class.respond_to?(:primary_key)
92
+ @options[:target_pk], @options[:target_pkclass] = target_class.primary_key
93
+ end
94
+ end
95
+
96
+ # To avoid forward declarations, references to undefined
97
+ # (at the time of the creation of the relation) classes are
98
+ # stored as symbols. These symbols are resolved by this
99
+ # method.
100
+ #--
101
+ # FIXME: do something more elegant here.
102
+ #++
103
+
104
+ def resolve_symbol(sym, owner_class)
105
+ c = owner_class.name.dup
106
+ c = "::" + c unless c =~ /::/
107
+ c.gsub!(/::.*$/, '::')
108
+ c << sym.to_s
109
+ begin
110
+ return constant(c)
111
+ rescue
112
+ unless c == sym
113
+ c = sym
114
+ retry
115
+ end
116
+ end
117
+ end
118
+
119
+ def resolve_target
120
+ if target_class.is_a?(Symbol)
121
+ klass = resolve_symbol(target_class, owner_class)
122
+ @options[:target_class] = klass
123
+ end
124
+ end
125
+
126
+ =begin
127
+ def resolve_target
128
+ if target_class.is_a?(Symbol)
129
+ c = owner_class.name.dup
130
+ c = "::" + c unless c =~ /::/
131
+ c.gsub!(/::.*$/, '::')
132
+ c << target_class.to_s
133
+ begin
134
+ klass = constant(c)
135
+ rescue
136
+ unless c == target_class
137
+ c = target_class
138
+ retry
139
+ end
140
+ end
141
+ @options[:target_class] = klass
142
+ end
143
+ end
144
+ =end
145
+
146
+ # Resolve a polymorphic target class.
147
+ # Overrided in subclasses.
148
+
149
+ def resolve_polymorphic
150
+ end
151
+
152
+ # This method is implemented in subclasses.
153
+
154
+ def enchant
155
+ end
156
+
157
+ # Access the hash values as methods.
158
+
159
+ def method_missing(sym, *args)
160
+ return @options[sym]
161
+ end
162
+
163
+ class << self
164
+
165
+ def resolve(klass, action)
166
+ if klass.__meta[:relations]
167
+ for relation in klass.__meta[:relations]
168
+ relation.send(action)
169
+ end
170
+ end
171
+ end
172
+
173
+ def enchant(klass)
174
+ if klass.__meta[:relations]
175
+ for relation in klass.__meta[:relations]
176
+ relation.enchant unless relation.target_class == Object
177
+ end
178
+ end
179
+ end
180
+
181
+ end
158
182
 
159
183
  end
160
184
 
@@ -162,73 +186,73 @@ end
162
186
  # relations.
163
187
 
164
188
  module RelationMacros
165
- def self.append_features(base)
166
- super
167
- base.extend(ClassMethods)
168
- end
169
-
170
- module ClassMethods
171
-
172
- # === Examples
173
- #
174
- # belongs_to Article
175
- # belongs_to :article, Article
176
- # belongs_to :article, Article, :view => 'lala'
177
-
178
- def belongs_to(*args)
179
- require 'og/relation/belongs_to'
180
- meta :relations, Og::BelongsTo.new(args, :owner_class => self)
181
- end
182
-
183
- # === Examples
184
- #
185
- # refers_to Topic
186
-
187
- def refers_to(*args)
188
- require 'og/relation/refers_to'
189
- meta :relations, Og::RefersTo.new(args, :owner_class => self)
190
- end
191
-
192
- # === Examples
193
- #
194
- # has_one User
195
-
196
- def has_one(*args)
197
- require 'og/relation/has_one'
198
- meta :relations, Og::HasOne.new(args, :owner_class => self)
199
- end
200
-
201
- # === Examples
202
- #
203
- # has_many Comment
204
- # has_many :comments, Comment
205
-
206
- def has_many(*args)
207
- require 'og/relation/has_many'
208
- meta :relations, Og::HasMany.new(args, :owner_class => self, :collection => true)
209
- end
210
-
211
- def joins_many(*args)
212
- require 'og/relation/joins_many'
213
- meta :relations, Og::JoinsMany.new(args, :owner_class => self, :collection => true)
214
- end
215
-
216
- def many_to_many(*args)
217
- require 'og/relation/many_to_many'
218
- meta :relations, Og::ManyToMany.new(args, :owner_class => self, :collection => true)
219
- end
220
-
221
- def inspect_relations
222
- __meta[:relations]
223
- end
224
- alias_method :relations, :inspect_relations
225
-
226
- def inspect_relation(name)
227
- __meta[:relations].find { |r| r[:name] == name }
228
- end
229
- alias_method :relation, :inspect_relation
230
-
231
- end
189
+ def self.append_features(base)
190
+ super
191
+ base.extend(ClassMethods)
192
+ end
193
+
194
+ module ClassMethods
195
+
196
+ # === Examples
197
+ #
198
+ # belongs_to Article
199
+ # belongs_to :article, Article
200
+ # belongs_to :article, Article, :view => 'lala'
201
+
202
+ def belongs_to(*args)
203
+ require 'og/relation/belongs_to'
204
+ meta :relations, Og::BelongsTo.new(args, :owner_class => self)
205
+ end
206
+
207
+ # === Examples
208
+ #
209
+ # refers_to Topic
210
+
211
+ def refers_to(*args)
212
+ require 'og/relation/refers_to'
213
+ meta :relations, Og::RefersTo.new(args, :owner_class => self)
214
+ end
215
+
216
+ # === Examples
217
+ #
218
+ # has_one User
219
+
220
+ def has_one(*args)
221
+ require 'og/relation/has_one'
222
+ meta :relations, Og::HasOne.new(args, :owner_class => self)
223
+ end
224
+
225
+ # === Examples
226
+ #
227
+ # has_many Comment
228
+ # has_many :comments, Comment
229
+
230
+ def has_many(*args)
231
+ require 'og/relation/has_many'
232
+ meta :relations, Og::HasMany.new(args, :owner_class => self, :collection => true)
233
+ end
234
+
235
+ def joins_many(*args)
236
+ require 'og/relation/joins_many'
237
+ meta :relations, Og::JoinsMany.new(args, :owner_class => self, :collection => true)
238
+ end
239
+
240
+ def many_to_many(*args)
241
+ require 'og/relation/many_to_many'
242
+ meta :relations, Og::ManyToMany.new(args, :owner_class => self, :collection => true)
243
+ end
244
+
245
+ def inspect_relations
246
+ __meta[:relations]
247
+ end
248
+ alias_method :relations, :inspect_relations
249
+
250
+ def inspect_relation(name)
251
+ __meta[:relations].find { |r| r[:name] == name }
252
+ end
253
+ alias_method :relation, :inspect_relation
254
+
255
+ end
232
256
  end
233
257
 
234
258
  end