committee 2.0.1 → 2.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: d8e95c038f0a60b8733804e45d07d86d06fe443b
4
- data.tar.gz: 50bd54f25decd41bbd3f0408a27d96945cdcbf4c
3
+ metadata.gz: 6b64e50881610fea8f1bb4ee2f0c5ec42f196d15
4
+ data.tar.gz: b1a449811bf1750b00f3dde8acd48520a42af196
5
5
  SHA512:
6
- metadata.gz: 1882ae94a7ebc433f0c477fb8af1e39c9e54315387d276ecf1d2fa9c00aea9181ea343e1ce26628d06a01d062c82fdf9ca62728ee16afab2555594d0d1d14a39
7
- data.tar.gz: 31e11c118cac2fddee6723cd56434b49e91dedd5d32203446db4de8e8843403a943ce1ff9851a918df1ca844da39ce37d94b8930e3a52f245b2d7c87844fd4cf
6
+ metadata.gz: 577dcd6f0ff08f595af7c031d3f37cd96b9186858066716b27a9d6d150141309da0ccfab324b6c03fc38784a8456b0ddb523b1c37493b29d9d6baa343ee2ef53
7
+ data.tar.gz: 4193d95a73e0af8d5e66d51a05e2cd5e500874712c1bb498b7a9f89f829c9d4fac2ec69c9c27ed79e87d6ed3977e7966d3bcd924700559aec743c6c882a8ff28
@@ -81,19 +81,66 @@ module Committee::Drivers
81
81
  # data.
82
82
  attr_accessor :target_schema
83
83
 
84
+ attr_accessor :header_schema
85
+
84
86
  def rel
85
87
  raise "Committee: rel not implemented for OpenAPI"
86
88
  end
87
89
  end
88
90
 
89
- # ParameterSchemaBuilder converts OpenAPI 2 link parameters, which are not
90
- # quite JSON schemas (but will be in OpenAPI 3) into synthetic schemas that
91
- # we can use to do some basic request validation.
92
- class ParameterSchemaBuilder
91
+ class SchemaBuilder
93
92
  def initialize(link_data)
94
93
  self.link_data = link_data
95
94
  end
96
95
 
96
+ private
97
+
98
+ LINK_REQUIRED_FIELDS = [
99
+ :name
100
+ ].map(&:to_s).freeze
101
+
102
+ attr_accessor :link_data
103
+
104
+ def check_required_fields!(param_data)
105
+ LINK_REQUIRED_FIELDS.each do |field|
106
+ if !param_data[field]
107
+ raise ArgumentError,
108
+ "Committee: no #{field} section in link data."
109
+ end
110
+ end
111
+ end
112
+ end
113
+
114
+ class HeaderSchemaBuilder < SchemaBuilder
115
+ def call
116
+ if link_data["parameters"]
117
+ link_schema = JsonSchema::Schema.new
118
+ link_schema.properties = {}
119
+ link_schema.required = []
120
+
121
+ header_parameters = link_data["parameters"].select { |param_data| param_data["in"] == "header" }
122
+ header_parameters.each do |param_data|
123
+ check_required_fields!(param_data)
124
+
125
+ param_schema = JsonSchema::Schema.new
126
+
127
+ param_schema.type = [param_data["type"]]
128
+
129
+ link_schema.properties[param_data["name"]] = param_schema
130
+ if param_data["required"] == true
131
+ link_schema.required << param_data["name"]
132
+ end
133
+ end
134
+
135
+ link_schema
136
+ end
137
+ end
138
+ end
139
+
140
+ # ParameterSchemaBuilder converts OpenAPI 2 link parameters, which are not
141
+ # quite JSON schemas (but will be in OpenAPI 3) into synthetic schemas that
142
+ # we can use to do some basic request validation.
143
+ class ParameterSchemaBuilder < SchemaBuilder
97
144
  # Returns a tuple of (schema, schema_data) where only one of the two
98
145
  # values is present. This is either a full schema that's ready to go _or_
99
146
  # a hash of unparsed schema data.
