Class: Ripple::Association
- Includes:
- Translation
- Defined in:
- lib/ripple/associations.rb
Overview
The “reflection” for an association - metadata about how it is configured.
Instance Attribute Summary collapse
-
#name ⇒ Object
readonly
Returns the value of attribute name.
-
#options ⇒ Object
readonly
Returns the value of attribute options.
-
#type ⇒ Object
readonly
Returns the value of attribute type.
Instance Method Summary collapse
- #bucket_name ⇒ Object
-
#class_name ⇒ Object
String The class name of the associated object(s).
- #define_callbacks_on(klass) ⇒ Object
-
#embedded? ⇒ true, false
Is the associated class an EmbeddedDocument.
-
#initialize(type, name, options = {}) ⇒ Association
constructor
association options :using, :class_name, :class, :extend, options that may be added :validate.
-
#ivar ⇒ String
The instance variable in the owner where the association will be stored.
-
#klass ⇒ Class
The class of the associated object(s).
-
#link_filter ⇒ Proc
A filter proc to be used with Enumerable#select for collecting links that belong to this association (only when #linked? is true).
-
#link_spec ⇒ Riak::WalkSpec
When #linked? is true, a specification for which links to follow to retrieve the associated documents.
-
#link_tag ⇒ String?
When #linked? is true, the tag for outgoing links.
-
#linked? ⇒ true, false
Does the association use links.
-
#many? ⇒ true, false
Is the cardinality of the association > 1.
-
#one? ⇒ true, false
Is the cardinality of the association == 1.
-
#polymorphic? ⇒ true, false
TODO: Polymorphic not supported.
-
#proxy_class ⇒ Class
The association proxy class.
-
#proxy_class_name ⇒ String
The class name of the association proxy.
- #setup_on(model) ⇒ Object
-
#stored_key? ⇒ true, false
Does the association use stored_key.
- #type_matches?(value) ⇒ Boolean
- #uses_search? ⇒ Boolean
-
#using ⇒ Symbol
Which method is used for representing the association - currently only supports :embedded and :linked.
- #validate!(owner) ⇒ Object
- #verify_type!(value, owner) ⇒ Object
Methods included from Translation
Constructor Details
#initialize(type, name, options = {}) ⇒ Association
association options :using, :class_name, :class, :extend, options that may be added :validate
201 202 203 |
# File 'lib/ripple/associations.rb', line 201 def initialize(type, name, ={}) @type, @name, @options = type, name, . end |
Instance Attribute Details
#name ⇒ Object (readonly)
Returns the value of attribute name.
196 197 198 |
# File 'lib/ripple/associations.rb', line 196 def name @name end |
#options ⇒ Object (readonly)
Returns the value of attribute options.
196 197 198 |
# File 'lib/ripple/associations.rb', line 196 def @options end |
#type ⇒ Object (readonly)
Returns the value of attribute type.
196 197 198 |
# File 'lib/ripple/associations.rb', line 196 def type @type end |
Instance Method Details
#bucket_name ⇒ Object
291 292 293 |
# File 'lib/ripple/associations.rb', line 291 def bucket_name polymorphic? ? '_' : klass.bucket_name end |
#class_name ⇒ Object
Returns String The class name of the associated object(s).
216 217 218 219 220 221 222 223 224 225 226 227 |
# File 'lib/ripple/associations.rb', line 216 def class_name @class_name ||= case when @options[:class_name] @options[:class_name] when @options[:class] @options[:class].to_s when many? @name.to_s.classify else @name.to_s.camelize end end |
#define_callbacks_on(klass) ⇒ Object
350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 |
# File 'lib/ripple/associations.rb', line 350 def define_callbacks_on(klass) _association = self klass.before_save do if _association.linked? && !@_in_save_loaded_documents_callback @_in_save_loaded_documents_callback = true begin send(_association.name).loaded_documents.each do |document| document.save if document.new? || document.changed? end ensure remove_instance_variable(:@_in_save_loaded_documents_callback) end end end end |
#embedded? ⇒ true, false
Returns Is the associated class an EmbeddedDocument.
245 246 247 |
# File 'lib/ripple/associations.rb', line 245 def klass. end |
#ivar ⇒ String
Returns the instance variable in the owner where the association will be stored.
266 267 268 |
# File 'lib/ripple/associations.rb', line 266 def ivar "@_#{name}" end |
#klass ⇒ Class
Returns The class of the associated object(s).
230 231 232 |
# File 'lib/ripple/associations.rb', line 230 def klass @klass ||= discover_class end |
#link_filter ⇒ Proc
Returns a filter proc to be used with Enumerable#select for collecting links that belong to this association (only when #linked? is true).
282 283 284 |
# File 'lib/ripple/associations.rb', line 282 def link_filter linked? ? lambda {|link| link.tag == link_tag } : lambda {|_| false } end |
#link_spec ⇒ Riak::WalkSpec
Returns when #linked? is true, a specification for which links to follow to retrieve the associated documents.
296 297 298 299 300 301 302 303 304 |
# File 'lib/ripple/associations.rb', line 296 def link_spec # TODO: support transitive linked associations if linked? tag = name.to_s Riak::WalkSpec.new(:tag => tag, :bucket => bucket_name) else nil end end |
#link_tag ⇒ String?
Returns when #linked? is true, the tag for outgoing links.
287 288 289 |
# File 'lib/ripple/associations.rb', line 287 def link_tag linked? ? Array(link_spec).first.tag : nil end |
#linked? ⇒ true, false
Returns Does the association use links.
256 257 258 |
# File 'lib/ripple/associations.rb', line 256 def linked? using == :linked end |
#many? ⇒ true, false
Returns Is the cardinality of the association > 1.
235 236 237 |
# File 'lib/ripple/associations.rb', line 235 def many? @type == :many end |
#one? ⇒ true, false
Returns Is the cardinality of the association == 1.
240 241 242 |
# File 'lib/ripple/associations.rb', line 240 def one? @type == :one end |
#polymorphic? ⇒ true, false
TODO: Polymorphic not supported
251 252 253 |
# File 'lib/ripple/associations.rb', line 251 def polymorphic? false end |
#proxy_class ⇒ Class
Returns the association proxy class.
271 272 273 |
# File 'lib/ripple/associations.rb', line 271 def proxy_class @proxy_class ||= proxy_class_name.constantize end |
#proxy_class_name ⇒ String
Returns the class name of the association proxy.
276 277 278 279 |
# File 'lib/ripple/associations.rb', line 276 def proxy_class_name klass_name = (many? ? 'Many' : 'One') + using.to_s.camelize + ('Polymorphic' if polymorphic?).to_s + 'Proxy' "Ripple::Associations::#{klass_name}" end |
#setup_on(model) ⇒ Object
338 339 340 341 342 343 344 345 346 347 348 |
# File 'lib/ripple/associations.rb', line 338 def setup_on(model) @model = model define_callbacks_on(model) if uses_search? klass.before_save do |o| unless o.class.bucket.is_indexed? o.class.bucket.enable_index! end end end end |
#stored_key? ⇒ true, false
Returns Does the association use stored_key.
261 262 263 |
# File 'lib/ripple/associations.rb', line 261 def stored_key? using == :stored_key end |
#type_matches?(value) ⇒ Boolean
323 324 325 326 327 328 329 330 331 332 |
# File 'lib/ripple/associations.rb', line 323 def type_matches?(value) case when polymorphic? one? || Array === value when many? Array === value && value.all? {|d| ( && Hash === d) || klass === d } when one? value.nil? || ( && Hash === value) || value.kind_of?(klass) end end |
#uses_search? ⇒ Boolean
334 335 336 |
# File 'lib/ripple/associations.rb', line 334 def uses_search? ([:using] == :reference) end |
#using ⇒ Symbol
Returns which method is used for representing the association - currently only supports :embedded and :linked.
307 308 309 |
# File 'lib/ripple/associations.rb', line 307 def using @using ||= [:using] || ( ? :embedded : :linked) end |
#validate!(owner) ⇒ Object
205 206 207 208 209 210 211 212 213 |
# File 'lib/ripple/associations.rb', line 205 def validate!(owner) # TODO: Refactor this into an association subclass. See also GH #284 if @options[:using] == :stored_key single_name = ActiveSupport::Inflector.singularize(@name.to_s) prop_name = "#{single_name}_key" prop_name << "s" if many? raise ArgumentError, t('stored_key_requires_property', :name => prop_name) unless owner.properties.include?(prop_name) end end |
#verify_type!(value, owner) ⇒ Object
312 313 314 315 316 317 318 319 320 |
# File 'lib/ripple/associations.rb', line 312 def verify_type!(value, owner) unless type_matches?(value) raise ArgumentError.new(t('invalid_association_value', :name => name, :owner => owner.inspect, :klass => polymorphic? ? "<polymorphic>" : klass.name, :value => value.inspect)) end end |