morpheus 0.4.0 → 0.5.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/.rspec +1 -1
- data/CHANGELOG.md +17 -0
- data/Gemfile +1 -1
- data/lib/morpheus.rb +3 -23
- data/lib/morpheus/base.rb +11 -11
- data/lib/morpheus/client.rb +10 -0
- data/lib/morpheus/client/associations.rb +6 -6
- data/lib/morpheus/client/cached_request_formatter.rb +20 -0
- data/lib/morpheus/client/log_subscriber.rb +2 -28
- data/lib/morpheus/client/railtie.rb +4 -4
- data/lib/morpheus/client/request_formatter.rb +50 -0
- data/lib/morpheus/client/uncached_request_formatter.rb +40 -0
- data/lib/morpheus/configuration.rb +30 -9
- data/lib/morpheus/mixins.rb +16 -0
- data/lib/morpheus/mixins/associations.rb +39 -37
- data/lib/morpheus/mixins/associations/association.rb +112 -0
- data/lib/morpheus/mixins/associations/belongs_to_association.rb +47 -0
- data/lib/morpheus/mixins/associations/has_many_association.rb +72 -0
- data/lib/morpheus/mixins/associations/has_one_association.rb +48 -0
- data/lib/morpheus/mixins/attributes.rb +97 -95
- data/lib/morpheus/mixins/conversion.rb +16 -14
- data/lib/morpheus/mixins/filtering.rb +13 -11
- data/lib/morpheus/mixins/finders.rb +47 -45
- data/lib/morpheus/mixins/introspection.rb +15 -13
- data/lib/morpheus/mixins/persistence.rb +32 -30
- data/lib/morpheus/mixins/reflections.rb +17 -15
- data/lib/morpheus/mixins/request_handling.rb +27 -25
- data/lib/morpheus/mixins/response_parsing.rb +10 -8
- data/lib/morpheus/mixins/url_support.rb +27 -25
- data/lib/morpheus/reflection.rb +5 -2
- data/lib/morpheus/type_caster.rb +1 -1
- data/lib/morpheus/version.rb +1 -1
- data/morpheus.gemspec +2 -2
- data/spec/dummy/app/resources/book.rb +1 -1
- data/spec/morpheus/base_spec.rb +35 -35
- data/spec/morpheus/client/cached_request_formatter_spec.rb +28 -0
- data/spec/morpheus/client/log_subscriber_spec.rb +53 -10
- data/spec/morpheus/client/request_formatter_spec.rb +5 -0
- data/spec/morpheus/client/uncached_request_formatter_spec.rb +29 -0
- data/spec/morpheus/configuration_spec.rb +49 -11
- data/spec/morpheus/{associations → mixins/associations}/association_spec.rb +1 -1
- data/spec/morpheus/{associations → mixins/associations}/belongs_to_association_spec.rb +1 -1
- data/spec/morpheus/{associations → mixins/associations}/has_many_association_spec.rb +1 -1
- data/spec/morpheus/{associations → mixins/associations}/has_one_association_spec.rb +1 -1
- data/spec/morpheus/mixins/associations_spec.rb +1 -1
- data/spec/morpheus/mixins/attributes_spec.rb +27 -6
- data/spec/morpheus/mixins/conversion_spec.rb +1 -1
- data/spec/morpheus/mixins/filtering_spec.rb +2 -2
- data/spec/morpheus/mixins/finders_spec.rb +1 -1
- data/spec/morpheus/mixins/introspection_spec.rb +1 -1
- data/spec/morpheus/mixins/persistence_spec.rb +1 -1
- data/spec/morpheus/mixins/reflections_spec.rb +1 -1
- data/spec/morpheus/mixins/request_handling_spec.rb +2 -2
- data/spec/morpheus/mixins/response_parsing_spec.rb +2 -2
- data/spec/morpheus/mixins/url_support_spec.rb +2 -2
- data/spec/morpheus/response_parser_spec.rb +5 -1
- data/spec/regressions/sorting_resources_spec.rb +119 -0
- data/spec/spec_helper.rb +3 -2
- metadata +159 -87
- data/lib/morpheus/associations/association.rb +0 -110
- data/lib/morpheus/associations/belongs_to_association.rb +0 -45
- data/lib/morpheus/associations/has_many_association.rb +0 -70
- data/lib/morpheus/associations/has_one_association.rb +0 -46
@@ -1,22 +1,24 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Conversion
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def to_model
|
6
|
+
self
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
-
|
10
|
-
|
9
|
+
def to_param
|
10
|
+
id.to_s unless new_record?
|
11
|
+
end
|
11
12
|
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
def to_key
|
14
|
+
attributes.keys if persisted?
|
15
|
+
end
|
15
16
|
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
17
|
+
def to_partial_path
|
18
|
+
underscored_model_name = self.class.model_name.underscore
|
19
|
+
"#{underscored_model_name.pluralize}/#{underscored_model_name}"
|
20
|
+
end
|
20
21
|
|
22
|
+
end
|
21
23
|
end
|
22
24
|
end
|
@@ -1,21 +1,23 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Filtering
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
11
|
+
def filter(name, &block)
|
12
|
+
(@filters ||= []) << Filter.new(name, &block)
|
13
|
+
end
|
14
|
+
|
15
|
+
def find_filter(name)
|
16
|
+
(@filters ||= []).find { |filter| filter.name == name }
|
17
|
+
end
|
13
18
|
|
14
|
-
def find_filter(name)
|
15
|
-
(@filters ||= []).find { |filter| filter.name == name }
|
16
19
|
end
|
17
20
|
|
18
21
|
end
|
19
|
-
|
20
22
|
end
|
21
23
|
end
|
@@ -1,65 +1,67 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Finders
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
11
|
+
def find(*args)
|
12
|
+
options = args.extract_options!
|
13
|
+
if args.length == 1
|
14
|
+
case args.first
|
15
|
+
when Integer, String
|
16
|
+
attributes = [UrlBuilder.find_one(self, args.first.to_i), nil, { :id => args.first.to_i }]
|
17
|
+
get(*attributes)
|
18
|
+
when Array
|
19
|
+
attributes = UrlBuilder.find_some(self, args.first.sort).push({ :ids => args.first })
|
20
|
+
get(*attributes)
|
21
|
+
else
|
22
|
+
raise ArgumentError, "Unrecognized argument (#{args.first.inspect})."
|
23
|
+
end
|
20
24
|
else
|
21
|
-
|
25
|
+
attributes = UrlBuilder.find_some(self, args.sort).push({ :ids => args })
|
26
|
+
get(*attributes)
|
22
27
|
end
|
23
|
-
else
|
24
|
-
attributes = UrlBuilder.find_some(self, args.sort).push({ :ids => args })
|
25
|
-
get(*attributes)
|
26
28
|
end
|
27
|
-
end
|
28
29
|
|
29
|
-
|
30
|
-
|
31
|
-
|
30
|
+
def scoped
|
31
|
+
Relation.new(self)
|
32
|
+
end
|
32
33
|
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
34
|
+
def all
|
35
|
+
attributes = [UrlBuilder.find_all(self), nil, {}]
|
36
|
+
get(*attributes)
|
37
|
+
end
|
37
38
|
|
38
|
-
|
39
|
-
|
40
|
-
|
39
|
+
def first
|
40
|
+
limit(1).first
|
41
|
+
end
|
41
42
|
|
42
|
-
|
43
|
-
|
44
|
-
|
43
|
+
def where(query_attributes)
|
44
|
+
Relation.new(self).where(query_attributes)
|
45
|
+
end
|
45
46
|
|
46
|
-
|
47
|
-
|
48
|
-
|
47
|
+
def limit(amount)
|
48
|
+
Relation.new(self).limit(amount)
|
49
|
+
end
|
49
50
|
|
50
|
-
|
51
|
-
|
52
|
-
|
51
|
+
def page(page_number)
|
52
|
+
Relation.new(self).page(page_number)
|
53
|
+
end
|
53
54
|
|
54
|
-
|
55
|
-
|
56
|
-
|
55
|
+
def results_per_page
|
56
|
+
@results_per_page || 10
|
57
|
+
end
|
58
|
+
|
59
|
+
def results_per_page=(_results_per_page)
|
60
|
+
@results_per_page = _results_per_page
|
61
|
+
end
|
57
62
|
|
58
|
-
def results_per_page=(_results_per_page)
|
59
|
-
@results_per_page = _results_per_page
|
60
63
|
end
|
61
64
|
|
62
65
|
end
|
63
|
-
|
64
66
|
end
|
65
67
|
end
|
@@ -1,21 +1,23 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Introspection
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def persisted?
|
6
|
+
!id.nil?
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
-
|
10
|
-
|
9
|
+
def new_record?
|
10
|
+
!persisted?
|
11
|
+
end
|
11
12
|
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
def destroyed?
|
14
|
+
false
|
15
|
+
end
|
15
16
|
|
16
|
-
|
17
|
-
|
18
|
-
|
17
|
+
def respond_to?(method, include_private = false)
|
18
|
+
attributes.include?(method) ? true : super
|
19
|
+
end
|
19
20
|
|
21
|
+
end
|
20
22
|
end
|
21
23
|
end
|
@@ -1,45 +1,47 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Persistence
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
end
|
7
|
-
|
8
|
-
def save(with_validations = true)
|
9
|
-
attributes_for_save = { self.class.attributes_root => attributes_without_basic_attributes.reject { |k,v| v.nil? } }
|
10
|
-
|
11
|
-
if with_validations
|
12
|
-
return false unless valid?
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
13
7
|
end
|
14
8
|
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
9
|
+
def save(with_validations = true)
|
10
|
+
attributes_for_save = { self.class.attributes_root => attributes_without_basic_attributes.reject { |k,v| v.nil? } }
|
11
|
+
|
12
|
+
if with_validations
|
13
|
+
return false unless valid?
|
14
|
+
end
|
15
|
+
|
16
|
+
if new_record?
|
17
|
+
built_object = self.class.post(*UrlBuilder.save(self.class, nil, attributes_for_save))
|
18
|
+
else
|
19
|
+
built_object = self.class.put(*UrlBuilder.save(self.class, id, attributes_for_save))
|
20
|
+
end
|
21
|
+
built_object.instance_variables.each do |iv|
|
22
|
+
self.instance_variable_set(iv, built_object.instance_variable_get(iv))
|
23
|
+
end
|
24
|
+
@valid
|
19
25
|
end
|
20
|
-
|
21
|
-
|
26
|
+
|
27
|
+
def update_attributes(new_attributes)
|
28
|
+
merge_attributes(new_attributes)
|
29
|
+
save
|
22
30
|
end
|
23
|
-
@valid
|
24
|
-
end
|
25
31
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
end
|
32
|
+
def destroy
|
33
|
+
self.class.delete(UrlBuilder.destroy(self.class, id))
|
34
|
+
end
|
30
35
|
|
31
|
-
|
32
|
-
self.class.delete(UrlBuilder.destroy(self.class, id))
|
33
|
-
end
|
36
|
+
module ClassMethods
|
34
37
|
|
35
|
-
|
38
|
+
def create(new_attributes = {})
|
39
|
+
new(new_attributes).tap { |new_instance| new_instance.save }
|
40
|
+
end
|
41
|
+
alias :create! :create
|
36
42
|
|
37
|
-
def create(new_attributes = {})
|
38
|
-
new(new_attributes).tap { |new_instance| new_instance.save }
|
39
43
|
end
|
40
|
-
alias :create! :create
|
41
44
|
|
42
45
|
end
|
43
|
-
|
44
46
|
end
|
45
47
|
end
|
@@ -1,27 +1,29 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module Reflections
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
11
|
+
def create_reflection(macro, name, options)
|
12
|
+
Reflection.new(macro, name, options).tap do |reflection|
|
13
|
+
reflections.merge!(name => reflection)
|
14
|
+
end
|
13
15
|
end
|
14
|
-
end
|
15
16
|
|
16
|
-
|
17
|
-
|
18
|
-
|
17
|
+
def reflections
|
18
|
+
@reflections ||= {}
|
19
|
+
end
|
20
|
+
|
21
|
+
def reflect_on_association(association)
|
22
|
+
reflections[association.to_sym].is_a?(Reflection) ? reflections[association.to_sym] : nil
|
23
|
+
end
|
19
24
|
|
20
|
-
def reflect_on_association(association)
|
21
|
-
reflections[association.to_sym].is_a?(Reflection) ? reflections[association.to_sym] : nil
|
22
25
|
end
|
23
26
|
|
24
27
|
end
|
25
|
-
|
26
28
|
end
|
27
29
|
end
|
@@ -1,37 +1,39 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module RequestHandling
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
11
|
+
def get(path, params = nil, metadata = {}, &block)
|
12
|
+
request = Request.enqueue(:get, path, params)
|
13
|
+
request.on_complete = block if block_given?
|
14
|
+
response_from_request(request, metadata)
|
15
|
+
end
|
15
16
|
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
17
|
+
def post(path, params = nil, metadata = {}, &block)
|
18
|
+
request = Request.enqueue(:post, path, params)
|
19
|
+
request.on_complete = block if block_given?
|
20
|
+
response_from_request(request, metadata)
|
21
|
+
end
|
21
22
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
23
|
+
def put(path, params = nil, metadata = {}, &block)
|
24
|
+
request = Request.enqueue(:put, path, params)
|
25
|
+
request.on_complete = block if block_given?
|
26
|
+
response_from_request(request, metadata)
|
27
|
+
end
|
28
|
+
|
29
|
+
def delete(path, params = nil, metadata = {}, &block)
|
30
|
+
request = Request.enqueue(:delete, path, params)
|
31
|
+
request.on_complete = block if block_given?
|
32
|
+
response_from_request(request, metadata)
|
33
|
+
end
|
27
34
|
|
28
|
-
def delete(path, params = nil, metadata = {}, &block)
|
29
|
-
request = Request.enqueue(:delete, path, params)
|
30
|
-
request.on_complete = block if block_given?
|
31
|
-
response_from_request(request, metadata)
|
32
35
|
end
|
33
36
|
|
34
37
|
end
|
35
|
-
|
36
38
|
end
|
37
39
|
end
|
@@ -1,16 +1,18 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module ResponseParsing
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
11
|
+
def response_from_request(request, metadata)
|
12
|
+
ResponseParser.parse(self, request, metadata)
|
13
|
+
end
|
13
14
|
|
15
|
+
end
|
14
16
|
end
|
15
17
|
end
|
16
18
|
end
|
@@ -1,39 +1,41 @@
|
|
1
1
|
module Morpheus
|
2
|
-
module
|
2
|
+
module Mixins
|
3
|
+
module UrlSupport
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
|
5
|
+
def self.included(base)
|
6
|
+
base.extend(ClassMethods)
|
7
|
+
end
|
7
8
|
|
8
|
-
|
9
|
+
module ClassMethods
|
9
10
|
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
11
|
+
def url_name
|
12
|
+
@url_name ||= model_name.underscore
|
13
|
+
end
|
14
|
+
alias_method :singular_url_name, :url_name
|
14
15
|
|
15
|
-
|
16
|
-
|
17
|
-
|
16
|
+
def plural_url_name
|
17
|
+
url_name.pluralize
|
18
|
+
end
|
18
19
|
|
19
|
-
|
20
|
-
|
21
|
-
|
20
|
+
def set_base_url(url_name)
|
21
|
+
@url_name = url_name
|
22
|
+
end
|
22
23
|
|
23
|
-
|
24
|
-
|
25
|
-
|
24
|
+
def attributes_root
|
25
|
+
@attributes_root ||= model_name.underscore
|
26
|
+
end
|
26
27
|
|
27
|
-
|
28
|
-
|
29
|
-
|
28
|
+
def set_attributes_root(name)
|
29
|
+
@attributes_root = name
|
30
|
+
end
|
31
|
+
|
32
|
+
def set_base_model_name(name)
|
33
|
+
set_base_url(name)
|
34
|
+
set_attributes_root(name)
|
35
|
+
end
|
30
36
|
|
31
|
-
def set_base_model_name(name)
|
32
|
-
set_base_url(name)
|
33
|
-
set_attributes_root(name)
|
34
37
|
end
|
35
38
|
|
36
39
|
end
|
37
|
-
|
38
40
|
end
|
39
41
|
end
|