@@ -115,7 +162,8 @@ module Committee::Drivers
115
162
  link_schema.properties = {}
116
163
  link_schema.required = []
117
164
 
118
- link_data["parameters"].each do |param_data|
165
+ parameters = link_data["parameters"].reject { |param_data| param_data["in"] == "header" }
166
+ parameters.each do |param_data|
119
167
  check_required_fields!(param_data)
120
168
 
121
169
  param_schema = JsonSchema::Schema.new
@@ -143,23 +191,6 @@ module Committee::Drivers
143
191
  end
144
192
  end
145
193
  end
146
-
147
- private
148
-
149
- LINK_REQUIRED_FIELDS = [
150
- :name
151
- ].map(&:to_s).freeze
152
-
153
- attr_accessor :link_data
154
-
155
- def check_required_fields!(param_data)
156
- LINK_REQUIRED_FIELDS.each do |field|
157
- if !param_data[field]
158
- raise ArgumentError,
159
- "Committee: no #{field} section in link data."
160
- end
161
- end
162
- end
163
194
  end
164
195
 
165
196
  class Schema < Committee::Drivers::Schema
@@ -266,6 +297,7 @@ module Committee::Drivers
266
297
  # Convert the spec's parameter pseudo-schemas into JSON schemas that
267
298
  # we can use for some basic request validation.
268
299
  link.schema, schema_data = ParameterSchemaBuilder.new(link_data).call
300
+ link.header_schema = HeaderSchemaBuilder.new(link_data).call
269
301
 
270
302
  # If data came back instead of a schema (this occurs when a route has
271
303
  # a single `body` parameter instead of a collection of URL/query/form
@@ -5,6 +5,7 @@ module Committee::Middleware
5
5
 
6
6
  @error_class = options.fetch(:error_class, Committee::ValidationError)
7
7
  @params_key = options[:params_key] || "committee.params"
8
+ @headers_key = options[:headers_key] || "committee.headers"
8
9
  @raise = options[:raise]
9
10
  @schema = get_schema(options[:schema] ||
10
11
  raise(ArgumentError, "Committee: need option `schema`"))
@@ -6,6 +6,7 @@ module Committee::Middleware
6
6
  @allow_form_params = options.fetch(:allow_form_params, true)
7
7
  @allow_query_params = options.fetch(:allow_query_params, true)
8
8
  @check_content_type = options.fetch(:check_content_type, true)
9
+ @check_header = options.fetch(:check_header, true)
9
10
  @optimistic_json = options.fetch(:optimistic_json, false)
10
11
  @strict = options[:strict]
11
12
  @coerce_date_times = options.fetch(:coerce_date_times, false)
@@ -39,7 +40,7 @@ module Committee::Middleware
39
40
  end
40
41
  end
41
42
 
