Class: Model
- Includes:
- ModelWrapper, ObjectTracking, ReactiveTags
- Defined in:
- lib/volt/models/model.rb
Direct Known Subclasses
Instance Attribute Summary collapse
-
#attributes ⇒ Object
Returns the value of attribute attributes.
-
#parent ⇒ Object
readonly
Returns the value of attribute parent.
-
#path ⇒ Object
readonly
Returns the value of attribute path.
Instance Method Summary collapse
-
#! ⇒ Object
Pass through needed.
-
#<<(value) ⇒ Object
Initialize an empty array and append to it.
-
#==(val) ⇒ Object
Pass the comparison through.
-
#assign_attribute(method_name, *args, &block) ⇒ Object
Do the assignment to a model and trigger a changed event.
- #delete(*args) ⇒ Object
-
#expand! ⇒ Object
If this model is nil, it makes it into a hash model, then sets it up to track from the parent.
- #false? ⇒ Boolean
-
#initialize(attributes = {}, parent = nil, path = nil, class_paths = nil) ⇒ Model
constructor
A new instance of Model.
- #inspect ⇒ Object
- #method_missing(method_name, *args, &block) ⇒ Object
- #new_model(*args) ⇒ Object
- #nil? ⇒ Boolean
-
#read_attribute(method_name) ⇒ Object
When reading an attribute, we need to handle reading on: 1) a nil model, which returns a wrapped error 2) reading directly from attributes 3) trying to read a key that doesn’t exist.
- #return_undefined_method(method_name) ⇒ Object
- #trigger_by_attribute!(event_name, attribute, *passed_args) ⇒ Object
- #true? ⇒ Boolean
Methods included from ObjectTracking
Methods included from ModelWrapper
Methods included from ReactiveTags
included, #reactive_method_tag
Constructor Details
#initialize(attributes = {}, parent = nil, path = nil, class_paths = nil) ⇒ Model
Returns a new instance of Model.
35 36 37 38 39 |
# File 'lib/volt/models/model.rb', line 35 def initialize(attributes={}, parent=nil, path=nil, class_paths=nil) self.attributes = wrap_values(attributes) @parent = parent @path = path end |
Dynamic Method Handling
This class handles dynamic methods through the method_missing method
#method_missing(method_name, *args, &block) ⇒ Object
68 69 70 71 72 73 74 75 76 77 78 79 80 81 |
# File 'lib/volt/models/model.rb', line 68 def method_missing(method_name, *args, &block) if method_name[0] == '_' if method_name[-1] == '=' # Assigning an attribute with = assign_attribute(method_name, *args, &block) else read_attribute(method_name) end else # Call method directly on attributes. (since they are # not using _ ) attributes.send(method_name, *args, &block) end end |
Instance Attribute Details
#attributes ⇒ Object
Returns the value of attribute attributes.
20 21 22 |
# File 'lib/volt/models/model.rb', line 20 def attributes @attributes end |
#parent ⇒ Object (readonly)
Returns the value of attribute parent.
21 22 23 |
# File 'lib/volt/models/model.rb', line 21 def parent @parent end |
#path ⇒ Object (readonly)
Returns the value of attribute path.
21 22 23 |
# File 'lib/volt/models/model.rb', line 21 def path @path end |
Instance Method Details
#! ⇒ Object
Pass through needed
47 48 49 |
# File 'lib/volt/models/model.rb', line 47 def ! !attributes end |
#<<(value) ⇒ Object
Initialize an empty array and append to it
165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 |
# File 'lib/volt/models/model.rb', line 165 def <<(value) @parent. result = @parent.send(@path) if result.nil? # If this isn't a model yet, instantiate it @parent.send(:"#{@path}=", ArrayModel.new([], @parent, @path)) result = @parent.send(@path) # Add the new item result << value end return result end |
#==(val) ⇒ Object
Pass the comparison through
42 43 44 |
# File 'lib/volt/models/model.rb', line 42 def ==(val) attributes == val end |
#assign_attribute(method_name, *args, &block) ⇒ Object
Do the assignment to a model and trigger a changed event
84 85 86 87 88 89 90 91 92 93 94 |
# File 'lib/volt/models/model.rb', line 84 def assign_attribute(method_name, *args, &block) self. # Assign, without the = attribute_name = method_name[0..-2].to_sym value = args[0] __assign_element(attribute_name, value) attributes[attribute_name] = wrap_value(value) trigger_by_attribute!('changed', attribute_name) end |
#delete(*args) ⇒ Object
54 55 56 57 58 |
# File 'lib/volt/models/model.rb', line 54 def delete(*args) __clear_element(args[0]) attributes.delete(*args) trigger_by_attribute!('changed', args[0]) end |
#expand! ⇒ Object
If this model is nil, it makes it into a hash model, then sets it up to track from the parent.
149 150 151 152 153 154 155 156 157 158 |
# File 'lib/volt/models/model.rb', line 149 def if attributes.nil? self.attributes = {} if @parent @parent. @parent.attributes[@path] = self end end end |
#false? ⇒ Boolean
27 28 29 |
# File 'lib/volt/models/model.rb', line 27 def false? attributes.false? end |
#inspect ⇒ Object
181 182 183 |
# File 'lib/volt/models/model.rb', line 181 def inspect "<#{self.class.to_s}:#{@path} #{attributes.inspect}>" end |
#new_model(*args) ⇒ Object
130 131 132 |
# File 'lib/volt/models/model.rb', line 130 def new_model(*args) Model.new(*args) end |
#read_attribute(method_name) ⇒ Object
When reading an attribute, we need to handle reading on: 1) a nil model, which returns a wrapped error 2) reading directly from attributes 3) trying to read a key that doesn’t exist.
100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 |
# File 'lib/volt/models/model.rb', line 100 def read_attribute(method_name) # Reading an attribute, we may get back a nil model. method_name = method_name.to_sym if attributes == nil # The method we are calling is on a nil model, return a wrapped # exception. return return_undefined_method(method_name) elsif attributes && attributes.has_key?(method_name) # Method has the key, look it up directly return attributes[method_name] else return new_model(nil, self, method_name) end end |
#return_undefined_method(method_name) ⇒ Object
116 117 118 119 120 121 122 123 124 125 126 127 128 |
# File 'lib/volt/models/model.rb', line 116 def return_undefined_method(method_name) # Methods called on nil capture an error so the user can know where # their nil calls are. This error can be re-raised at a later point. begin raise NilMethodCall.new("undefined method `#{method_name}' for #{self.to_s}") rescue => e result = e # Cleanup backtrace around ReactiveValue's # TODO: this could be better result.backtrace.reject! {|line| line['lib/models/model.rb'] || line['lib/models/live_value.rb'] } end end |
#trigger_by_attribute!(event_name, attribute, *passed_args) ⇒ Object
134 135 136 137 138 139 140 141 142 143 144 145 |
# File 'lib/volt/models/model.rb', line 134 def trigger_by_attribute!(event_name, attribute, *passed_args) trigger_by_scope!(event_name, *passed_args) do |scope| method_name, *args, block = scope # TODO: Opal bug args ||= [] # Any methods without _ are not directly related to one attribute, so # they should all trigger !method_name || method_name[0] != '_' || (method_name == attribute.to_sym && args.size == 0) end end |