logical_model 0.5.13 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.6.0
|
@@ -14,6 +14,9 @@ class LogicalModel
|
|
14
14
|
attr_accessor "#{key}_id"
|
15
15
|
attr_class = get_attr_class(key, options)
|
16
16
|
|
17
|
+
@belongs_to_keys ||= {}
|
18
|
+
@belongs_to_keys.merge!({key => attr_class})
|
19
|
+
|
17
20
|
define_method("#{key}=") do |param|
|
18
21
|
if param.is_a?(Hash)
|
19
22
|
param.stringify_keys!
|
@@ -51,6 +54,30 @@ class LogicalModel
|
|
51
54
|
end
|
52
55
|
end
|
53
56
|
|
57
|
+
def belongs_to_keys
|
58
|
+
# This hack was needed to consider the case where the belongs_to was set on a parent class, for example:
|
59
|
+
#
|
60
|
+
# class ContactAttribute < LogicalModel
|
61
|
+
# ...
|
62
|
+
# belongs_to :contact
|
63
|
+
# end
|
64
|
+
#
|
65
|
+
# class Telephone < ContactAttribute
|
66
|
+
# ...
|
67
|
+
# end
|
68
|
+
#
|
69
|
+
# It returns the parent's class variable if present.
|
70
|
+
result = nil
|
71
|
+
if !@belongs_to_keys.nil?
|
72
|
+
result = @belongs_to_keys
|
73
|
+
elsif self.superclass.respond_to? :belongs_to_keys
|
74
|
+
result = self.superclass.belongs_to_keys
|
75
|
+
else
|
76
|
+
result = nil
|
77
|
+
end
|
78
|
+
result
|
79
|
+
end
|
80
|
+
|
54
81
|
private
|
55
82
|
|
56
83
|
def get_attr_class(key, options)
|
@@ -66,6 +66,8 @@ class LogicalModel
|
|
66
66
|
# in this case we recieved instanciated objects
|
67
67
|
collection << attr_params
|
68
68
|
else
|
69
|
+
clazz_name = attr_params['_type']
|
70
|
+
attr_class = clazz_name.constantize unless clazz_name.blank?
|
69
71
|
# in this case we recieved object attributes, we instanciate here
|
70
72
|
collection << attr_class.new(attr_params)
|
71
73
|
end
|
@@ -75,13 +77,16 @@ class LogicalModel
|
|
75
77
|
|
76
78
|
# Initialize instance of associated object
|
77
79
|
define_method "new_#{StringHelper.singularize(association.to_s)}" do |attr_params|
|
78
|
-
|
80
|
+
run_callbacks :new_nested do
|
81
|
+
clazz_name = attr_params['_type']
|
82
|
+
clazz = clazz_name.blank? ? attr_class : clazz_name.constantize
|
79
83
|
|
80
|
-
|
84
|
+
return unless clazz
|
81
85
|
|
82
|
-
|
83
|
-
|
84
|
-
|
86
|
+
temp_object = clazz.new(attr_params.merge({"#{self.json_root}_id" => self.id}))
|
87
|
+
eval(association.to_s) << temp_object
|
88
|
+
temp_object
|
89
|
+
end
|
85
90
|
end
|
86
91
|
|
87
92
|
# this method loads the contact attributes from the html form (using nested resources conventions)
|
data/lib/logical_model/cache.rb
CHANGED
@@ -2,9 +2,11 @@ class LogicalModel
|
|
2
2
|
module Cache
|
3
3
|
|
4
4
|
def self.included(base)
|
5
|
-
base.
|
5
|
+
base.extend ClassMethods
|
6
6
|
base.send(:include, InstanceMethods)
|
7
7
|
base.send(:after_initialize, :initialize_loaded_at)
|
8
|
+
base.send(:define_model_callbacks, :new_nested)
|
9
|
+
base.send(:after_new_nested, :delete_cached)
|
8
10
|
end
|
9
11
|
|
10
12
|
module InstanceMethods
|
@@ -19,9 +21,7 @@ class LogicalModel
|
|
19
21
|
end
|
20
22
|
|
21
23
|
def _save_with_cache
|
22
|
-
|
23
|
-
self.class.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/#{self.id}-.*"
|
24
|
-
self.class.cache_store.delete_matched(/#{model_name}\/#{self.id}-.*/)
|
24
|
+
delete_cached
|
25
25
|
_save_without_cache
|
26
26
|
end
|
27
27
|
alias_method_chain :_save, :cache
|
@@ -31,9 +31,7 @@ class LogicalModel
|
|
31
31
|
end
|
32
32
|
|
33
33
|
def _update_with_cache(params={})
|
34
|
-
|
35
|
-
self.class.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/#{self.id}-.*"
|
36
|
-
self.class.cache_store.delete_matched(/#{model_name}\/#{self.id}-.*/)
|
34
|
+
delete_cached
|
37
35
|
_update_without_cache params
|
38
36
|
end
|
39
37
|
alias_method_chain :_update, :cache
|
@@ -43,12 +41,27 @@ class LogicalModel
|
|
43
41
|
end
|
44
42
|
|
45
43
|
def _destroy_with_cache(params={})
|
44
|
+
delete_cached
|
45
|
+
_destroy_without_cache
|
46
|
+
end
|
47
|
+
alias_method_chain :_destroy, :cache
|
48
|
+
|
49
|
+
def delete_cached
|
46
50
|
model_name = self.class.to_s.pluralize.underscore
|
47
51
|
self.class.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/#{self.id}-.*"
|
52
|
+
# Delete cached models
|
48
53
|
self.class.cache_store.delete_matched(/#{model_name}\/#{self.id}-.*/)
|
49
|
-
|
54
|
+
|
55
|
+
if self.class.respond_to?(:belongs_to_keys) && !self.class.belongs_to_keys.blank?
|
56
|
+
# If it belongs to another model (or models)
|
57
|
+
self.class.belongs_to_keys.each do |association_name, association_class|
|
58
|
+
model_name = association_class.to_s.pluralize.underscore
|
59
|
+
self.class.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/#{self.send("#{association_name}_id")}-.*"
|
60
|
+
# Delete cached models
|
61
|
+
self.class.cache_store.delete_matched(/#{model_name}\/#{self.send("#{association_name}_id")}-.*/)
|
62
|
+
end
|
63
|
+
end
|
50
64
|
end
|
51
|
-
alias_method_chain :_destroy, :cache
|
52
65
|
end
|
53
66
|
|
54
67
|
module ClassMethods
|
@@ -111,6 +124,7 @@ class LogicalModel
|
|
111
124
|
model_name = self.to_s.pluralize.underscore
|
112
125
|
self.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/#{id}-.*"
|
113
126
|
self.cache_store.delete_matched(/#{model_name}\/#{id}-.*/)
|
127
|
+
#TODO: also delete cache for parent (belongs_to)
|
114
128
|
delete_without_cache(id, params)
|
115
129
|
end
|
116
130
|
alias_method_chain :delete, :cache
|
@@ -123,10 +137,10 @@ class LogicalModel
|
|
123
137
|
model_name = self.to_s.pluralize.underscore
|
124
138
|
self.logger.debug "LogicalModel Log CACHE: Delete cache for #{model_name}\/(#{ids.join('|')})-.*"
|
125
139
|
self.cache_store.delete_matched(/#{model_name}\/(#{ids.join('|')})-.*/)
|
140
|
+
#TODO: also delete cache for parent (belongs_to)
|
126
141
|
delete_multiple_without_cache(ids, params)
|
127
142
|
end
|
128
143
|
alias_method_chain :delete_multiple, :cache
|
129
144
|
end
|
130
|
-
|
131
145
|
end
|
132
146
|
end
|
data/logical_model.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = "logical_model"
|
8
|
-
s.version = "0.
|
8
|
+
s.version = "0.6.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Dwayne Macgowan"]
|
12
|
-
s.date = "2014-06-
|
12
|
+
s.date = "2014-06-25"
|
13
13
|
s.description = "LogicalModel allows to use a resource as a model. It is based on web presentation http://www.slideshare.net/ihower/serviceoriented-design-and-implement-with-rails3"
|
14
14
|
s.email = "dwaynemac@gmail.com"
|
15
15
|
s.extra_rdoc_files = [
|
@@ -1,17 +1,19 @@
|
|
1
1
|
require './lib/logical_model'
|
2
2
|
|
3
3
|
describe LogicalModel::Cache do
|
4
|
+
class Example < LogicalModel
|
5
|
+
|
6
|
+
attribute :id
|
7
|
+
attribute :name
|
8
|
+
|
9
|
+
self.hydra = Typhoeus::Hydra.new
|
10
|
+
|
11
|
+
self.enable_delete_multiple = true
|
12
|
+
end
|
13
|
+
|
4
14
|
describe "when included" do
|
5
15
|
before do
|
6
|
-
|
7
|
-
|
8
|
-
attribute :id
|
9
|
-
attribute :name
|
10
|
-
|
11
|
-
self.hydra = Typhoeus::Hydra.new
|
12
|
-
|
13
|
-
self.enable_delete_multiple = true
|
14
|
-
end
|
16
|
+
|
15
17
|
end
|
16
18
|
|
17
19
|
it "adds expires_in class method" do
|
@@ -133,4 +135,59 @@ describe LogicalModel::Cache do
|
|
133
135
|
end
|
134
136
|
end
|
135
137
|
end
|
138
|
+
|
139
|
+
describe "when using has_many & belongs_to" do
|
140
|
+
|
141
|
+
class SecondaryExample < LogicalModel
|
142
|
+
attribute :id
|
143
|
+
|
144
|
+
self.hydra = Typhoeus::Hydra.new
|
145
|
+
|
146
|
+
self.enable_delete_multiple = true
|
147
|
+
|
148
|
+
belongs_to :example
|
149
|
+
end
|
150
|
+
|
151
|
+
class SecondaryExampleChild < SecondaryExample
|
152
|
+
attribute :name
|
153
|
+
end
|
154
|
+
|
155
|
+
before do
|
156
|
+
Example.has_many_keys = [:secondary_examples]
|
157
|
+
end
|
158
|
+
|
159
|
+
it "should set belongs_to_keys" do
|
160
|
+
SecondaryExampleChild.belongs_to_keys.should_not be_blank
|
161
|
+
end
|
162
|
+
|
163
|
+
describe "save" do
|
164
|
+
before do
|
165
|
+
Example.stub_chain(:cache_store, :read).and_return(Example.new)
|
166
|
+
SecondaryExampleChild.stub_chain(:cache_store, :read).and_return(SecondaryExampleChild.new(:example_id => 123))
|
167
|
+
Example.stub_chain(:cache_store, :delete_matched).and_return(nil)
|
168
|
+
SecondaryExampleChild.stub_chain(:cache_store, :delete_matched).and_return(nil)
|
169
|
+
SecondaryExampleChild.async_find("id") {|r| @result = r}
|
170
|
+
end
|
171
|
+
|
172
|
+
it "should clear cache" do
|
173
|
+
SecondaryExampleChild.cache_store.should_receive(:delete_matched).with(/examples\/123-.*/)
|
174
|
+
@result.save
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
describe "adding a new model to has_many" do
|
179
|
+
before do
|
180
|
+
Example.stub_chain(:cache_store, :read).and_return(Example.new(:id => 123))
|
181
|
+
SecondaryExampleChild.stub_chain(:cache_store, :read).and_return(SecondaryExampleChild.new(:example_id => 123))
|
182
|
+
Example.stub_chain(:cache_store, :delete_matched).and_return(nil)
|
183
|
+
SecondaryExampleChild.stub_chain(:cache_store, :delete_matched).and_return(nil)
|
184
|
+
Example.async_find("123") {|r| @result = r}
|
185
|
+
end
|
186
|
+
|
187
|
+
it "should clear cache" do
|
188
|
+
Example.cache_store.should_receive(:delete_matched).with(/examples\/123-.*/)
|
189
|
+
@result.new_secondary_example(:example_id => 123)
|
190
|
+
end
|
191
|
+
end
|
192
|
+
end
|
136
193
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: logical_model
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.6.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2014-06-
|
12
|
+
date: 2014-06-25 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: activemodel
|
@@ -393,7 +393,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
393
393
|
version: '0'
|
394
394
|
segments:
|
395
395
|
- 0
|
396
|
-
hash: -
|
396
|
+
hash: -732207341
|
397
397
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
398
398
|
none: false
|
399
399
|
requirements:
|