42
- request.env[@params_key] = Committee::RequestUnpacker.new(
43
+ request.env[@params_key], request.env[@headers_key] = Committee::RequestUnpacker.new(
43
44
  request,
44
45
  allow_form_params: @allow_form_params,
45
46
  allow_query_params: @allow_query_params,
@@ -51,8 +52,8 @@ module Committee::Middleware
51
52
  request.env[@params_key].merge!(param_matches) if param_matches
52
53
 
53
54
  if link
54
- validator = Committee::RequestValidator.new(link, check_content_type: @check_content_type)
55
- validator.call(request, request.env[@params_key])
55
+ validator = Committee::RequestValidator.new(link, check_content_type: @check_content_type, check_header: @check_header)
56
+ validator.call(request, request.env[@params_key], request.env[@headers_key])
56
57
 
57
58
  parameter_coerce!(request, link, @params_key)
58
59
  parameter_coerce!(request, link, "rack.request.query_hash") if !request.GET.nil? && !link.schema.nil?
@@ -40,9 +40,9 @@ module Committee
40
40
  end
41
41
 
42
42
  if @allow_query_params
43
- indifferent_params(@request.GET).merge(params)
43
+ [indifferent_params(@request.GET).merge(params), headers]
44
44
  else
45
- params
45
+ [params, headers]
46
46
  end
47
47
  end
48
48
 
@@ -87,5 +87,14 @@ module Committee
87
87
  nil
88
88
  end
89
89
  end
90
+
91
+ def headers
92
+ env = @request.env
93
+ env.keys.grep(/HTTP_/).inject({}) do |headers, key|
94
+ headerized_key = key.gsub(/^HTTP_/, '').gsub(/_/, '-')
95
+ headers[headerized_key] = env[key]
96
+ headers
97
+ end
98
+ end
90
99
  end
91
100
  end
@@ -3,12 +3,21 @@ module Committee
3
3
  def initialize(link, options = {})
4
4
  @link = link
5
5
  @check_content_type = options.fetch(:check_content_type, true)
6
+ @check_header = options.fetch(:check_header, true)
6
7
  end
7
8
 
8
- def call(request, data)
9
- check_content_type!(request, data) if @check_content_type
9
+ def call(request, params, headers)
10
+ check_content_type!(request, params) if @check_content_type
10
11
  if @link.schema
11
- valid, errors = @link.schema.validate(data)
12
+ valid, errors = @link.schema.validate(params)
13
+ if !valid
14
+ errors = JsonSchema::SchemaError.aggregate(errors).join("\n")
15
+ raise InvalidRequest, "Invalid request.\n\n#{errors}"
16
+ end
17
+ end
18
+
19
+ if @check_header && @link.respond_to?(:header_schema) && @link.header_schema
20
+ valid, errors = @link.header_schema.validate(headers)
12
21
  if !valid
13
22
  errors = JsonSchema::SchemaError.aggregate(errors).join("\n")
14
23
  raise InvalidRequest, "Invalid request.\n\n#{errors}"
@@ -298,3 +298,26 @@ describe Committee::Drivers::OpenAPI2::ParameterSchemaBuilder do
298
298
  Committee::Drivers::OpenAPI2::ParameterSchemaBuilder.new(data).call
299
299
  end
300
300
  end
301
+
302
+ describe Committee::Drivers::OpenAPI2::HeaderSchemaBuilder do
303
+ it "returns schema data for header" do
304
+ data = {
305
+ "parameters" => [
306
+ {
307
+ "name" => "AUTH_TOKEN",
308
+ "type" => "string",
309
+ "in" => "header",
310
+ }
311
+ ]
312
+ }
313
+ schema = call(data)
314
+
315
+ assert_equal ["string"], schema.properties["AUTH_TOKEN"].type
316
+ end
317
+
318
+ private
319
+
320
+ def call(data)
321
+ Committee::Drivers::OpenAPI2::HeaderSchemaBuilder.new(data).call
322
+ end
323
+ end
@@ -347,13 +347,13 @@ describe Committee::Middleware::RequestValidation do
347
347
  }
348
348
 
349
349
  @app = new_rack_app_with_lambda(check_parameter, schema: open_api_2_schema)
350
- get "/api/pets?limit=3"
350
+ get "/api/pets?limit=3", nil, { "HTTP_AUTH_TOKEN" => "xxx" }
351
351
  assert_equal 200, last_response.status
352
352
  end
353
353
 
354
354
  it "detects an invalid request for OpenAPI" do
355
355
  @app = new_rack_app(schema: open_api_2_schema)
356
- get "/api/pets?limit=foo"
356
+ get "/api/pets?limit=foo", nil, { "HTTP_AUTH_TOKEN" => "xxx" }
357
357
  assert_equal 400, last_response.status
358
358
  assert_match /invalid request/i, last_response.body
359
359
  end
@@ -7,7 +7,7 @@ describe Committee::ParameterCoercer do
7
7
  @schema = JsonSchema.parse!(hyper_schema_data)
8
8
  @schema.expand_references!
9
9
  # POST /apps/:id
10
- @link = @link = @schema.properties["app"].links[0]
10
+ @link = @schema.properties["app"].links[0]
11
11
  end
12
12
 
13
13
  it "pass datetime string" do
@@ -9,7 +9,7 @@ describe Committee::RequestUnpacker do
9
9
  "rack.input" => StringIO.new('{"x":"y"}'),
10
10
  }
