json_api_client 1.22.0 → 1.24.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.
Files changed (48) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE +20 -20
  3. data/README.md +723 -705
  4. data/Rakefile +32 -32
  5. data/lib/json_api_client/associations/base_association.rb +33 -33
  6. data/lib/json_api_client/associations/belongs_to.rb +31 -31
  7. data/lib/json_api_client/associations/has_many.rb +7 -7
  8. data/lib/json_api_client/associations/has_one.rb +16 -16
  9. data/lib/json_api_client/associations.rb +7 -7
  10. data/lib/json_api_client/connection.rb +41 -41
  11. data/lib/json_api_client/error_collector.rb +91 -91
  12. data/lib/json_api_client/errors.rb +125 -125
  13. data/lib/json_api_client/formatter.rb +145 -145
  14. data/lib/json_api_client/helpers/associatable.rb +88 -88
  15. data/lib/json_api_client/helpers/callbacks.rb +27 -27
  16. data/lib/json_api_client/helpers/dirty.rb +75 -75
  17. data/lib/json_api_client/helpers/dynamic_attributes.rb +78 -78
  18. data/lib/json_api_client/helpers/uri.rb +9 -9
  19. data/lib/json_api_client/helpers.rb +9 -9
  20. data/lib/json_api_client/implementation.rb +11 -11
  21. data/lib/json_api_client/included_data.rb +58 -58
  22. data/lib/json_api_client/linking/links.rb +21 -21
  23. data/lib/json_api_client/linking/top_level_links.rb +39 -39
  24. data/lib/json_api_client/linking.rb +5 -5
  25. data/lib/json_api_client/meta_data.rb +19 -19
  26. data/lib/json_api_client/middleware/json_request.rb +26 -26
  27. data/lib/json_api_client/middleware/status.rb +67 -67
  28. data/lib/json_api_client/middleware.rb +6 -7
  29. data/lib/json_api_client/paginating/nested_param_paginator.rb +140 -140
  30. data/lib/json_api_client/paginating/paginator.rb +89 -89
  31. data/lib/json_api_client/paginating.rb +6 -6
  32. data/lib/json_api_client/parsers/parser.rb +102 -102
  33. data/lib/json_api_client/parsers.rb +4 -4
  34. data/lib/json_api_client/query/builder.rb +239 -239
  35. data/lib/json_api_client/query/requestor.rb +73 -73
  36. data/lib/json_api_client/query.rb +5 -5
  37. data/lib/json_api_client/relationships/relations.rb +55 -55
  38. data/lib/json_api_client/relationships/top_level_relations.rb +30 -30
  39. data/lib/json_api_client/relationships.rb +5 -5
  40. data/lib/json_api_client/request_params.rb +57 -57
  41. data/lib/json_api_client/resource.rb +671 -658
  42. data/lib/json_api_client/result_set.rb +25 -25
  43. data/lib/json_api_client/schema.rb +154 -154
  44. data/lib/json_api_client/utils.rb +53 -53
  45. data/lib/json_api_client/version.rb +3 -3
  46. data/lib/json_api_client.rb +30 -30
  47. metadata +74 -36
  48. data/lib/json_api_client/middleware/parse_json.rb +0 -31
