grape 1.0.3 → 1.1.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.
- checksums.yaml +5 -5
- data/Appraisals +1 -1
- data/CHANGELOG.md +15 -0
- data/Gemfile.lock +25 -25
- data/README.md +15 -4
- data/UPGRADING.md +6 -0
- data/gemfiles/multi_json.gemfile +1 -1
- data/gemfiles/multi_xml.gemfile +1 -1
- data/gemfiles/rack_1.5.2.gemfile +1 -1
- data/gemfiles/rack_edge.gemfile +1 -1
- data/gemfiles/rails_3.gemfile +1 -1
- data/gemfiles/rails_4.gemfile +1 -1
- data/gemfiles/rails_5.gemfile +1 -1
- data/gemfiles/rails_edge.gemfile +2 -2
- data/grape.gemspec +1 -1
- data/lib/grape/middleware/error.rb +4 -0
- data/lib/grape/middleware/formatter.rb +4 -2
- data/lib/grape/validations/params_scope.rb +1 -1
- data/lib/grape/version.rb +1 -1
- data/pkg/grape-0.17.0.gem +0 -0
- data/pkg/grape-0.19.0.gem +0 -0
- data/spec/grape/api_spec.rb +26 -2
- data/spec/grape/endpoint_spec.rb +11 -7
- data/spec/grape/middleware/exception_spec.rb +4 -4
- data/spec/grape/middleware/formatter_spec.rb +74 -0
- data/spec/grape/validations/params_scope_spec.rb +18 -0
- metadata +5 -4
- data/pkg/grape-1.0.0.gem +0 -0
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
|
-
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: 7768f2318b0b1045ec81b3a83cb08b5d80676da77aaa30f059fb056175578781
|
|
4
|
+
data.tar.gz: e19ecc4e39b33a19e43e7831ceab4d5a13fd186677cef84547066e48d24d98d0
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: afc16b3f2a5036029bb22615ded000eefb2c24f396efa1f2bc22b253bb84d1adb2a4f2ea7dad63a8d4f98a0c69e7720b828072e57bd8e5ce281c1d158f25cb02
|
|
7
|
+
data.tar.gz: b650ba30bc697feea23a4aa03a50e525b135e25c14707b85f4e95b7a95c5ba37e1565ddce147148885467516c1a7d48e74d58cabb1172679978dcbe28216674a
|
data/Appraisals
CHANGED
data/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,18 @@
|
|
|
1
|
+
### 1.1.0 (8/4/2018)
|
|
2
|
+
|
|
3
|
+
#### Features
|
|
4
|
+
|
|
5
|
+
* [#1759](https://github.com/ruby-grape/grape/pull/1759): Instrument serialization as `'format_response.grape'` - [@zvkemp](https://github.com/zvkemp).
|
|
6
|
+
|
|
7
|
+
#### Fixes
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
* [#1762](https://github.com/ruby-grape/grape/pull/1763): Fix unsafe HTML rendering on errors - [@ctennis](https://github.com/ctennis).
|
|
11
|
+
* [#1759](https://github.com/ruby-grape/grape/pull/1759): Update appraisal for rails_edge - [@zvkemp](https://github.com/zvkemp).
|
|
12
|
+
* [#1758](https://github.com/ruby-grape/grape/pull/1758): Fix expanding load_path in gemspec - [@2maz](https://github.com/2maz).
|
|
13
|
+
* [#1765](https://github.com/ruby-grape/grape/pull/1765): Use 415 when request body is of an unsupported media type - [@jdmurphy](https://github.com/jdmurphy).
|
|
14
|
+
* [#1771](https://github.com/ruby-grape/grape/pull/1771): Fix param aliases with 'given' blocks - [@jereynolds](https://github.com/jereynolds).
|
|
15
|
+
|
|
1
16
|
### 1.0.3 (4/23/2018)
|
|
2
17
|
|
|
3
18
|
#### Fixes
|
data/Gemfile.lock
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
PATH
|
|
2
2
|
remote: .
|
|
3
3
|
specs:
|
|
4
|
-
grape (1.0
|
|
4
|
+
grape (1.1.0)
|
|
5
5
|
activesupport
|
|
6
6
|
builder
|
|
7
7
|
mustermann-grape (~> 1.0.0)
|
|
@@ -12,9 +12,9 @@ PATH
|
|
|
12
12
|
GEM
|
|
13
13
|
remote: https://rubygems.org/
|
|
14
14
|
specs:
|
|
15
|
-
activesupport (5.
|
|
15
|
+
activesupport (5.2.0)
|
|
16
16
|
concurrent-ruby (~> 1.0, >= 1.0.2)
|
|
17
|
-
i18n (
|
|
17
|
+
i18n (>= 0.7, < 2)
|
|
18
18
|
minitest (~> 5.1)
|
|
19
19
|
tzinfo (~> 1.1)
|
|
20
20
|
addressable (2.5.2)
|
|
@@ -44,9 +44,9 @@ GEM
|
|
|
44
44
|
cookiejar (0.3.3)
|
|
45
45
|
cork (0.3.0)
|
|
46
46
|
colored2 (~> 3.1)
|
|
47
|
-
coveralls (0.8.
|
|
47
|
+
coveralls (0.8.22)
|
|
48
48
|
json (>= 1.8, < 3)
|
|
49
|
-
simplecov (~> 0.
|
|
49
|
+
simplecov (~> 0.16.1)
|
|
50
50
|
term-ansicolor (~> 1.3)
|
|
51
51
|
thor (~> 0.19.4)
|
|
52
52
|
tins (~> 1.6)
|
|
@@ -72,15 +72,15 @@ GEM
|
|
|
72
72
|
descendants_tracker (0.0.4)
|
|
73
73
|
thread_safe (~> 0.3, >= 0.3.1)
|
|
74
74
|
diff-lcs (1.3)
|
|
75
|
-
docile (1.1
|
|
75
|
+
docile (1.3.1)
|
|
76
76
|
equalizer (0.0.11)
|
|
77
|
-
faraday (0.
|
|
77
|
+
faraday (0.15.2)
|
|
78
78
|
multipart-post (>= 1.2, < 3)
|
|
79
79
|
faraday-http-cache (1.3.1)
|
|
80
80
|
faraday (~> 0.8)
|
|
81
|
-
ffi (1.9.
|
|
81
|
+
ffi (1.9.25)
|
|
82
82
|
formatador (0.2.5)
|
|
83
|
-
git (1.
|
|
83
|
+
git (1.4.0)
|
|
84
84
|
grape-entity (0.7.1)
|
|
85
85
|
activesupport (>= 4.0)
|
|
86
86
|
multi_json (>= 1.3.2)
|
|
@@ -102,16 +102,16 @@ GEM
|
|
|
102
102
|
guard (~> 2.0)
|
|
103
103
|
rubocop (~> 0.20)
|
|
104
104
|
hashie (3.5.7)
|
|
105
|
-
i18n (0.
|
|
105
|
+
i18n (1.0.1)
|
|
106
106
|
concurrent-ruby (~> 1.0)
|
|
107
107
|
ice_nine (0.11.2)
|
|
108
108
|
json (2.1.0)
|
|
109
|
-
kramdown (1.
|
|
109
|
+
kramdown (1.17.0)
|
|
110
110
|
listen (3.1.5)
|
|
111
111
|
rb-fsevent (~> 0.9, >= 0.9.4)
|
|
112
112
|
rb-inotify (~> 0.9, >= 0.9.7)
|
|
113
113
|
ruby_dep (~> 1.2)
|
|
114
|
-
lumberjack (1.0.
|
|
114
|
+
lumberjack (1.0.13)
|
|
115
115
|
maruku (0.7.3)
|
|
116
116
|
method_source (0.9.0)
|
|
117
117
|
mime-types (3.1)
|
|
@@ -120,7 +120,7 @@ GEM
|
|
|
120
120
|
minitest (5.11.3)
|
|
121
121
|
multi_json (1.13.1)
|
|
122
122
|
multipart-post (2.0.0)
|
|
123
|
-
mustermann (1.0.
|
|
123
|
+
mustermann (1.0.2)
|
|
124
124
|
mustermann-grape (1.0.0)
|
|
125
125
|
mustermann (~> 1.0.0)
|
|
126
126
|
nap (1.1.0)
|
|
@@ -128,18 +128,18 @@ GEM
|
|
|
128
128
|
notiffany (0.1.1)
|
|
129
129
|
nenv (~> 0.1)
|
|
130
130
|
shellany (~> 0.0)
|
|
131
|
-
octokit (4.
|
|
131
|
+
octokit (4.9.0)
|
|
132
132
|
sawyer (~> 0.8.0, >= 0.5.3)
|
|
133
133
|
open4 (1.3.4)
|
|
134
134
|
parallel (1.12.1)
|
|
135
|
-
parser (2.
|
|
136
|
-
ast (~> 2.
|
|
137
|
-
powerpack (0.1.
|
|
135
|
+
parser (2.5.1.2)
|
|
136
|
+
ast (~> 2.4.0)
|
|
137
|
+
powerpack (0.1.2)
|
|
138
138
|
pry (0.11.3)
|
|
139
139
|
coderay (~> 1.1.0)
|
|
140
140
|
method_source (~> 0.9.0)
|
|
141
|
-
public_suffix (3.0.
|
|
142
|
-
rack (2.0.
|
|
141
|
+
public_suffix (3.0.2)
|
|
142
|
+
rack (2.0.5)
|
|
143
143
|
rack-accept (0.4.5)
|
|
144
144
|
rack (>= 0.4)
|
|
145
145
|
rack-jsonp (1.3.1)
|
|
@@ -148,8 +148,8 @@ GEM
|
|
|
148
148
|
rack (>= 1.0)
|
|
149
149
|
rainbow (2.2.2)
|
|
150
150
|
rake
|
|
151
|
-
rake (12.3.
|
|
152
|
-
rb-fsevent (0.10.
|
|
151
|
+
rake (12.3.1)
|
|
152
|
+
rb-fsevent (0.10.3)
|
|
153
153
|
rb-inotify (0.9.10)
|
|
154
154
|
ffi (>= 0.5.0, < 2)
|
|
155
155
|
rspec (3.7.0)
|
|
@@ -181,8 +181,8 @@ GEM
|
|
|
181
181
|
addressable (>= 2.3.5, < 2.6)
|
|
182
182
|
faraday (~> 0.8, < 1.0)
|
|
183
183
|
shellany (0.0.1)
|
|
184
|
-
simplecov (0.
|
|
185
|
-
docile (~> 1.1
|
|
184
|
+
simplecov (0.16.1)
|
|
185
|
+
docile (~> 1.1)
|
|
186
186
|
json (>= 1.8, < 3)
|
|
187
187
|
simplecov-html (~> 0.10.0)
|
|
188
188
|
simplecov-html (0.10.2)
|
|
@@ -195,7 +195,7 @@ GEM
|
|
|
195
195
|
tins (1.16.3)
|
|
196
196
|
tzinfo (1.2.5)
|
|
197
197
|
thread_safe (~> 0.1)
|
|
198
|
-
unicode-display_width (1.
|
|
198
|
+
unicode-display_width (1.4.0)
|
|
199
199
|
virtus (1.0.5)
|
|
200
200
|
axiom-types (~> 0.1)
|
|
201
201
|
coercible (~> 1.0)
|
|
@@ -228,4 +228,4 @@ DEPENDENCIES
|
|
|
228
228
|
ruby-grape-danger (~> 0.1.0)
|
|
229
229
|
|
|
230
230
|
BUNDLED WITH
|
|
231
|
-
1.
|
|
231
|
+
1.16.3
|
data/README.md
CHANGED
|
@@ -129,6 +129,7 @@
|
|
|
129
129
|
- [endpoint_render.grape](#endpoint_rendergrape)
|
|
130
130
|
- [endpoint_run_filters.grape](#endpoint_run_filtersgrape)
|
|
131
131
|
- [endpoint_run_validators.grape](#endpoint_run_validatorsgrape)
|
|
132
|
+
- [format_response.grape](#format_responsegrape)
|
|
132
133
|
- [Monitoring Products](#monitoring-products)
|
|
133
134
|
- [Contributing to Grape](#contributing-to-grape)
|
|
134
135
|
- [License](#license)
|
|
@@ -144,7 +145,7 @@ content negotiation, versioning and much more.
|
|
|
144
145
|
|
|
145
146
|
## Stable Release
|
|
146
147
|
|
|
147
|
-
You're reading the documentation for the stable release of Grape, **1.0
|
|
148
|
+
You're reading the documentation for the stable release of Grape, **1.1.0**.
|
|
148
149
|
Please read [UPGRADING](UPGRADING.md) when upgrading from a previous version.
|
|
149
150
|
|
|
150
151
|
## Project Resources
|
|
@@ -1815,8 +1816,8 @@ module SharedParams
|
|
|
1815
1816
|
extend Grape::API::Helpers
|
|
1816
1817
|
|
|
1817
1818
|
params :order do |options|
|
|
1818
|
-
optional :order_by, type:Symbol, values:options[:order_by], default:options[:default_order_by]
|
|
1819
|
-
optional :order, type:Symbol, values
|
|
1819
|
+
optional :order_by, type: Symbol, values: options[:order_by], default: options[:default_order_by]
|
|
1820
|
+
optional :order, type: Symbol, values: %i(asc desc), default: options[:default_order]
|
|
1820
1821
|
end
|
|
1821
1822
|
end
|
|
1822
1823
|
|
|
@@ -1825,7 +1826,7 @@ class API < Grape::API
|
|
|
1825
1826
|
|
|
1826
1827
|
desc 'Get a sorted collection.'
|
|
1827
1828
|
params do
|
|
1828
|
-
use :order, order_by
|
|
1829
|
+
use :order, order_by: %i(id created_at), default_order_by: :created_at, default_order: :asc
|
|
1829
1830
|
end
|
|
1830
1831
|
|
|
1831
1832
|
get do
|
|
@@ -2549,6 +2550,9 @@ Built-in formatters are the following.
|
|
|
2549
2550
|
* `:serializable_hash`: use object's `serializable_hash` when available, otherwise fallback to `:json`
|
|
2550
2551
|
* `:binary`: data will be returned "as is"
|
|
2551
2552
|
|
|
2553
|
+
If a body is present in a request to an API, with a Content-Type header value that is of an unsupported type a
|
|
2554
|
+
"415 Unsupported Media Type" error code will be returned by Grape.
|
|
2555
|
+
|
|
2552
2556
|
Response statuses that indicate no content as defined by [Rack](https://github.com/rack)
|
|
2553
2557
|
[here](https://github.com/rack/rack/blob/master/lib/rack/utils.rb#L567)
|
|
2554
2558
|
will bypass serialization and the body entity - though there should be none -
|
|
@@ -3483,6 +3487,13 @@ The execution of validators.
|
|
|
3483
3487
|
* *validators* - The validators being executed
|
|
3484
3488
|
* *request* - The request being validated
|
|
3485
3489
|
|
|
3490
|
+
#### format_response.grape
|
|
3491
|
+
|
|
3492
|
+
Serialization or template rendering.
|
|
3493
|
+
|
|
3494
|
+
* *env* - The request environment
|
|
3495
|
+
* *formatter* - The formatter object (e.g., `Grape::Formatter::Json`)
|
|
3496
|
+
|
|
3486
3497
|
See the [ActiveSupport::Notifications documentation](http://api.rubyonrails.org/classes/ActiveSupport/Notifications.html) for information on how to subscribe to these events.
|
|
3487
3498
|
|
|
3488
3499
|
### Monitoring Products
|
data/UPGRADING.md
CHANGED
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
Upgrading Grape
|
|
2
2
|
===============
|
|
3
3
|
|
|
4
|
+
### Upgrading to >= 1.1.0
|
|
5
|
+
|
|
6
|
+
#### Changes in HTTP Response Code for Unsupported Content Type
|
|
7
|
+
|
|
8
|
+
For PUT, POST, PATCH, and DELETE requests where a non-empty body and a "Content-Type" header is supplied that is not supported by the Grape API, Grape will no longer return a 406 "Not Acceptable" HTTP status code and will instead return a 415 "Unsupported Media Type" so that the usage of HTTP status code falls more in line with the specification of [RFC 2616](https://www.ietf.org/rfc/rfc2616.txt).
|
|
9
|
+
|
|
4
10
|
### Upgrading to >= 1.0.0
|
|
5
11
|
|
|
6
12
|
#### Changes in XML and JSON Parsers
|
data/gemfiles/multi_json.gemfile
CHANGED
data/gemfiles/multi_xml.gemfile
CHANGED
data/gemfiles/rack_1.5.2.gemfile
CHANGED
data/gemfiles/rack_edge.gemfile
CHANGED
data/gemfiles/rails_3.gemfile
CHANGED
data/gemfiles/rails_4.gemfile
CHANGED
data/gemfiles/rails_5.gemfile
CHANGED
data/gemfiles/rails_edge.gemfile
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
source 'https://rubygems.org'
|
|
4
4
|
|
|
5
|
-
gem '
|
|
5
|
+
gem 'rails', github: 'rails/rails'
|
|
6
6
|
|
|
7
7
|
group :development, :test do
|
|
8
8
|
gem 'bundler'
|
|
@@ -22,7 +22,7 @@ end
|
|
|
22
22
|
group :test do
|
|
23
23
|
gem 'cookiejar'
|
|
24
24
|
gem 'coveralls', '~> 0.8.17', require: false
|
|
25
|
-
gem 'danger-toc', '~> 0.1.
|
|
25
|
+
gem 'danger-toc', '~> 0.1.2'
|
|
26
26
|
gem 'grape-entity', '~> 0.6'
|
|
27
27
|
gem 'maruku'
|
|
28
28
|
gem 'mime-types'
|
data/grape.gemspec
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
require 'grape/middleware/base'
|
|
2
|
+
require 'active_support/core_ext/string/output_safety'
|
|
2
3
|
|
|
3
4
|
module Grape
|
|
4
5
|
module Middleware
|
|
@@ -69,6 +70,9 @@ module Grape
|
|
|
69
70
|
end
|
|
70
71
|
|
|
71
72
|
def rack_response(message, status = options[:default_status], headers = { Grape::Http::Headers::CONTENT_TYPE => content_type })
|
|
73
|
+
if headers[Grape::Http::Headers::CONTENT_TYPE] == TEXT_HTML
|
|
74
|
+
message = ERB::Util.html_escape(message)
|
|
75
|
+
end
|
|
72
76
|
Rack::Response.new([message], status, headers).finish
|
|
73
77
|
end
|
|
74
78
|
|
|
@@ -41,7 +41,9 @@ module Grape
|
|
|
41
41
|
else
|
|
42
42
|
# Allow content-type to be explicitly overwritten
|
|
43
43
|
formatter = fetch_formatter(headers, options)
|
|
44
|
-
bodymap =
|
|
44
|
+
bodymap = ActiveSupport::Notifications.instrument('format_response.grape', formatter: formatter, env: env) do
|
|
45
|
+
bodies.collect { |body| formatter.call(body, env) }
|
|
46
|
+
end
|
|
45
47
|
Rack::Response.new(bodymap, status, headers)
|
|
46
48
|
end
|
|
47
49
|
rescue Grape::Exceptions::InvalidFormatter => e
|
|
@@ -93,7 +95,7 @@ module Grape
|
|
|
93
95
|
fmt = request.media_type ? mime_types[request.media_type] : options[:default_format]
|
|
94
96
|
|
|
95
97
|
unless content_type_for(fmt)
|
|
96
|
-
throw :error, status:
|
|
98
|
+
throw :error, status: 415, message: "The provided content-type '#{request.media_type}' is not supported."
|
|
97
99
|
end
|
|
98
100
|
parser = Grape::Parser.parser_for fmt, options
|
|
99
101
|
if parser
|
|
@@ -116,7 +116,7 @@ module Grape
|
|
|
116
116
|
# @param attrs [Array] (see Grape::DSL::Parameters#requires)
|
|
117
117
|
def push_declared_params(attrs, **opts)
|
|
118
118
|
if lateral?
|
|
119
|
-
@parent.push_declared_params(attrs)
|
|
119
|
+
@parent.push_declared_params(attrs, opts)
|
|
120
120
|
else
|
|
121
121
|
if opts && opts[:as]
|
|
122
122
|
@api.route_setting(:aliased_params, @api.route_setting(:aliased_params) || [])
|
data/lib/grape/version.rb
CHANGED
|
Binary file
|
|
Binary file
|
data/spec/grape/api_spec.rb
CHANGED
|
@@ -2142,7 +2142,11 @@ XML
|
|
|
2142
2142
|
end
|
|
2143
2143
|
get '/excel.json'
|
|
2144
2144
|
expect(last_response.status).to eq(406)
|
|
2145
|
-
|
|
2145
|
+
if ActiveSupport::VERSION::MAJOR == 3
|
|
2146
|
+
expect(last_response.body).to eq('The requested format 'txt' is not supported.')
|
|
2147
|
+
else
|
|
2148
|
+
expect(last_response.body).to eq('The requested format 'txt' is not supported.')
|
|
2149
|
+
end
|
|
2146
2150
|
end
|
|
2147
2151
|
end
|
|
2148
2152
|
|
|
@@ -3524,7 +3528,27 @@ XML
|
|
|
3524
3528
|
end
|
|
3525
3529
|
get '/something'
|
|
3526
3530
|
expect(last_response.status).to eq(406)
|
|
3527
|
-
|
|
3531
|
+
if ActiveSupport::VERSION::MAJOR == 3
|
|
3532
|
+
expect(last_response.body).to eq('{"error":"The requested format 'txt' is not supported."}')
|
|
3533
|
+
else
|
|
3534
|
+
expect(last_response.body).to eq('{"error":"The requested format 'txt' is not supported."}')
|
|
3535
|
+
end
|
|
3536
|
+
end
|
|
3537
|
+
end
|
|
3538
|
+
|
|
3539
|
+
context 'with unsafe HTML format specified' do
|
|
3540
|
+
it 'escapes the HTML' do
|
|
3541
|
+
subject.content_type :json, 'application/json'
|
|
3542
|
+
subject.get '/something' do
|
|
3543
|
+
'foo'
|
|
3544
|
+
end
|
|
3545
|
+
get '/something?format=<script>blah</script>'
|
|
3546
|
+
expect(last_response.status).to eq(406)
|
|
3547
|
+
if ActiveSupport::VERSION::MAJOR == 3
|
|
3548
|
+
expect(last_response.body).to eq('The requested format '<script>blah</script>' is not supported.')
|
|
3549
|
+
else
|
|
3550
|
+
expect(last_response.body).to eq('The requested format '<script>blah</script>' is not supported.')
|
|
3551
|
+
end
|
|
3528
3552
|
end
|
|
3529
3553
|
end
|
|
3530
3554
|
|
data/spec/grape/endpoint_spec.rb
CHANGED
|
@@ -941,15 +941,15 @@ describe Grape::Endpoint do
|
|
|
941
941
|
end
|
|
942
942
|
end
|
|
943
943
|
|
|
944
|
-
it 'responds with a
|
|
944
|
+
it 'responds with a 415 for an unsupported content-type' do
|
|
945
945
|
subject.format :json
|
|
946
946
|
# subject.content_type :json, "application/json"
|
|
947
947
|
subject.put '/request_body' do
|
|
948
948
|
params[:user]
|
|
949
949
|
end
|
|
950
950
|
put '/request_body', '<user>Bobby T.</user>', 'CONTENT_TYPE' => 'application/xml'
|
|
951
|
-
expect(last_response.status).to eq(
|
|
952
|
-
expect(last_response.body).to eq('{"error":"The
|
|
951
|
+
expect(last_response.status).to eq(415)
|
|
952
|
+
expect(last_response.body).to eq('{"error":"The provided content-type \'application/xml\' is not supported."}')
|
|
953
953
|
end
|
|
954
954
|
|
|
955
955
|
it 'does not accept text/plain in JSON format if application/json is specified as content type' do
|
|
@@ -960,8 +960,8 @@ describe Grape::Endpoint do
|
|
|
960
960
|
end
|
|
961
961
|
put '/request_body', ::Grape::Json.dump(user: 'Bob'), 'CONTENT_TYPE' => 'text/plain'
|
|
962
962
|
|
|
963
|
-
expect(last_response.status).to eq(
|
|
964
|
-
expect(last_response.body).to eq('{"error":"The
|
|
963
|
+
expect(last_response.status).to eq(415)
|
|
964
|
+
expect(last_response.body).to eq('{"error":"The provided content-type \'text/plain\' is not supported."}')
|
|
965
965
|
end
|
|
966
966
|
|
|
967
967
|
context 'content type with params' do
|
|
@@ -1493,7 +1493,9 @@ describe Grape::Endpoint do
|
|
|
1493
1493
|
filters: [],
|
|
1494
1494
|
type: :after }),
|
|
1495
1495
|
have_attributes(name: 'endpoint_run.grape', payload: { endpoint: a_kind_of(Grape::Endpoint),
|
|
1496
|
-
env: an_instance_of(Hash) })
|
|
1496
|
+
env: an_instance_of(Hash) }),
|
|
1497
|
+
have_attributes(name: 'format_response.grape', payload: { env: an_instance_of(Hash),
|
|
1498
|
+
formatter: a_kind_of(Module) })
|
|
1497
1499
|
)
|
|
1498
1500
|
|
|
1499
1501
|
# In order that events were initialized
|
|
@@ -1515,7 +1517,9 @@ describe Grape::Endpoint do
|
|
|
1515
1517
|
have_attributes(name: 'endpoint_render.grape', payload: { endpoint: a_kind_of(Grape::Endpoint) }),
|
|
1516
1518
|
have_attributes(name: 'endpoint_run_filters.grape', payload: { endpoint: a_kind_of(Grape::Endpoint),
|
|
1517
1519
|
filters: [],
|
|
1518
|
-
type: :after })
|
|
1520
|
+
type: :after }),
|
|
1521
|
+
have_attributes(name: 'format_response.grape', payload: { env: an_instance_of(Hash),
|
|
1522
|
+
formatter: a_kind_of(Module) })
|
|
1519
1523
|
)
|
|
1520
1524
|
end
|
|
1521
1525
|
end
|
|
@@ -192,7 +192,7 @@ describe Grape::Middleware::Error do
|
|
|
192
192
|
end
|
|
193
193
|
it 'is possible to return errors in jsonapi format' do
|
|
194
194
|
get '/'
|
|
195
|
-
expect(last_response.body).to eq('{
|
|
195
|
+
expect(last_response.body).to eq('{"error":"rain!"}')
|
|
196
196
|
end
|
|
197
197
|
end
|
|
198
198
|
|
|
@@ -207,8 +207,8 @@ describe Grape::Middleware::Error do
|
|
|
207
207
|
|
|
208
208
|
it 'is possible to return hash errors in jsonapi format' do
|
|
209
209
|
get '/'
|
|
210
|
-
expect(['{
|
|
211
|
-
'{
|
|
210
|
+
expect(['{"error":"rain!","detail":"missing widget"}',
|
|
211
|
+
'{"detail":"missing widget","error":"rain!"}']).to include(last_response.body)
|
|
212
212
|
end
|
|
213
213
|
end
|
|
214
214
|
|
|
@@ -258,7 +258,7 @@ describe Grape::Middleware::Error do
|
|
|
258
258
|
end
|
|
259
259
|
it 'is possible to specify a custom formatter' do
|
|
260
260
|
get '/'
|
|
261
|
-
expect(last_response.body).to eq('{:custom_formatter
|
|
261
|
+
expect(last_response.body).to eq('{:custom_formatter=>"rain!"}')
|
|
262
262
|
end
|
|
263
263
|
end
|
|
264
264
|
|
|
@@ -224,6 +224,80 @@ describe Grape::Middleware::Formatter do
|
|
|
224
224
|
|
|
225
225
|
context 'input' do
|
|
226
226
|
%w[POST PATCH PUT DELETE].each do |method|
|
|
227
|
+
context 'when body is not nil or empty' do
|
|
228
|
+
context 'when Content-Type is supported' do
|
|
229
|
+
let(:io) { StringIO.new('{"is_boolean":true,"string":"thing"}') }
|
|
230
|
+
let(:content_type) { 'application/json' }
|
|
231
|
+
|
|
232
|
+
it "parses the body from #{method} and copies values into rack.request.form_hash" do
|
|
233
|
+
subject.call(
|
|
234
|
+
'PATH_INFO' => '/info',
|
|
235
|
+
'REQUEST_METHOD' => method,
|
|
236
|
+
'CONTENT_TYPE' => content_type,
|
|
237
|
+
'rack.input' => io,
|
|
238
|
+
'CONTENT_LENGTH' => io.length
|
|
239
|
+
)
|
|
240
|
+
expect(subject.env['rack.request.form_hash']['is_boolean']).to be true
|
|
241
|
+
expect(subject.env['rack.request.form_hash']['string']).to eq('thing')
|
|
242
|
+
end
|
|
243
|
+
end
|
|
244
|
+
|
|
245
|
+
context 'when Content-Type is not supported' do
|
|
246
|
+
let(:io) { StringIO.new('{"is_boolean":true,"string":"thing"}') }
|
|
247
|
+
let(:content_type) { 'application/atom+xml' }
|
|
248
|
+
|
|
249
|
+
it 'returns a 415 HTTP error status' do
|
|
250
|
+
error = catch(:error) {
|
|
251
|
+
subject.call(
|
|
252
|
+
'PATH_INFO' => '/info',
|
|
253
|
+
'REQUEST_METHOD' => method,
|
|
254
|
+
'CONTENT_TYPE' => content_type,
|
|
255
|
+
'rack.input' => io,
|
|
256
|
+
'CONTENT_LENGTH' => io.length
|
|
257
|
+
)
|
|
258
|
+
}
|
|
259
|
+
expect(error[:status]).to eq(415)
|
|
260
|
+
expect(error[:message]).to eq("The provided content-type 'application/atom+xml' is not supported.")
|
|
261
|
+
end
|
|
262
|
+
end
|
|
263
|
+
end
|
|
264
|
+
|
|
265
|
+
context 'when body is nil' do
|
|
266
|
+
let(:io) { double }
|
|
267
|
+
before do
|
|
268
|
+
allow(io).to receive_message_chain(:rewind, :read).and_return(nil)
|
|
269
|
+
end
|
|
270
|
+
|
|
271
|
+
it 'does not read and parse the body' do
|
|
272
|
+
expect(subject).not_to receive(:read_rack_input)
|
|
273
|
+
subject.call(
|
|
274
|
+
'PATH_INFO' => '/info',
|
|
275
|
+
'REQUEST_METHOD' => method,
|
|
276
|
+
'CONTENT_TYPE' => 'application/json',
|
|
277
|
+
'rack.input' => io,
|
|
278
|
+
'CONTENT_LENGTH' => 0
|
|
279
|
+
)
|
|
280
|
+
end
|
|
281
|
+
end
|
|
282
|
+
|
|
283
|
+
context 'when body is empty' do
|
|
284
|
+
let(:io) { double }
|
|
285
|
+
before do
|
|
286
|
+
allow(io).to receive_message_chain(:rewind, :read).and_return('')
|
|
287
|
+
end
|
|
288
|
+
|
|
289
|
+
it 'does not read and parse the body' do
|
|
290
|
+
expect(subject).not_to receive(:read_rack_input)
|
|
291
|
+
subject.call(
|
|
292
|
+
'PATH_INFO' => '/info',
|
|
293
|
+
'REQUEST_METHOD' => method,
|
|
294
|
+
'CONTENT_TYPE' => 'application/json',
|
|
295
|
+
'rack.input' => io,
|
|
296
|
+
'CONTENT_LENGTH' => 0
|
|
297
|
+
)
|
|
298
|
+
end
|
|
299
|
+
end
|
|
300
|
+
|
|
227
301
|
['application/json', 'application/json; charset=utf-8'].each do |content_type|
|
|
228
302
|
context content_type do
|
|
229
303
|
it "parses the body from #{method} and copies values into rack.request.form_hash" do
|
|
@@ -479,6 +479,24 @@ describe Grape::Validations::ParamsScope do
|
|
|
479
479
|
end.to_not raise_error
|
|
480
480
|
end
|
|
481
481
|
|
|
482
|
+
it 'allows aliasing of dependent parameters' do
|
|
483
|
+
subject.params do
|
|
484
|
+
optional :a
|
|
485
|
+
given :a do
|
|
486
|
+
requires :b, as: :c
|
|
487
|
+
end
|
|
488
|
+
end
|
|
489
|
+
|
|
490
|
+
subject.get('/multiple') { declared(params).to_json }
|
|
491
|
+
|
|
492
|
+
get '/multiple', a: 'a', b: 'b'
|
|
493
|
+
|
|
494
|
+
body = JSON.parse(last_response.body)
|
|
495
|
+
|
|
496
|
+
expect(body.keys).to include('c')
|
|
497
|
+
expect(body.keys).to_not include('b')
|
|
498
|
+
end
|
|
499
|
+
|
|
482
500
|
it 'does not validate nested requires when given is false' do
|
|
483
501
|
subject.params do
|
|
484
502
|
requires :a, type: String, allow_blank: false, values: %w[x y z]
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: grape
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.0
|
|
4
|
+
version: 1.1.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Michael Bleigh
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2018-04
|
|
11
|
+
date: 2018-08-04 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: activesupport
|
|
@@ -250,7 +250,8 @@ files:
|
|
|
250
250
|
- lib/grape/validations/validators/regexp.rb
|
|
251
251
|
- lib/grape/validations/validators/values.rb
|
|
252
252
|
- lib/grape/version.rb
|
|
253
|
-
- pkg/grape-
|
|
253
|
+
- pkg/grape-0.17.0.gem
|
|
254
|
+
- pkg/grape-0.19.0.gem
|
|
254
255
|
- spec/grape/api/custom_validations_spec.rb
|
|
255
256
|
- spec/grape/api/deeply_included_options_spec.rb
|
|
256
257
|
- spec/grape/api/inherited_helpers_spec.rb
|
|
@@ -368,7 +369,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
368
369
|
version: '0'
|
|
369
370
|
requirements: []
|
|
370
371
|
rubyforge_project:
|
|
371
|
-
rubygems_version: 2.6
|
|
372
|
+
rubygems_version: 2.7.6
|
|
372
373
|
signing_key:
|
|
373
374
|
specification_version: 4
|
|
374
375
|
summary: A simple Ruby framework for building REST-like APIs.
|
data/pkg/grape-1.0.0.gem
DELETED
|
Binary file
|