11
11
  request = Rack::Request.new(env)
12
- params = Committee::RequestUnpacker.new(request).call
12
+ params, _ = Committee::RequestUnpacker.new(request).call
13
13
  assert_equal({ "x" => "y" }, params)
14
14
  end
15
15
 
@@ -18,7 +18,7 @@ describe Committee::RequestUnpacker do
18
18
  "rack.input" => StringIO.new('{"x":"y"}'),
19
19
  }
20
20
  request = Rack::Request.new(env)
21
- params = Committee::RequestUnpacker.new(request).call
21
+ params, _ = Committee::RequestUnpacker.new(request).call
22
22
  assert_equal({ "x" => "y" }, params)
23
23
  end
24
24
 
@@ -28,7 +28,7 @@ describe Committee::RequestUnpacker do
28
28
  "rack.input" => StringIO.new('{"x":"y"}'),
29
29
  }
30
30
  request = Rack::Request.new(env)
31
- params = Committee::RequestUnpacker.new(request).call
31
+ params, _ = Committee::RequestUnpacker.new(request).call
32
32
  assert_equal({}, params)
33
33
  end
34
34
 
@@ -38,7 +38,7 @@ describe Committee::RequestUnpacker do
38
38
  "rack.input" => StringIO.new('{"x":"y"}'),
39
39
  }
40
40
  request = Rack::Request.new(env)
41
- params = Committee::RequestUnpacker.new(request, optimistic_json: true).call
41
+ params, _ = Committee::RequestUnpacker.new(request, optimistic_json: true).call
42
42
  assert_equal({ "x" => "y" }, params)
43
43
  end
44
44
 
@@ -48,7 +48,7 @@ describe Committee::RequestUnpacker do
48
48
  "rack.input" => StringIO.new('x=y&foo=42'),
49
49
  }
50
50
  request = Rack::Request.new(env)
51
- params = Committee::RequestUnpacker.new(request, optimistic_json: true).call
51
+ params, _ = Committee::RequestUnpacker.new(request, optimistic_json: true).call
52
52
  assert_equal({}, params)
53
53
  end
54
54
 
@@ -58,7 +58,7 @@ describe Committee::RequestUnpacker do
58
58
  "rack.input" => StringIO.new(""),
59
59
  }
60
60
  request = Rack::Request.new(env)
61
- params = Committee::RequestUnpacker.new(request).call
61
+ params, _ = Committee::RequestUnpacker.new(request).call
62
62
  assert_equal({}, params)
63
63
  end
64
64
 
@@ -68,7 +68,7 @@ describe Committee::RequestUnpacker do
68
68
  "rack.input" => StringIO.new("x=y"),
69
69
  }
70
70
  request = Rack::Request.new(env)
71
- params = Committee::RequestUnpacker.new(request).call
71
+ params, _ = Committee::RequestUnpacker.new(request).call
72
72
  assert_equal({}, params)
73
73
  end
74
74
 
@@ -78,7 +78,7 @@ describe Committee::RequestUnpacker do
78
78
  "rack.input" => StringIO.new("x=y"),
79
79
  }
80
80
  request = Rack::Request.new(env)
81
- params = Committee::RequestUnpacker.new(request, allow_form_params: true).call
81
+ params, _ = Committee::RequestUnpacker.new(request, allow_form_params: true).call
82
82
  assert_equal({ "x" => "y" }, params)
83
83
  end
84
84
 
@@ -92,7 +92,7 @@ describe Committee::RequestUnpacker do
92
92
  "rack.input" => StringIO.new("x=1"),
93
93
  }
94
94
  request = Rack::Request.new(env)