@@ -1,125 +1,125 @@
1
- require 'rack'
2
-
3
- module JsonApiClient
4
- module Errors
5
- class ApiError < StandardError
6
- attr_reader :env
7
-
8
- def initialize(env, msg = nil)
9
- @env = env
10
- # Try to fetch json_api errors from response
11
- msg = track_json_api_errors(msg)
12
-
13
- super msg
14
- end
15
-
16
- private
17
-
18
- # Try to fetch json_api errors from response
19
- def track_json_api_errors(msg)
20
- return msg unless env.try(:body).kind_of?(Hash) || env.body.key?('errors')
21
-
22
- errors_msg = env.body['errors'].map { |e| e['title'] }.compact.join('; ').presence
23
- return msg unless errors_msg
24
-
25
- msg.nil? ? errors_msg : "#{msg} (#{errors_msg})"
26
- # Just to be sure that it is back compatible
27
- rescue StandardError
28
- msg
29
- end
30
- end
31
-
32
- class ClientError < ApiError
33
- end
34
-
35
- class ResourceImmutableError < StandardError
36
- def initialize(msg = 'Resource immutable')
37
- super msg
38
- end
39
- end
40
-
41
- class AccessDenied < ClientError
42
- end
43
-
44
- class NotAuthorized < ClientError
45
- end
46
-
47
- class NotFound < ClientError
48
- attr_reader :uri
49
- def initialize(env_or_uri, msg = nil)
50
- env = nil
51
-
52
- if env_or_uri.kind_of?(Faraday::Env)
53
- env = env_or_uri
54
- @uri = env[:url]
55
- else
56
- @uri = env_or_uri
57
- end
58
-
59
- msg ||= "Resource not found: #{uri.to_s}"
60
- super env, msg
61
- end
62
- end
63
-
64
- class RequestTimeout < ClientError
65
- end
66
-
67
- class Conflict < ClientError
68
- def initialize(env, msg = 'Resource already exists')
69
- super env, msg
70
- end
71
- end
72
-
73
- class TooManyRequests < ClientError
74
- end
75
-
76
- class ConnectionError < ApiError
77
- end
78
-
79
- class ServerError < ApiError
80
- def initialize(env, msg = nil)
81
- msg ||= begin
82
- status = env.status
83
- message = ::Rack::Utils::HTTP_STATUS_CODES[status]
84
- "#{status} #{message}"
85
- end
86
-
87
- super env, msg
88
- end
89
- end
90
-
91
- class InternalServerError < ServerError
92
- end
93
-
94
- class BadGateway < ServerError
95
- end
96
-
97
- class ServiceUnavailable < ServerError
98
- end
99
-
100
- class GatewayTimeout < ServerError
101
- end
102
-
103
- class UnexpectedStatus < ServerError
104
- attr_reader :code, :uri
105
- def initialize(code, uri)
106
- @code = code
107
- @uri = uri
108
-
109
- msg = "Unexpected response status: #{code} from: #{uri.to_s}"
110
- super nil, msg
111
- end
112
- end
113
-
114
- class RecordNotSaved < ServerError
115
- attr_reader :record
116
-
117
- def initialize(message = nil, record = nil)
118
- @record = record
119
- end
120
- def message
121
- "Record not saved"
122
- end
123
- end
124
- end
125
- end
1
+ require 'rack'
2
+
3
+ module JsonApiClient
4
+ module Errors
5
+ class ApiError < StandardError
6
+ attr_reader :env
7
+
8
+ def initialize(env, msg = nil)
9
+ @env = env
10
+ # Try to fetch json_api errors from response
11
+ msg = track_json_api_errors(msg)
12
+
13
+ super msg
14
+ end
15
+
16
+ private
17
+
18
+ # Try to fetch json_api errors from response
19
+ def track_json_api_errors(msg)
20
+ return msg unless env.try(:body).kind_of?(Hash) || env.body.key?('errors')
21
+
22
+ errors_msg = env.body['errors'].map { |e| e['title'] }.compact.join('; ').presence
23
+ return msg unless errors_msg
24
+
25
+ msg.nil? ? errors_msg : "#{msg} (#{errors_msg})"
26
+ # Just to be sure that it is back compatible
27
+ rescue StandardError
28
+ msg
29
+ end
30
+ end
31
+
32
+ class ClientError < ApiError
33
+ end
34
+
35
+ class ResourceImmutableError < StandardError
36
+ def initialize(msg = 'Resource immutable')
37
+ super msg
38
+ end
39
+ end
40
+
41
+ class AccessDenied < ClientError
42
+ end
43
+
44
+ class NotAuthorized < ClientError
45
+ end
46
+
47
+ class NotFound < ClientError
48
+ attr_reader :uri
49
+ def initialize(env_or_uri, msg = nil)
50
+ env = nil
51
+
52
+ if env_or_uri.kind_of?(Faraday::Env)
53
+ env = env_or_uri
54
+ @uri = env[:url]
55
+ else
56
+ @uri = env_or_uri
57
+ end
58
+
59
+ msg ||= "Resource not found: #{uri.to_s}"
60
+ super env, msg
61
+ end
62
+ end
63
+
64
+ class RequestTimeout < ClientError
65
+ end
66
+
67
+ class Conflict < ClientError
68
+ def initialize(env, msg = 'Resource already exists')
69
+ super env, msg
70
+ end
71
+ end
72
+
73
+ class TooManyRequests < ClientError
74
+ end
75
+
76
+ class ConnectionError < ApiError
77
+ end
78
+
79
+ class ServerError < ApiError
80
+ def initialize(env, msg = nil)
81
+ msg ||= begin
82
+ status = env.status
83
+ message = ::Rack::Utils::HTTP_STATUS_CODES[status]
84
+ "#{status} #{message}"
85
+ end
86
+
87
+ super env, msg
88
+ end
89
+ end
90
+
91
+ class InternalServerError < ServerError
92
+ end
93
+
94
+ class BadGateway < ServerError
95
+ end
96
+
97
+ class ServiceUnavailable < ServerError
98
+ end
99
+
100
+ class GatewayTimeout < ServerError
101
+ end
102
+
103
+ class UnexpectedStatus < ServerError
104
+ attr_reader :code, :uri
105
+ def initialize(code, uri)
106
+ @code = code
107
+ @uri = uri
108
+
109
+ msg = "Unexpected response status: #{code} from: #{uri.to_s}"
110
+ super nil, msg
111
+ end
112
+ end
113
+
114
+ class RecordNotSaved < ServerError
115
+ attr_reader :record
116
+
117
+ def initialize(message = nil, record = nil)
118
+ @record = record
119
+ end
120
+ def message
121
+ "Record not saved"
122
+ end
123
+ end
124
+ end
125
+ end
@@ -1,145 +1,145 @@
1
- # Taken form jsonapi_resources formatter
2
-
3
- require 'active_support/inflector'
4
-
5
- module JsonApiClient
6
- class Formatter
7
- class << self
8
- def format(arg)
9
- arg.to_s
10
- end
11
-
12
- def unformat(arg)
13
- # We call to_s() here so that unformat consistently returns a string
14
- # (instead of a symbol) regardless which Formatter subclass it is called on
15
- arg.to_s
16
- end
17
-
18
- def formatter_for(format)
19
- formatter_class_name = "JsonApiClient::#{format.to_s.camelize}Formatter"
20
- formatter_class_name.safe_constantize
21
- end
22
- end
23
- end
24
-
25
- class KeyFormatter < Formatter
26
- class << self
27
- def format(key)
28
- super
29
- end
30
-
31
- def format_keys(hash)
32
- Hash[
33
- hash.map do |key, value|
34
- [format(key).to_sym, value]
35
- end
36
- ]
37
- end
38
-
39
- def unformat(formatted_key)
40
- super
41
- end
42
- end
43
- end
44
-
45
- class RouteFormatter < Formatter
46
- class << self
47
- def format(route)
48
- super
49
- end
50
-
51
- def unformat(formatted_route)
52
- super
53
- end
54
- end
55
- end
56
-
57
- class ValueFormatter < Formatter
58
- class << self
59
- def format(raw_value)
60
- super(raw_value)
61
- end
62
-
63
- def unformat(value)
64
- super(value)
65
- end
66
-
67
- def value_formatter_for(type)
68
- formatter_name = "#{type.to_s.camelize}Value"
69
- formatter_for(formatter_name)
70
- end
71
- end
72
- end
73
-
74
- class UnderscoredKeyFormatter < KeyFormatter
75
- end
76
-
77
- class CamelizedKeyFormatter < KeyFormatter
78
- class << self
79
- def format(key)
80
- super.camelize(:lower)
81
- end
82
-
83
- def unformat(formatted_key)
84
- formatted_key.to_s.underscore
85
- end
86
- end
87
- end
88
-
89
- class DasherizedKeyFormatter < KeyFormatter
90
- class << self
91
- def format(key)
92
- super.dasherize
93
- end
94
-
95
- def unformat(formatted_key)
96
- formatted_key.to_s.underscore
97
- end
98
- end
99
- end
100
-
101
- class DefaultValueFormatter < ValueFormatter
102
- class << self
103
- def format(raw_value)
104
- raw_value
105
- end
106
- end
107
- end
108
-
109
- class IdValueFormatter < ValueFormatter
110
- class << self
111
- def format(raw_value)
112
- return if raw_value.nil?
113
- raw_value.to_s
114
- end
115
- end
116
- end
117
-
118
- class UnderscoredRouteFormatter < RouteFormatter
119
- end
120
-
121
- class CamelizedRouteFormatter < RouteFormatter
122
- class << self
123
- def format(route)
124
- super.camelize(:lower)
125
- end
126
-
127
- def unformat(formatted_route)
128
- formatted_route.to_s.underscore
129
- end
130
- end
131
- end
132
-
133
- class DasherizedRouteFormatter < RouteFormatter
134
- class << self
135
- def format(route)
136
- super.dasherize
137
- end
138
-
139
- def unformat(formatted_route)
140
- formatted_route.to_s.underscore
141
- end
142
- end
143
- end
144
-
145
- end
1
+ # Taken form jsonapi_resources formatter
2
+
3
+ require 'active_support/inflector'
4
+
5
+ module JsonApiClient
6
+ class Formatter
7
+ class << self
8
+ def format(arg)
9
+ arg.to_s
10
+ end
11
+
12
+ def unformat(arg)
13
+ # We call to_s() here so that unformat consistently returns a string
14
+ # (instead of a symbol) regardless which Formatter subclass it is called on
15
+ arg.to_s
16
+ end
17
+
18
+ def formatter_for(format)
19
+ formatter_class_name = "JsonApiClient::#{format.to_s.camelize}Formatter"
20
+ formatter_class_name.safe_constantize
21
+ end
22
+ end
23
+ end
24
+
25
+ class KeyFormatter < Formatter
26
+ class << self
27
+ def format(key)
28
+ super
29
+ end
30
+
31
+ def format_keys(hash)
32
+ Hash[
33
+ hash.map do |key, value|
34
+ [format(key).to_sym, value]
35
+ end
36
+ ]
37
+ end
38
+
39
+ def unformat(formatted_key)
40
+ super
41
+ end
42
+ end
43
+ end
44
+
45
+ class RouteFormatter < Formatter
46
+ class << self
47
+ def format(route)
48
+ super
49
+ end
50
+
51
+ def unformat(formatted_route)
52
+ super
53
+ end
54
+ end
55
+ end
56
+
57
+ class ValueFormatter < Formatter
58
+ class << self
59
+ def format(raw_value)
60
+ super(raw_value)
61
+ end
62
+
63
+ def unformat(value)
64
+ super(value)
65
+ end
66
+
67
+ def value_formatter_for(type)
68
+ formatter_name = "#{type.to_s.camelize}Value"
69
+ formatter_for(formatter_name)
70
+ end
71
+ end
72
+ end
73
+
74
+ class UnderscoredKeyFormatter < KeyFormatter
75
+ end
76
+
77
+ class CamelizedKeyFormatter < KeyFormatter
78
+ class << self
79
+ def format(key)
80
+ super.camelize(:lower)
81
+ end
82
+
83
+ def unformat(formatted_key)
84
+ formatted_key.to_s.underscore
85
+ end
86
+ end
87
+ end
88
+
89
+ class DasherizedKeyFormatter < KeyFormatter
90
+ class << self
91
+ def format(key)
92
+ super.dasherize
93
+ end
94
+
95
+ def unformat(formatted_key)
96
+ formatted_key.to_s.underscore
97
+ end
98
+ end
99
+ end
100
+
101
+ class DefaultValueFormatter < ValueFormatter
102
+ class << self
103
+ def format(raw_value)
104
+ raw_value
105
+ end
106
+ end
107
+ end
108
+
109
+ class IdValueFormatter < ValueFormatter
110
+ class << self
111
+ def format(raw_value)
112
+ return if raw_value.nil?
113
+ raw_value.to_s
114
+ end
115
+ end
116
+ end
117
+
118
+ class UnderscoredRouteFormatter < RouteFormatter
119
+ end
120
+
121
+ class CamelizedRouteFormatter < RouteFormatter
122
+ class << self
123
+ def format(route)
124
+ super.camelize(:lower)
125
+ end
126
+
127
+ def unformat(formatted_route)
128
+ formatted_route.to_s.underscore
129
+ end
130
+ end
131
+ end
132
+
133
+ class DasherizedRouteFormatter < RouteFormatter
134
+ class << self
135
+ def format(route)
136
+ super.dasherize
137
+ end
138
+
139
+ def unformat(formatted_route)
140
+ formatted_route.to_s.underscore
141
+ end
142
+ end
143
+ end
144
+
145
+ end