grape 0.9.0 → 0.10.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of grape might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/.rubocop.yml +1 -66
- data/.rubocop_todo.yml +78 -17
- data/.travis.yml +7 -3
- data/Appraisals +7 -0
- data/CHANGELOG.md +24 -0
- data/CONTRIBUTING.md +7 -0
- data/Gemfile +1 -7
- data/Guardfile +1 -1
- data/README.md +560 -94
- data/RELEASING.md +1 -1
- data/Rakefile +10 -11
- data/UPGRADING.md +211 -3
- data/gemfiles/rails_3.gemfile +14 -0
- data/gemfiles/rails_4.gemfile +14 -0
- data/grape.gemspec +10 -9
- data/lib/backports/active_support/deep_dup.rb +49 -0
- data/lib/backports/active_support/duplicable.rb +88 -0
- data/lib/grape.rb +29 -2
- data/lib/grape/api.rb +59 -65
- data/lib/grape/dsl/api.rb +19 -0
- data/lib/grape/dsl/callbacks.rb +6 -4
- data/lib/grape/dsl/configuration.rb +49 -5
- data/lib/grape/dsl/helpers.rb +7 -8
- data/lib/grape/dsl/inside_route.rb +22 -10
- data/lib/grape/dsl/middleware.rb +5 -5
- data/lib/grape/dsl/parameters.rb +6 -2
- data/lib/grape/dsl/request_response.rb +23 -20
- data/lib/grape/dsl/routing.rb +52 -49
- data/lib/grape/dsl/settings.rb +110 -0
- data/lib/grape/dsl/validations.rb +14 -6
- data/lib/grape/endpoint.rb +104 -88
- data/lib/grape/exceptions/base.rb +2 -2
- data/lib/grape/exceptions/incompatible_option_values.rb +1 -1
- data/lib/grape/exceptions/invalid_formatter.rb +1 -1
- data/lib/grape/exceptions/invalid_versioner_option.rb +1 -1
- data/lib/grape/exceptions/invalid_with_option_for_represent.rb +1 -1
- data/lib/grape/exceptions/missing_mime_type.rb +1 -1
- data/lib/grape/exceptions/missing_option.rb +1 -1
- data/lib/grape/exceptions/missing_vendor_option.rb +1 -1
- data/lib/grape/exceptions/unknown_options.rb +1 -1
- data/lib/grape/exceptions/unknown_validator.rb +1 -1
- data/lib/grape/exceptions/validation.rb +1 -1
- data/lib/grape/exceptions/validation_errors.rb +2 -2
- data/lib/grape/formatter/serializable_hash.rb +1 -1
- data/lib/grape/formatter/xml.rb +1 -1
- data/lib/grape/locale/en.yml +2 -0
- data/lib/grape/middleware/auth/dsl.rb +26 -21
- data/lib/grape/middleware/auth/strategies.rb +1 -1
- data/lib/grape/middleware/auth/strategy_info.rb +0 -2
- data/lib/grape/middleware/base.rb +2 -2
- data/lib/grape/middleware/error.rb +1 -1
- data/lib/grape/middleware/formatter.rb +5 -5
- data/lib/grape/middleware/versioner.rb +1 -1
- data/lib/grape/middleware/versioner/header.rb +3 -3
- data/lib/grape/middleware/versioner/param.rb +2 -2
- data/lib/grape/middleware/versioner/path.rb +1 -1
- data/lib/grape/namespace.rb +1 -1
- data/lib/grape/path.rb +9 -3
- data/lib/grape/util/content_types.rb +16 -8
- data/lib/grape/util/inheritable_setting.rb +74 -0
- data/lib/grape/util/inheritable_values.rb +51 -0
- data/lib/grape/util/stackable_values.rb +52 -0
- data/lib/grape/util/strict_hash_configuration.rb +106 -0
- data/lib/grape/validations.rb +0 -220
- data/lib/grape/validations/attributes_iterator.rb +21 -0
- data/lib/grape/validations/params_scope.rb +176 -0
- data/lib/grape/validations/validators/all_or_none.rb +20 -0
- data/lib/grape/validations/validators/allow_blank.rb +30 -0
- data/lib/grape/validations/validators/at_least_one_of.rb +20 -0
- data/lib/grape/validations/validators/base.rb +37 -0
- data/lib/grape/validations/{coerce.rb → validators/coerce.rb} +3 -3
- data/lib/grape/validations/{default.rb → validators/default.rb} +1 -1
- data/lib/grape/validations/validators/exactly_one_of.rb +20 -0
- data/lib/grape/validations/validators/multiple_params_base.rb +26 -0
- data/lib/grape/validations/validators/mutual_exclusion.rb +25 -0
- data/lib/grape/validations/{presence.rb → validators/presence.rb} +2 -2
- data/lib/grape/validations/validators/regexp.rb +12 -0
- data/lib/grape/validations/validators/values.rb +26 -0
- data/lib/grape/version.rb +1 -1
- data/spec/grape/api_spec.rb +522 -343
- data/spec/grape/dsl/callbacks_spec.rb +4 -4
- data/spec/grape/dsl/configuration_spec.rb +48 -9
- data/spec/grape/dsl/helpers_spec.rb +6 -13
- data/spec/grape/dsl/inside_route_spec.rb +43 -4
- data/spec/grape/dsl/middleware_spec.rb +1 -10
- data/spec/grape/dsl/parameters_spec.rb +8 -1
- data/spec/grape/dsl/request_response_spec.rb +16 -22
- data/spec/grape/dsl/routing_spec.rb +21 -5
- data/spec/grape/dsl/settings_spec.rb +219 -0
- data/spec/grape/dsl/validations_spec.rb +8 -11
- data/spec/grape/endpoint_spec.rb +115 -86
- data/spec/grape/entity_spec.rb +33 -33
- data/spec/grape/exceptions/invalid_formatter_spec.rb +3 -5
- data/spec/grape/exceptions/invalid_versioner_option_spec.rb +4 -6
- data/spec/grape/exceptions/missing_mime_type_spec.rb +5 -6
- data/spec/grape/exceptions/missing_option_spec.rb +3 -5
- data/spec/grape/exceptions/unknown_options_spec.rb +3 -5
- data/spec/grape/exceptions/unknown_validator_spec.rb +3 -5
- data/spec/grape/exceptions/validation_errors_spec.rb +5 -5
- data/spec/grape/loading_spec.rb +44 -0
- data/spec/grape/middleware/auth/base_spec.rb +0 -4
- data/spec/grape/middleware/auth/dsl_spec.rb +2 -4
- data/spec/grape/middleware/auth/strategies_spec.rb +5 -6
- data/spec/grape/middleware/exception_spec.rb +8 -10
- data/spec/grape/middleware/formatter_spec.rb +13 -15
- data/spec/grape/middleware/versioner/accept_version_header_spec.rb +10 -10
- data/spec/grape/middleware/versioner/header_spec.rb +25 -25
- data/spec/grape/middleware/versioner/param_spec.rb +15 -17
- data/spec/grape/middleware/versioner/path_spec.rb +1 -2
- data/spec/grape/middleware/versioner_spec.rb +0 -1
- data/spec/grape/path_spec.rb +66 -45
- data/spec/grape/util/inheritable_setting_spec.rb +217 -0
- data/spec/grape/util/inheritable_values_spec.rb +63 -0
- data/spec/grape/util/stackable_values_spec.rb +115 -0
- data/spec/grape/util/strict_hash_configuration_spec.rb +38 -0
- data/spec/grape/validations/attributes_iterator_spec.rb +4 -0
- data/spec/grape/validations/params_scope_spec.rb +57 -0
- data/spec/grape/validations/validators/all_or_none_spec.rb +60 -0
- data/spec/grape/validations/validators/allow_blank_spec.rb +170 -0
- data/spec/grape/validations/{at_least_one_of_spec.rb → validators/at_least_one_of_spec.rb} +7 -3
- data/spec/grape/validations/{coerce_spec.rb → validators/coerce_spec.rb} +8 -11
- data/spec/grape/validations/{default_spec.rb → validators/default_spec.rb} +7 -9
- data/spec/grape/validations/{exactly_one_of_spec.rb → validators/exactly_one_of_spec.rb} +15 -11
- data/spec/grape/validations/{mutual_exclusion_spec.rb → validators/mutual_exclusion_spec.rb} +11 -9
- data/spec/grape/validations/{presence_spec.rb → validators/presence_spec.rb} +30 -30
- data/spec/grape/validations/{regexp_spec.rb → validators/regexp_spec.rb} +2 -4
- data/spec/grape/validations/{values_spec.rb → validators/values_spec.rb} +95 -23
- data/spec/grape/validations/{zh-CN.yml → validators/zh-CN.yml} +0 -0
- data/spec/grape/validations_spec.rb +335 -70
- data/spec/shared/versioning_examples.rb +7 -8
- data/spec/spec_helper.rb +2 -0
- data/spec/support/basic_auth_encode_helpers.rb +1 -1
- data/spec/support/content_type_helpers.rb +1 -1
- data/spec/support/versioned_helpers.rb +3 -3
- metadata +80 -33
- data/lib/grape/util/deep_merge.rb +0 -23
- data/lib/grape/util/hash_stack.rb +0 -120
- data/lib/grape/validations/at_least_one_of.rb +0 -25
- data/lib/grape/validations/exactly_one_of.rb +0 -26
- data/lib/grape/validations/mutual_exclusion.rb +0 -25
- data/lib/grape/validations/regexp.rb +0 -12
- data/lib/grape/validations/values.rb +0 -23
- data/spec/grape/util/hash_stack_spec.rb +0 -132
data/lib/grape.rb
CHANGED
@@ -7,11 +7,19 @@ require 'rack/auth/basic'
|
|
7
7
|
require 'rack/auth/digest/md5'
|
8
8
|
require 'hashie'
|
9
9
|
require 'set'
|
10
|
+
require 'active_support/version'
|
10
11
|
require 'active_support/core_ext/hash/indifferent_access'
|
12
|
+
|
13
|
+
if ActiveSupport::VERSION::MAJOR >= 4
|
14
|
+
require 'active_support/core_ext/object/deep_dup'
|
15
|
+
else
|
16
|
+
require_relative 'backports/active_support/deep_dup'
|
17
|
+
end
|
18
|
+
|
11
19
|
require 'active_support/ordered_hash'
|
12
20
|
require 'active_support/core_ext/object/conversions'
|
13
21
|
require 'active_support/core_ext/array/extract_options'
|
14
|
-
require '
|
22
|
+
require 'active_support/core_ext/hash/deep_merge'
|
15
23
|
require 'grape/util/content_types'
|
16
24
|
require 'multi_json'
|
17
25
|
require 'multi_xml'
|
@@ -92,11 +100,16 @@ module Grape
|
|
92
100
|
end
|
93
101
|
|
94
102
|
module Util
|
95
|
-
autoload :
|
103
|
+
autoload :InheritableValues, 'grape/util/inheritable_values'
|
104
|
+
autoload :StackableValues, 'grape/util/stackable_values'
|
105
|
+
autoload :InheritableSetting, 'grape/util/inheritable_setting'
|
106
|
+
autoload :StrictHashConfiguration, 'grape/util/strict_hash_configuration'
|
96
107
|
end
|
97
108
|
|
98
109
|
module DSL
|
110
|
+
autoload :API, 'grape/dsl/api'
|
99
111
|
autoload :Callbacks, 'grape/dsl/callbacks'
|
112
|
+
autoload :Settings, 'grape/dsl/settings'
|
100
113
|
autoload :Configuration, 'grape/dsl/configuration'
|
101
114
|
autoload :InsideRoute, 'grape/dsl/inside_route'
|
102
115
|
autoload :Helpers, 'grape/dsl/helpers'
|
@@ -112,4 +125,18 @@ module Grape
|
|
112
125
|
end
|
113
126
|
end
|
114
127
|
|
128
|
+
require 'grape/validations/validators/base'
|
129
|
+
require 'grape/validations/attributes_iterator'
|
130
|
+
require 'grape/validations/validators/allow_blank'
|
131
|
+
require 'grape/validations/validators/at_least_one_of'
|
132
|
+
require 'grape/validations/validators/coerce'
|
133
|
+
require 'grape/validations/validators/default'
|
134
|
+
require 'grape/validations/validators/exactly_one_of'
|
135
|
+
require 'grape/validations/validators/mutual_exclusion'
|
136
|
+
require 'grape/validations/validators/presence'
|
137
|
+
require 'grape/validations/validators/regexp'
|
138
|
+
require 'grape/validations/validators/values'
|
139
|
+
require 'grape/validations/params_scope'
|
140
|
+
require 'grape/validations/validators/all_or_none'
|
141
|
+
|
115
142
|
require 'grape/version'
|
data/lib/grape/api.rb
CHANGED
@@ -3,23 +3,13 @@ module Grape
|
|
3
3
|
# creating Grape APIs.Users should subclass this
|
4
4
|
# class in order to build an API.
|
5
5
|
class API
|
6
|
-
|
7
|
-
|
8
|
-
include Grape::DSL::Validations
|
9
|
-
include Grape::DSL::Callbacks
|
10
|
-
include Grape::DSL::Configuration
|
11
|
-
include Grape::DSL::Helpers
|
12
|
-
include Grape::DSL::Middleware
|
13
|
-
include Grape::DSL::RequestResponse
|
14
|
-
include Grape::DSL::Routing
|
6
|
+
include Grape::DSL::API
|
15
7
|
|
16
8
|
class << self
|
17
9
|
attr_reader :instance
|
18
|
-
|
19
10
|
LOCK = Mutex.new
|
20
11
|
|
21
12
|
def reset!
|
22
|
-
@settings = Grape::Util::HashStack.new
|
23
13
|
@route_set = Rack::Mount::RouteSet.new
|
24
14
|
@endpoints = []
|
25
15
|
@routes = nil
|
@@ -45,36 +35,21 @@ module Grape
|
|
45
35
|
|
46
36
|
# Create a scope without affecting the URL.
|
47
37
|
#
|
48
|
-
# @param name [Symbol] Purely placebo, just allows to
|
38
|
+
# @param name [Symbol] Purely placebo, just allows to name the scope to make the code more readable.
|
49
39
|
def scope(name = nil, &block)
|
50
|
-
|
40
|
+
within_namespace do
|
41
|
+
nest(block)
|
42
|
+
end
|
51
43
|
end
|
52
44
|
|
53
45
|
def cascade(value = nil)
|
54
46
|
if value.nil?
|
55
|
-
|
47
|
+
inheritable_setting.namespace_inheritable.keys.include?(:cascade) ? !!namespace_inheritable(:cascade) : true
|
56
48
|
else
|
57
|
-
|
49
|
+
namespace_inheritable(:cascade, value)
|
58
50
|
end
|
59
51
|
end
|
60
52
|
|
61
|
-
# Set a configuration value for this namespace.
|
62
|
-
#
|
63
|
-
# @param key [Symbol] The key of the configuration variable.
|
64
|
-
# @param value [Object] The value to which to set the configuration variable.
|
65
|
-
def set(key, value)
|
66
|
-
settings[key.to_sym] = value
|
67
|
-
end
|
68
|
-
|
69
|
-
# Add to a configuration value for this
|
70
|
-
# namespace.
|
71
|
-
#
|
72
|
-
# @param key [Symbol] The key of the configuration variable.
|
73
|
-
# @param value [Object] The value to which to set the configuration variable.
|
74
|
-
def imbue(key, value)
|
75
|
-
settings.imbue(key, value)
|
76
|
-
end
|
77
|
-
|
78
53
|
protected
|
79
54
|
|
80
55
|
def prepare_routes
|
@@ -89,12 +64,10 @@ module Grape
|
|
89
64
|
# block passed in. Allows for simple 'before' setups
|
90
65
|
# of settings stack pushes.
|
91
66
|
def nest(*blocks, &block)
|
92
|
-
blocks.reject!
|
67
|
+
blocks.reject!(&:nil?)
|
93
68
|
if blocks.any?
|
94
|
-
settings.push # create a new context to eval the follow
|
95
69
|
instance_eval(&block) if block_given?
|
96
70
|
blocks.each { |b| instance_eval(&b) }
|
97
|
-
settings.pop # when finished, we pop the context
|
98
71
|
reset_validations!
|
99
72
|
else
|
100
73
|
instance_eval(&block)
|
@@ -106,12 +79,12 @@ module Grape
|
|
106
79
|
subclass.logger = logger.clone
|
107
80
|
end
|
108
81
|
|
109
|
-
def inherit_settings(
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
82
|
+
def inherit_settings(other_settings)
|
83
|
+
top_level_setting.inherit_from other_settings.point_in_time_copy
|
84
|
+
|
85
|
+
endpoints.each(&:reset_routes!)
|
86
|
+
|
87
|
+
@routes = nil
|
115
88
|
end
|
116
89
|
end
|
117
90
|
|
@@ -121,6 +94,7 @@ module Grape
|
|
121
94
|
self.class.endpoints.each do |endpoint|
|
122
95
|
endpoint.mount_in(@route_set)
|
123
96
|
end
|
97
|
+
|
124
98
|
@route_set.freeze
|
125
99
|
end
|
126
100
|
|
@@ -139,8 +113,8 @@ module Grape
|
|
139
113
|
# errors from reaching upstream. This is effectivelly done by unsetting
|
140
114
|
# X-Cascade. Default :cascade is true.
|
141
115
|
def cascade?
|
142
|
-
return !!self.class.
|
143
|
-
return !!self.class.
|
116
|
+
return !!self.class.namespace_inheritable(:cascade) if self.class.inheritable_setting.namespace_inheritable.keys.include?(:cascade)
|
117
|
+
return !!self.class.namespace_inheritable(:version_options)[:cascade] if self.class.namespace_inheritable(:version_options) && self.class.namespace_inheritable(:version_options).key?(:cascade)
|
144
118
|
true
|
145
119
|
end
|
146
120
|
|
@@ -154,6 +128,7 @@ module Grape
|
|
154
128
|
# cannot handle.
|
155
129
|
def add_head_not_allowed_methods_and_options_methods
|
156
130
|
methods_per_path = {}
|
131
|
+
|
157
132
|
self.class.endpoints.each do |endpoint|
|
158
133
|
routes = endpoint.routes
|
159
134
|
routes.each do |route|
|
@@ -166,39 +141,58 @@ module Grape
|
|
166
141
|
# contain already versioning information when using path versioning.
|
167
142
|
# Disable versioning so adding a route won't prepend versioning
|
168
143
|
# informations again.
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
144
|
+
without_root_prefix do
|
145
|
+
without_versioning do
|
146
|
+
methods_per_path.each do |path, methods|
|
147
|
+
allowed_methods = methods.dup
|
148
|
+
unless self.class.namespace_inheritable(:do_not_route_head)
|
149
|
+
allowed_methods |= ['HEAD'] if allowed_methods.include?('GET')
|
150
|
+
end
|
175
151
|
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
152
|
+
allow_header = (['OPTIONS'] | allowed_methods).join(', ')
|
153
|
+
unless self.class.namespace_inheritable(:do_not_route_options)
|
154
|
+
unless allowed_methods.include?('OPTIONS')
|
155
|
+
self.class.options(path, {}) do
|
156
|
+
header 'Allow', allow_header
|
157
|
+
status 204
|
158
|
+
''
|
159
|
+
end
|
183
160
|
end
|
184
161
|
end
|
185
|
-
end
|
186
162
|
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
163
|
+
not_allowed_methods = %w(GET PUT POST DELETE PATCH HEAD) - allowed_methods
|
164
|
+
not_allowed_methods << 'OPTIONS' if self.class.namespace_inheritable(:do_not_route_options)
|
165
|
+
self.class.route(not_allowed_methods, path) do
|
166
|
+
header 'Allow', allow_header
|
167
|
+
status 405
|
168
|
+
''
|
169
|
+
end
|
193
170
|
end
|
194
171
|
end
|
195
172
|
end
|
196
173
|
end
|
197
174
|
|
198
175
|
def without_versioning(&block)
|
199
|
-
self.class.
|
176
|
+
old_version = self.class.namespace_inheritable(:version)
|
177
|
+
old_version_options = self.class.namespace_inheritable(:version_options)
|
178
|
+
|
179
|
+
self.class.namespace_inheritable_to_nil(:version)
|
180
|
+
self.class.namespace_inheritable_to_nil(:version_options)
|
181
|
+
|
200
182
|
yield
|
201
|
-
|
183
|
+
|
184
|
+
self.class.namespace_inheritable(:version, old_version)
|
185
|
+
self.class.namespace_inheritable(:version_options, old_version_options)
|
186
|
+
end
|
187
|
+
|
188
|
+
def without_root_prefix(&block)
|
189
|
+
old_prefix = self.class.namespace_inheritable(:root_prefix)
|
190
|
+
|
191
|
+
self.class.namespace_inheritable_to_nil(:root_prefix)
|
192
|
+
|
193
|
+
yield
|
194
|
+
|
195
|
+
self.class.namespace_inheritable(:root_prefix, old_prefix)
|
202
196
|
end
|
203
197
|
end
|
204
198
|
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'active_support/concern'
|
2
|
+
|
3
|
+
module Grape
|
4
|
+
module DSL
|
5
|
+
module API
|
6
|
+
extend ActiveSupport::Concern
|
7
|
+
|
8
|
+
include Grape::Middleware::Auth::DSL
|
9
|
+
|
10
|
+
include Grape::DSL::Validations
|
11
|
+
include Grape::DSL::Callbacks
|
12
|
+
include Grape::DSL::Configuration
|
13
|
+
include Grape::DSL::Helpers
|
14
|
+
include Grape::DSL::Middleware
|
15
|
+
include Grape::DSL::RequestResponse
|
16
|
+
include Grape::DSL::Routing
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
data/lib/grape/dsl/callbacks.rb
CHANGED
@@ -5,21 +5,23 @@ module Grape
|
|
5
5
|
module Callbacks
|
6
6
|
extend ActiveSupport::Concern
|
7
7
|
|
8
|
+
include Grape::DSL::Configuration
|
9
|
+
|
8
10
|
module ClassMethods
|
9
11
|
def before(&block)
|
10
|
-
|
12
|
+
namespace_stackable(:befores, block)
|
11
13
|
end
|
12
14
|
|
13
15
|
def before_validation(&block)
|
14
|
-
|
16
|
+
namespace_stackable(:before_validations, block)
|
15
17
|
end
|
16
18
|
|
17
19
|
def after_validation(&block)
|
18
|
-
|
20
|
+
namespace_stackable(:after_validations, block)
|
19
21
|
end
|
20
22
|
|
21
23
|
def after(&block)
|
22
|
-
|
24
|
+
namespace_stackable(:afters, block)
|
23
25
|
end
|
24
26
|
end
|
25
27
|
end
|
@@ -7,19 +7,63 @@ module Grape
|
|
7
7
|
|
8
8
|
module ClassMethods
|
9
9
|
attr_writer :logger
|
10
|
-
|
10
|
+
|
11
|
+
include Grape::DSL::Settings
|
11
12
|
|
12
13
|
def logger(logger = nil)
|
13
14
|
if logger
|
14
|
-
|
15
|
+
global_setting(:logger, logger)
|
15
16
|
else
|
16
|
-
|
17
|
+
global_setting(:logger) || global_setting(:logger, Logger.new($stdout))
|
17
18
|
end
|
18
19
|
end
|
19
20
|
|
20
21
|
# Add a description to the next namespace or function.
|
21
|
-
def desc(description, options = {})
|
22
|
-
|
22
|
+
def desc(description, options = {}, &config_block)
|
23
|
+
if block_given?
|
24
|
+
config_class = Grape::DSL::Configuration.desc_container
|
25
|
+
|
26
|
+
config_class.configure do
|
27
|
+
description description
|
28
|
+
end
|
29
|
+
|
30
|
+
config_class.configure(&config_block)
|
31
|
+
options = config_class.settings
|
32
|
+
else
|
33
|
+
options = options.merge(description: description)
|
34
|
+
end
|
35
|
+
|
36
|
+
namespace_setting :description, options
|
37
|
+
route_setting :description, options
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
module_function
|
42
|
+
|
43
|
+
def stacked_hash_to_hash(settings)
|
44
|
+
return nil if settings.nil? || settings.blank?
|
45
|
+
settings.each_with_object(ActiveSupport::OrderedHash.new) { |value, result| result.deep_merge!(value) }
|
46
|
+
end
|
47
|
+
|
48
|
+
def desc_container
|
49
|
+
Module.new do
|
50
|
+
include Grape::Util::StrictHashConfiguration.module(
|
51
|
+
:description,
|
52
|
+
:detail,
|
53
|
+
:params,
|
54
|
+
:entity,
|
55
|
+
:http_codes,
|
56
|
+
:named,
|
57
|
+
:headers
|
58
|
+
)
|
59
|
+
|
60
|
+
def config_context.success(*args)
|
61
|
+
entity(*args)
|
62
|
+
end
|
63
|
+
|
64
|
+
def config_context.failure(*args)
|
65
|
+
http_codes(*args)
|
66
|
+
end
|
23
67
|
end
|
24
68
|
end
|
25
69
|
end
|
data/lib/grape/dsl/helpers.rb
CHANGED
@@ -4,6 +4,7 @@ module Grape
|
|
4
4
|
module DSL
|
5
5
|
module Helpers
|
6
6
|
extend ActiveSupport::Concern
|
7
|
+
include Grape::DSL::Configuration
|
7
8
|
|
8
9
|
module ClassMethods
|
9
10
|
# Add helper methods that will be accessible from any
|
@@ -27,23 +28,21 @@ module Grape
|
|
27
28
|
#
|
28
29
|
def helpers(new_mod = nil, &block)
|
29
30
|
if block_given? || new_mod
|
30
|
-
mod =
|
31
|
+
mod = new_mod || Module.new
|
31
32
|
if new_mod
|
32
33
|
inject_api_helpers_to_mod(new_mod) if new_mod.is_a?(BaseHelper)
|
33
|
-
mod.class_eval do
|
34
|
-
include new_mod
|
35
|
-
end
|
36
34
|
end
|
37
35
|
if block_given?
|
38
36
|
inject_api_helpers_to_mod(mod) do
|
39
37
|
mod.class_eval(&block)
|
40
38
|
end
|
41
39
|
end
|
42
|
-
|
40
|
+
|
41
|
+
namespace_stackable(:helpers, mod)
|
43
42
|
else
|
44
43
|
mod = Module.new
|
45
|
-
|
46
|
-
mod.send :include,
|
44
|
+
namespace_stackable(:helpers).each do |mod_to_include|
|
45
|
+
mod.send :include, mod_to_include
|
47
46
|
end
|
48
47
|
change!
|
49
48
|
mod
|
@@ -77,7 +76,7 @@ module Grape
|
|
77
76
|
|
78
77
|
def process_named_params
|
79
78
|
if @named_params && @named_params.any?
|
80
|
-
api.
|
79
|
+
api.namespace_stackable(:named_params, @named_params)
|
81
80
|
end
|
82
81
|
end
|
83
82
|
end
|
@@ -4,6 +4,7 @@ module Grape
|
|
4
4
|
module DSL
|
5
5
|
module InsideRoute
|
6
6
|
extend ActiveSupport::Concern
|
7
|
+
include Grape::DSL::Settings
|
7
8
|
|
8
9
|
# A filtering method that will return a hash
|
9
10
|
# consisting only of keys that have been declared by a
|
@@ -18,12 +19,12 @@ module Grape
|
|
18
19
|
options[:include_missing] = true unless options.key?(:include_missing)
|
19
20
|
options[:include_parent_namespaces] = true unless options.key?(:include_parent_namespaces)
|
20
21
|
if declared_params.nil?
|
21
|
-
declared_params = !options[:include_parent_namespaces] ?
|
22
|
-
|
22
|
+
declared_params = (!options[:include_parent_namespaces] ? route_setting(:declared_params) :
|
23
|
+
(route_setting(:saved_declared_params) || [])).flatten(1) || []
|
23
24
|
end
|
24
25
|
|
25
26
|
unless declared_params
|
26
|
-
|
27
|
+
fail ArgumentError, 'Tried to filter for declared parameters but none exist.'
|
27
28
|
end
|
28
29
|
|
29
30
|
if params.is_a? Array
|
@@ -36,6 +37,9 @@ module Grape
|
|
36
37
|
|
37
38
|
key.each_pair do |parent, children|
|
38
39
|
output_key = options[:stringify] ? parent.to_s : parent.to_sym
|
40
|
+
|
41
|
+
next unless options[:include_missing] || children || params[parent]
|
42
|
+
|
39
43
|
if params.key?(parent) || options[:include_missing]
|
40
44
|
hash[output_key] = if children
|
41
45
|
declared(params[parent] || {}, options, Array(children))
|
@@ -61,7 +65,7 @@ module Grape
|
|
61
65
|
# @param message [String] The message to display.
|
62
66
|
# @param status [Integer] the HTTP Status Code. Defaults to default_error_status, 500 if not set.
|
63
67
|
def error!(message, status = nil, headers = nil)
|
64
|
-
self.status(status ||
|
68
|
+
self.status(status || namespace_inheritable(:default_error_status))
|
65
69
|
throw :error, message: message, status: self.status, headers: headers
|
66
70
|
end
|
67
71
|
|
@@ -75,14 +79,14 @@ module Grape
|
|
75
79
|
if merged_options[:permanent]
|
76
80
|
status 301
|
77
81
|
else
|
78
|
-
if env['HTTP_VERSION'] == 'HTTP/1.1' && request.request_method.to_s.upcase !=
|
82
|
+
if env['HTTP_VERSION'] == 'HTTP/1.1' && request.request_method.to_s.upcase != 'GET'
|
79
83
|
status 303
|
80
84
|
else
|
81
85
|
status 302
|
82
86
|
end
|
83
87
|
end
|
84
|
-
header
|
85
|
-
body
|
88
|
+
header 'Location', url
|
89
|
+
body ''
|
86
90
|
end
|
87
91
|
|
88
92
|
# Set or retrieve the HTTP status code.
|
@@ -146,6 +150,9 @@ module Grape
|
|
146
150
|
def body(value = nil)
|
147
151
|
if value
|
148
152
|
@body = value
|
153
|
+
elsif value == false
|
154
|
+
@body = ''
|
155
|
+
status 204
|
149
156
|
else
|
150
157
|
@body
|
151
158
|
end
|
@@ -186,7 +193,12 @@ module Grape
|
|
186
193
|
end
|
187
194
|
|
188
195
|
representation = { root => representation } if root
|
189
|
-
|
196
|
+
if key
|
197
|
+
representation = (@body || {}).merge(key => representation)
|
198
|
+
elsif entity_class.present? && representation.respond_to?('merge')
|
199
|
+
representation = (@body || {}).merge(representation)
|
200
|
+
end
|
201
|
+
|
190
202
|
body representation
|
191
203
|
end
|
192
204
|
|
@@ -199,7 +211,7 @@ module Grape
|
|
199
211
|
# route.route_description
|
200
212
|
# end
|
201
213
|
def route
|
202
|
-
env[
|
214
|
+
env['rack.routing_args'][:route_info]
|
203
215
|
end
|
204
216
|
|
205
217
|
def entity_class_for_obj(object, options)
|
@@ -214,7 +226,7 @@ module Grape
|
|
214
226
|
end
|
215
227
|
|
216
228
|
object_class.ancestors.each do |potential|
|
217
|
-
entity_class ||= (
|
229
|
+
entity_class ||= (Grape::DSL::Configuration.stacked_hash_to_hash(namespace_stackable(:representations)) || {})[potential]
|
218
230
|
end
|
219
231
|
|
220
232
|
entity_class ||= object_class.const_get(:Entity) if object_class.const_defined?(:Entity) && object_class.const_get(:Entity).respond_to?(:represent)
|