95
- params = Committee::RequestUnpacker.new(
95
+ params, _ = Committee::RequestUnpacker.new(
96
96
  request,
97
97
  allow_form_params: true,
98
98
  coerce_form_params: true,
@@ -108,7 +108,7 @@ describe Committee::RequestUnpacker do
108
108
  "QUERY_STRING" => "a=b"
109
109
  }
110
110
  request = Rack::Request.new(env)
111
- params = Committee::RequestUnpacker.new(request, allow_form_params: true, allow_query_params: true).call
111
+ params, _ = Committee::RequestUnpacker.new(request, allow_form_params: true, allow_query_params: true).call
112
112
  assert_equal({ "x" => "y", "a" => "b" }, params)
113
113
  end
114
114
 
@@ -118,7 +118,7 @@ describe Committee::RequestUnpacker do
118
118
  "QUERY_STRING" => "a=b"
119
119
  }
120
120
  request = Rack::Request.new(env)
121
- params = Committee::RequestUnpacker.new(request, allow_query_params: true).call
121
+ params, _ = Committee::RequestUnpacker.new(request, allow_query_params: true).call
122
122
  assert_equal({ "a" => "b" }, params)
123
123
  end
124
124
 
@@ -139,7 +139,7 @@ describe Committee::RequestUnpacker do
139
139
  "rack.input" => StringIO.new('{"x":"y"}'),
140
140
  }
141
141
  request = Rack::Request.new(env)
142
- params = Committee::RequestUnpacker.new(request).call
142
+ params, _ = Committee::RequestUnpacker.new(request).call
143
143
  assert_equal({}, params)
144
144
  end
145
145
 
@@ -149,7 +149,17 @@ describe Committee::RequestUnpacker do
149
149
  "rack.input" => StringIO.new('{"x":[]}'),
150
150
  }
151
151
  request = Rack::Request.new(env)
152
- params = Committee::RequestUnpacker.new(request).call
152
+ params, _ = Committee::RequestUnpacker.new(request).call
153
153
  assert_equal({ "x" => [] }, params)
154
154
  end
155
+
156
+ it "unpacks http header" do
157
+ env = {
158
+ "HTTP_FOO_BAR" => "some header value",
159
+ "rack.input" => StringIO.new(""),
160
+ }
161
+ request = Rack::Request.new(env)
162
+ _, headers = Committee::RequestUnpacker.new(request, { allow_header_params: true }).call
163
+ assert_equal({ "FOO-BAR" => "some header value" }, headers)
164
+ end
155
165
  end
@@ -3,102 +3,147 @@ require_relative "test_helper"
3
3
  require "stringio"
4
4
 
5
5
  describe Committee::RequestValidator do
6
- before do
7
- @schema = JsonSchema.parse!(hyper_schema_data)
8
- @schema.expand_references!
9
- # POST /apps/:id
10
- @link = @link = @schema.properties["app"].links[0]
11
- @request = Rack::Request.new({
12
- "CONTENT_TYPE" => "application/json",
13
- "rack.input" => StringIO.new("{}"),
14
- "REQUEST_METHOD" => "POST"
15
- })
16
- end
6
+ describe 'HyperSchema' do
7
+ before do
8
+ @schema = JsonSchema.parse!(hyper_schema_data)
9
+ @schema.expand_references!
10
+ # POST /apps/:id
11
+ @link = @schema.properties["app"].links[0]
12
+ @request = Rack::Request.new({
13
+ "CONTENT_TYPE" => "application/json",
14
+ "rack.input" => StringIO.new("{}"),
15
+ "REQUEST_METHOD" => "POST"
16
+ })
17
+ end
17
18
 
18
- it "passes through a valid request with Content-Type options" do
19
- @headers = { "Content-Type" => "application/json; charset=utf-8" }
20
- call({})
21
- end
19
+ it "passes through a valid request with Content-Type options" do
20
+ @headers = { "Content-Type" => "application/json; charset=utf-8" }
21
+ call({})
22
+ end
22
23
 
23
- it "passes through a valid request" do
24
- data = {
25
- "name" => "heroku-api",
26
- }
27
- call(data)
28
- end
24
+ it "passes through a valid request" do
25
+ data = {
26
+ "name" => "heroku-api",
27
+ }
28
+ call(data)
29
+ end
29
30
 
