Class: MotionResource::Base
- Inherits:
-
Object
- Object
- MotionResource::Base
- Includes:
- MotionSupport::Callbacks, MotionSupport::DescendantsTracker
- Defined in:
- lib/motion-resource/base.rb,
lib/motion-resource/crud.rb,
lib/motion-resource/find.rb,
lib/motion-resource/urls.rb,
lib/motion-resource/logger.rb,
lib/motion-resource/requests.rb,
lib/motion-resource/callbacks.rb,
lib/motion-resource/attributes.rb,
lib/motion-resource/associations.rb
Constant Summary collapse
- HTTP_METHODS =
[:get, :post, :put, :delete]
Instance Attribute Summary collapse
-
#id ⇒ Object
Returns the value of attribute id.
Class Method Summary collapse
- .attribute(*fields) ⇒ Object
- .belongs_to(name, options = {}) ⇒ Object
- .collection_url_or_default ⇒ Object
- .create(attributes = {}, &block) ⇒ Object
- .custom_urls(params = {}) ⇒ Object
- .delete(url, params = {}, &block) ⇒ Object
- .fetch_collection(url, &block) ⇒ Object
- .fetch_member(url, &block) ⇒ Object
- .find(id, params = {}, &block) ⇒ Object
- .find_all(params = {}, &block) ⇒ Object
- .get(url, params = {}, &block) ⇒ Object
- .has_many(name, options = {}) ⇒ Object
- .has_one(name) ⇒ Object
- .identity_map ⇒ Object
- .instantiate(json) ⇒ Object
- .json_root ⇒ Object
- .member_url_or_default ⇒ Object
- .on_auth_failure(&block) ⇒ Object
- .post(url, params = {}, &block) ⇒ Object
- .put(url, params = {}, &block) ⇒ Object
- .recall(id) ⇒ Object
- .remember(id, value) ⇒ Object
- .request_block_call(block, default_arg, extra_arg) ⇒ Object
- .scope(name, options = {}) ⇒ Object
Instance Method Summary collapse
- #attributes ⇒ Object
- #collection_url(params = {}) ⇒ Object
- #create(options = {}, &block) ⇒ Object
- #destroy(&block) ⇒ Object
-
#initialize(params = {}) ⇒ Base
constructor
A new instance of Base.
- #member_url(params = {}) ⇒ Object
- #new_record? ⇒ Boolean
- #reload(&block) ⇒ Object
- #save(options = {}, &block) ⇒ Object
- #update(options = {}, &block) ⇒ Object
- #update_attributes(params = {}) ⇒ Object
Constructor Details
#initialize(params = {}) ⇒ Base
Returns a new instance of Base.
10 11 12 13 |
# File 'lib/motion-resource/base.rb', line 10 def initialize(params = {}) @new_record = true update_attributes(params) end |
Instance Attribute Details
#id ⇒ Object
Returns the value of attribute id.
8 9 10 |
# File 'lib/motion-resource/base.rb', line 8 def id @id end |
Class Method Details
.attribute(*fields) ⇒ Object
7 8 9 10 11 12 13 14 15 16 17 18 19 |
# File 'lib/motion-resource/attributes.rb', line 7 def attribute(*fields) attr_reader *fields fields.each do |field| define_method "#{field}=" do |value| if value.is_a?(Hash) || value.is_a?(Array) instance_variable_set("@#{field}", value.dup) else instance_variable_set("@#{field}", value) end end end self.attributes += fields end |
.belongs_to(name, options = {}) ⇒ Object
70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 |
# File 'lib/motion-resource/associations.rb', line 70 def belongs_to(name, = {}) = { :params => lambda { |o| Hash.new }, :class_name => name.to_s.classify } = .merge() define_method name do |&block| if block.nil? instance_variable_get("@#{name}") else if cached = instance_variable_get("@#{name}") cached_response = instance_variable_get("@#{name}_response") MotionResource::Base.request_block_call(block, cached, cached_response) return end klass = Object.const_get([:class_name]) klass.find(self.send("#{name}_id"), [:params].call(self)) do |result, response| instance_variable_set("@#{name}", result) instance_variable_set("@#{name}_response", response) MotionResource::Base.request_block_call(block, result, response) end end end define_method "#{name}=" do |value| value = Object.const_get([:class_name]).instantiate(value) if value.is_a?(Hash) instance_variable_set("@#{name}_id", value.id) if value.respond_to?(:id) instance_variable_set("@#{name}", value) end define_method "reset_#{name}" do instance_variable_set("@#{name}", nil) end end |
.collection_url_or_default ⇒ Object
23 24 25 |
# File 'lib/motion-resource/urls.rb', line 23 def collection_url_or_default collection_url || name.underscore.pluralize end |
.create(attributes = {}, &block) ⇒ Object
25 26 27 28 29 |
# File 'lib/motion-resource/crud.rb', line 25 def self.create(attributes = {}, &block) new(attributes).tap do |model| model.create(&block) end end |
.custom_urls(params = {}) ⇒ Object
12 13 14 15 16 17 18 19 20 21 |
# File 'lib/motion-resource/urls.rb', line 12 def custom_urls(params = {}) params.each do |name, url_format| define_method name do |method_params = {}| self.url_encoder.fill_url_params(url_format, method_params, self) end define_singleton_method name do url_format end end end |
.delete(url, params = {}, &block) ⇒ Object
24 25 26 |
# File 'lib/motion-resource/requests.rb', line 24 def delete(url, params = {}, &block) http_call(:delete, url, params, &block) end |
.fetch_collection(url, &block) ⇒ Object
23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
# File 'lib/motion-resource/find.rb', line 23 def fetch_collection(url, &block) get(url) do |response, json| if response.ok? objs = [] arr_rep = nil if json.class == Array arr_rep = json elsif json.class == Hash root = self.json_root if json.has_key?(root) || json.has_key?(root.to_sym) arr_rep = json[root] || json[root.to_sym] end else # the returned data was something else # ie a string, number request_block_call(block, nil, response) return end if arr_rep arr_rep.each { |one_obj_hash| objs << instantiate(one_obj_hash) } end request_block_call(block, objs, response) else request_block_call(block, nil, response) end end end |
.fetch_member(url, &block) ⇒ Object
12 13 14 15 16 17 18 19 20 21 |
# File 'lib/motion-resource/find.rb', line 12 def fetch_member(url, &block) get(url) do |response, json| if response.ok? obj = instantiate(json) request_block_call(block, obj, response) else request_block_call(block, nil, response) end end end |
.find(id, params = {}, &block) ⇒ Object
4 5 6 |
# File 'lib/motion-resource/find.rb', line 4 def find(id, params = {}, &block) fetch_member(self.url_encoder.fill_url_params(member_url_or_default, params.merge(id: id)), &block) end |
.find_all(params = {}, &block) ⇒ Object
8 9 10 |
# File 'lib/motion-resource/find.rb', line 8 def find_all(params = {}, &block) fetch_collection(self.url_encoder.fill_url_params(collection_url_or_default, params), &block) end |
.get(url, params = {}, &block) ⇒ Object
12 13 14 |
# File 'lib/motion-resource/requests.rb', line 12 def get(url, params = {}, &block) http_call(:get, url, params, &block) end |
.has_many(name, options = {}) ⇒ Object
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 |
# File 'lib/motion-resource/associations.rb', line 20 def has_many(name, = {}) = { :params => lambda { |o| Hash.new }, :class_name => name.to_s.classify } = .merge() backwards_association = self.name.underscore define_method name do |&block| if block.nil? instance_variable_get("@#{name}") || instance_variable_set("@#{name}", []) else if cached = instance_variable_get("@#{name}") cached_response = instance_variable_get("@#{name}_response") MotionResource::Base.request_block_call(block, cached, cached_response) return end klass = [:class_name].constantize klass.find_all([:params].call(self)) do |results, response| if results && results.first && results.first.respond_to?("#{backwards_association}=") results.each do |result| result.send("#{backwards_association}=", self) end end instance_variable_set("@#{name}", results) instance_variable_set("@#{name}_response", response) MotionResource::Base.request_block_call(block, results, response) end end end define_method "#{name}=" do |array| klass = [:class_name].constantize instance_variable_set("@#{name}", []) array.each do |value| value = klass.instantiate(value) if value.is_a?(Hash) instance_variable_get("@#{name}") << value end end define_method "reset_#{name}" do instance_variable_set("@#{name}", nil) end end |
.has_one(name) ⇒ Object
4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
# File 'lib/motion-resource/associations.rb', line 4 def has_one(name) define_method name do instance_variable_get("@#{name}") end define_method "#{name}=" do |value| klass = Object.const_get(name.to_s.classify) value = klass.instantiate(value) if value.is_a?(Hash) instance_variable_set("@#{name}", value) end define_method "reset_#{name}" do instance_variable_set("@#{name}", nil) end end |
.identity_map ⇒ Object
53 54 55 |
# File 'lib/motion-resource/base.rb', line 53 def identity_map @identity_map ||= {} end |
.instantiate(json) ⇒ Object
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 |
# File 'lib/motion-resource/base.rb', line 20 def instantiate(json) if json.is_a?(Hash) json = json.symbolize_keys else json = { primary_key => json.to_i } end raise ArgumentError, "No :#{primary_key} parameter given for #{self.name}.instantiate" unless json[primary_key] klass = if json[:type] begin Object.const_get(json[:type].to_s) rescue NameError self end else self end if result = klass.recall(json[primary_key]) result.update_attributes(json) else result = klass.new(json) klass.remember(result.send(result.primary_key), result) end result.send(:instance_variable_set, "@new_record", false) result end |
.json_root ⇒ Object
49 50 51 |
# File 'lib/motion-resource/base.rb', line 49 def json_root self.name.underscore.pluralize end |
.member_url_or_default ⇒ Object
27 28 29 |
# File 'lib/motion-resource/urls.rb', line 27 def member_url_or_default member_url || "#{name.underscore.pluralize}/:#{primary_key}" end |
.on_auth_failure(&block) ⇒ Object
28 29 30 |
# File 'lib/motion-resource/requests.rb', line 28 def on_auth_failure(&block) @on_auth_failure = block end |
.post(url, params = {}, &block) ⇒ Object
16 17 18 |
# File 'lib/motion-resource/requests.rb', line 16 def post(url, params = {}, &block) http_call(:post, url, params, &block) end |
.put(url, params = {}, &block) ⇒ Object
20 21 22 |
# File 'lib/motion-resource/requests.rb', line 20 def put(url, params = {}, &block) http_call(:put, url, params, &block) end |
.recall(id) ⇒ Object
61 62 63 |
# File 'lib/motion-resource/base.rb', line 61 def recall(id) identity_map[id] end |
.remember(id, value) ⇒ Object
57 58 59 |
# File 'lib/motion-resource/base.rb', line 57 def remember(id, value) identity_map[id] = value end |
.request_block_call(block, default_arg, extra_arg) ⇒ Object
53 54 55 56 57 58 59 60 61 62 63 64 65 |
# File 'lib/motion-resource/find.rb', line 53 def request_block_call(block, default_arg, extra_arg) if block if block.arity == 1 block.call default_arg elsif block.arity == 2 block.call default_arg, extra_arg else raise "Not enough arguments to block" end else raise "No block given" end end |
.scope(name, options = {}) ⇒ Object
107 108 109 110 111 112 113 |
# File 'lib/motion-resource/associations.rb', line 107 def scope(name, = {}) custom_urls "#{name}_url" => [:url] if [:url] .send(:define_method, name) do |&block| fetch_collection(send("#{name}_url"), &block) end end |
Instance Method Details
#attributes ⇒ Object
31 32 33 34 35 36 |
# File 'lib/motion-resource/attributes.rb', line 31 def attributes self.class.attributes.inject({}) do |hash, attr| hash[attr] = send(attr) hash end end |
#collection_url(params = {}) ⇒ Object
33 34 35 |
# File 'lib/motion-resource/urls.rb', line 33 def collection_url(params = {}) self.class.url_encoder.fill_url_params(self.class.collection_url_or_default, params, self) end |
#create(options = {}, &block) ⇒ Object
17 18 19 20 21 22 23 |
# File 'lib/motion-resource/crud.rb', line 17 def create( = {}, &block) run_callbacks :create do self.class.post(collection_url, :payload => build_payload()) do |response, json| self.class.request_block_call(block, json.blank? ? self : self.class.instantiate(json), response) if block end end end |
#destroy(&block) ⇒ Object
31 32 33 34 35 36 37 |
# File 'lib/motion-resource/crud.rb', line 31 def destroy(&block) run_callbacks :destroy do self.class.delete(member_url) do |response, json| self.class.request_block_call(block, json.blank? ? nil : self.class.instantiate(json), response) if block end end end |
#member_url(params = {}) ⇒ Object
37 38 39 |
# File 'lib/motion-resource/urls.rb', line 37 def member_url(params = {}) self.class.url_encoder.fill_url_params(self.class.member_url_or_default, params, self) end |
#new_record? ⇒ Boolean
15 16 17 |
# File 'lib/motion-resource/base.rb', line 15 def new_record? @new_record end |
#reload(&block) ⇒ Object
39 40 41 42 43 |
# File 'lib/motion-resource/crud.rb', line 39 def reload(&block) self.class.get(member_url) do |response, json| self.class.request_block_call(block, json.blank? ? nil : self.class.instantiate(json), response) if block end end |
#save(options = {}, &block) ⇒ Object
3 4 5 6 7 |
# File 'lib/motion-resource/crud.rb', line 3 def save( = {}, &block) run_callbacks :save do @new_record ? create(, &block) : update(, &block) end end |
#update(options = {}, &block) ⇒ Object
9 10 11 12 13 14 15 |
# File 'lib/motion-resource/crud.rb', line 9 def update( = {}, &block) run_callbacks :update do self.class.put(member_url, :payload => build_payload()) do |response, json| self.class.request_block_call(block, json.blank? ? self : self.class.instantiate(json), response) if block end end end |
#update_attributes(params = {}) ⇒ Object
22 23 24 25 26 27 28 29 |
# File 'lib/motion-resource/attributes.rb', line 22 def update_attributes(params = {}) attributes = self.methods - Object.methods params.each do |key, value| if attributes.member?((key.to_s + "=:").to_sym) self.send((key.to_s + "=:").to_sym, value) end end end |