30
- it "passes through a valid request with Content-Type options" do
31
- @request =
32
- Rack::Request.new({
33
- "CONTENT_TYPE" => "application/json; charset=utf-8",
34
- "rack.input" => StringIO.new("{}"),
35
- })
36
- data = {
37
- "name" => "heroku-api",
38
- }
39
- call(data)
40
- end
31
+ it "passes through a valid request with Content-Type options" do
32
+ @request =
33
+ Rack::Request.new({
34
+ "CONTENT_TYPE" => "application/json; charset=utf-8",
35
+ "rack.input" => StringIO.new("{}"),
36
+ })
37
+ data = {
38
+ "name" => "heroku-api",
39
+ }
40
+ call(data)
41
+ end
42
+
43
+ it "detects an invalid request Content-Type" do
44
+ e = assert_raises(Committee::InvalidRequest) {
45
+ @request =
46
+ Rack::Request.new({
47
+ "CONTENT_TYPE" => "application/x-www-form-urlencoded",
48
+ "rack.input" => StringIO.new("{}"),
49
+ })
50
+ call({})
51
+ }
52
+ message =
53
+ %{"Content-Type" request header must be set to "application/json".}
54
+ assert_equal message, e.message
55
+ end
41
56
 
42
- it "detects an invalid request Content-Type" do
43
- e = assert_raises(Committee::InvalidRequest) {
57
+ it "allows skipping content_type check" do
44
58
  @request =
45
59
  Rack::Request.new({
46
- "CONTENT_TYPE" => "application/x-www-form-urlencoded",
47
- "rack.input" => StringIO.new("{}"),
48
- })
49
- call({})
50
- }
51
- message =
52
- %{"Content-Type" request header must be set to "application/json".}
53
- assert_equal message, e.message
54
- end
60
+ "CONTENT_TYPE" => "application/x-www-form-urlencoded",
61
+ "rack.input" => StringIO.new("{}"),
62
+ })
63
+ call({}, {}, check_content_type: false)
64
+ end
55
65
 
56
- it "allows skipping content_type check" do
57
- @request =
58
- Rack::Request.new({
59
- "CONTENT_TYPE" => "application/x-www-form-urlencoded",
60
- "rack.input" => StringIO.new("{}"),
61
- })
62
- call({}, check_content_type: false)
63
- end
66
+ it "detects an missing parameter in GET requests" do
67
+ # GET /apps/search?query=...
68
+ @link = @schema.properties["app"].links[5]
69
+ @request = Rack::Request.new({})
70
+ e = assert_raises(Committee::InvalidRequest) do
71
+ call({})
72
+ end
73
+ message =
74
+ %{Invalid request.\n\n#: failed schema #/definitions/app/links/5/schema: "query" wasn't supplied.}
75
+ assert_equal message, e.message
76
+ end
64
77
 
65
- it "detects an missing parameter in GET requests" do
66
- # GET /apps/search?query=...
67
- @link = @link = @schema.properties["app"].links[5]
68
- @request = Rack::Request.new({})
69
- e = assert_raises(Committee::InvalidRequest) do
78
+ it "allows an invalid Content-Type with an empty body" do
79
+ @request =
80
+ Rack::Request.new({
81
+ "CONTENT_TYPE" => "application/x-www-form-urlencoded",
82
+ "rack.input" => StringIO.new(""),
83
+ })
70
84
  call({})
71
85
  end
72
- message =
73
- %{Invalid request.\n\n#: failed schema #/definitions/app/links/5/schema: "query" wasn't supplied.}
74
- assert_equal message, e.message
75
- end
76
86
 
77
- it "allows an invalid Content-Type with an empty body" do
78
- @request =
79
- Rack::Request.new({
80
- "CONTENT_TYPE" => "application/x-www-form-urlencoded",
81
- "rack.input" => StringIO.new(""),
82
- })
83
- call({})
84
- end
87
+ it "detects a parameter of the wrong pattern" do
88
+ data = {
89
+ "name" => "%@!"
90
+ }
91
+ e = assert_raises(Committee::InvalidRequest) do
92
+ call(data)
93
+ end
94
+ message = %{Invalid request.\n\n#/name: failed schema #/definitions/app/links/0/schema/properties/name: %@! does not match /^[a-z][a-z0-9-]{3,30}$/.}
95
+ assert_equal message, e.message
96
+ end
85
97
 
86
- it "detects a parameter of the wrong pattern" do
87
- data = {
88
- "name" => "%@!"
89
- }
90
- e = assert_raises(Committee::InvalidRequest) do
91
- call(data)
98
+ private
99
+
100
+ def call(data, headers={}, options={})
101
+ # hyper-schema link should be dropped into driver wrapper before it's used
102
+ link = Committee::Drivers::HyperSchema::Link.new(@link)
103
+ Committee::RequestValidator.new(link, options).call(@request, data, headers)
92
104
  end
93
- message = %{Invalid request.\n\n#/name: failed schema #/definitions/app/links/0/schema/properties/name: %@! does not match /^[a-z][a-z0-9-]{3,30}$/.}
94
- assert_equal message, e.message
95
105
  end
96
106
 
97
- private
107
+ describe 'OpenAPI 2' do
108
+ before do
109
+ @schema = open_api_2_schema
110
+ @link = @schema.routes['GET'][0][1]
111
+ @request = Rack::Request.new({
112
+ "CONTENT_TYPE" => "application/json",
113
+ "rack.input" => StringIO.new("{}"),
114
+ "REQUEST_METHOD" => "POST"
115
+ })
116
+ end
117
+
118
+
119
+ it "passes through a valid request" do
120
+ headers = {
121
+ "AUTH-TOKEN" => "xxx"
122
+ }
123
+ call({}, headers)
124
+ end
125
+
126
+ it "detects an missing header parameter in GET requests" do
127
+ @link = @schema.routes['GET'][0][1]
128
+ @request = Rack::Request.new({})
129
+ e = assert_raises(Committee::InvalidRequest) do
130
+ call({}, {})
131
+ end
132
+ message = %{Invalid request.\n\n#: failed schema : "AUTH-TOKEN" wasn't supplied.}
133
+ assert_equal message, e.message
134
+ end
98
135
 
99
- def call(data, options={})
100
- # hyper-schema link should be dropped into driver wrapper before it's used
101
- link = Committee::Drivers::HyperSchema::Link.new(@link)
102
- Committee::RequestValidator.new(link, options).call(@request, data)
136
+ it "allows skipping header schema check" do
137
+ @link = @schema.routes['GET'][0][1]
138
+ @request = Rack::Request.new({})
139
+ call({}, {}, { check_header: false })
140
+ end
141
+
142
+ private
143
+
144
+ def call(data, headers={}, options={})
145
+ # hyper-schema link should be dropped into driver wrapper before it's used
146
+ Committee::RequestValidator.new(@link, options).call(@request, data, headers)
147
+ end
103
148
  end
104
149
  end
@@ -5,7 +5,7 @@ describe Committee::StringParamsCoercer do
5
5
  @schema = JsonSchema.parse!(hyper_schema_data)
6
6
  @schema.expand_references!
7
7
  # GET /search/apps
8
- @link = @link = @schema.properties["app"].links[5]
8
+ @link = @schema.properties["app"].links[5]
9
9
  end
10
10
 
11
11
  it "doesn't coerce params not in the schema" do
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: committee
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.1
4
+ version: 2.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Brandur
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2018-02-27 00:00:00.000000000 Z
12
+ date: 2018-03-27 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: json_schema
@@ -212,7 +212,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
212
212
  version: '0'
213
213
  requirements: []
214
214
  rubyforge_project:
215
- rubygems_version: 2.4.5.1
215
+ rubygems_version: 2.6.14
216
216
  signing_key:
217
217
  specification_version: 4
218
218
  summary: A collection of Rack middleware to support JSON Schema.