committee 2.5.1 → 3.0.0.alpha

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. checksums.yaml +5 -5
  2. data/lib/committee.rb +16 -5
  3. data/lib/committee/bin/committee_stub.rb +4 -0
  4. data/lib/committee/drivers.rb +12 -29
  5. data/lib/committee/drivers/hyper_schema.rb +9 -0
  6. data/lib/committee/drivers/open_api_2.rb +9 -20
  7. data/lib/committee/drivers/open_api_3.rb +70 -0
  8. data/lib/committee/errors.rb +3 -0
  9. data/lib/committee/middleware/base.rb +20 -62
  10. data/lib/committee/middleware/request_validation.rb +5 -62
  11. data/lib/committee/middleware/response_validation.rb +5 -19
  12. data/lib/committee/middleware/stub.rb +5 -1
  13. data/lib/committee/parameter_coercer.rb +1 -0
  14. data/lib/committee/request_unpacker.rb +2 -5
  15. data/lib/committee/schema_validator/hyper_schema.rb +92 -0
  16. data/lib/committee/{request_validator.rb → schema_validator/hyper_schema/request_validator.rb} +1 -1
  17. data/lib/committee/{response_generator.rb → schema_validator/hyper_schema/response_generator.rb} +1 -1
  18. data/lib/committee/{response_validator.rb → schema_validator/hyper_schema/response_validator.rb} +6 -6
  19. data/lib/committee/{router.rb → schema_validator/hyper_schema/router.rb} +10 -4
  20. data/lib/committee/{string_params_coercer.rb → schema_validator/hyper_schema/string_params_coercer.rb} +1 -1
  21. data/lib/committee/schema_validator/open_api_3.rb +67 -0
  22. data/lib/committee/schema_validator/open_api_3/operation_wrapper.rb +98 -0
  23. data/lib/committee/schema_validator/open_api_3/request_validator.rb +17 -0
  24. data/lib/committee/schema_validator/open_api_3/response_validator.rb +35 -0
  25. data/lib/committee/schema_validator/open_api_3/router.rb +26 -0
  26. data/lib/committee/schema_validator/option.rb +31 -0
  27. data/lib/committee/test/methods.rb +14 -117
  28. data/test/bin/committee_stub_test.rb +6 -0
  29. data/test/drivers/open_api_2_test.rb +0 -81
  30. data/test/drivers/open_api_3_test.rb +81 -0
  31. data/test/drivers_test.rb +2 -42
  32. data/test/middleware/base_test.rb +42 -21
  33. data/test/middleware/request_validation_open_api_3_test.rb +499 -0
  34. data/test/middleware/request_validation_test.rb +18 -0
  35. data/test/middleware/response_validation_open_api_3_test.rb +96 -0
  36. data/test/middleware/response_validation_test.rb +7 -30
  37. data/test/middleware/stub_test.rb +9 -0
  38. data/test/request_unpacker_test.rb +55 -21
  39. data/test/{request_validator_test.rb → schema_validator/hyper_schema/request_validator_test.rb} +4 -4
  40. data/test/{response_generator_test.rb → schema_validator/hyper_schema/response_generator_test.rb} +11 -11
  41. data/test/{response_validator_test.rb → schema_validator/hyper_schema/response_validator_test.rb} +3 -3
  42. data/test/{router_test.rb → schema_validator/hyper_schema/router_test.rb} +8 -10
  43. data/test/{string_params_coercer_test.rb → schema_validator/hyper_schema/string_params_coercer_test.rb} +3 -3
  44. data/test/schema_validator/open_api_3/operation_wrapper_test.rb +132 -0
  45. data/test/schema_validator/open_api_3/request_validator_test.rb +151 -0
  46. data/test/schema_validator/open_api_3/response_validator_test.rb +55 -0
  47. data/test/test/methods_new_version_test.rb +11 -20
  48. data/test/test/methods_test.rb +51 -55
  49. data/test/test_helper.rb +22 -8
  50. metadata +46 -18
@@ -373,6 +373,24 @@ describe Committee::Middleware::RequestValidation do
373
373
  assert_match(/invalid request/i, last_response.body)
374
374
  end
375
375
 
376
+ it "OpenAPI3 pass through a valid request" do
377
+ @app = new_rack_app(open_api_3: open_api_3_schema)
378
+ get "/characters"
379
+ assert_equal 200, last_response.status
380
+ end
381
+
382
+ it "OpenAPI3 pass not exist href" do
383
+ @app = new_rack_app(open_api_3: open_api_3_schema)
384
+ get "/unknown"
385
+ assert_equal 200, last_response.status
386
+ end
387
+
388
+ it "OpenAPI3 pass not exist href in strict mode" do
389
+ @app = new_rack_app(open_api_3: open_api_3_schema, strict: true)
390
+ get "/unknown"
391
+ assert_equal 404, last_response.status
392
+ end
393
+
376
394
  private
377
395
 
378
396
  def new_rack_app(options = {})
@@ -0,0 +1,96 @@
1
+ require_relative "../test_helper"
2
+
3
+ describe Committee::Middleware::ResponseValidation do
4
+ include Rack::Test::Methods
5
+
6
+ CHARACTERS_RESPONSE = {"Otonokizaka" => ["Honoka.Kousaka"]}
7
+
8
+ def app
9
+ @app
10
+ end
11
+
12
+ it "passes through a valid response" do
13
+ @app = new_response_rack(JSON.generate(CHARACTERS_RESPONSE), {}, open_api_3: open_api_3_schema)
14
+ get "/characters"
15
+ assert_equal 200, last_response.status
16
+ end
17
+
18
+ it "passes through a invalid json" do
19
+ @app = new_response_rack("not_json", {}, open_api_3: open_api_3_schema)
20
+
21
+ get "/characters"
22
+
23
+ assert_equal 500, last_response.status
24
+ assert_equal "{\"id\":\"invalid_response\",\"message\":\"Response wasn't valid JSON.\"}", last_response.body
25
+ end
26
+
27
+ it "passes through not definition" do
28
+ @app = new_response_rack(JSON.generate(CHARACTERS_RESPONSE), {}, open_api_3: open_api_3_schema)
29
+ get "/no_data"
30
+ assert_equal 200, last_response.status
31
+ end
32
+
33
+ it "detects a response invalid due to schema" do
34
+ @app = new_response_rack("[]", {}, open_api_3: open_api_3_schema)
35
+
36
+ e = assert_raises(Committee::InvalidRequest) { # TODO: change invalid request
37
+ get "/characters"
38
+ }
39
+
40
+ assert_match(/class is Array but it's not valid object/i, e.message)
41
+ end
42
+
43
+ it "passes through a 204 (no content) response" do
44
+ @app = new_response_rack("", {}, {open_api_3: open_api_3_schema}, {status: 204})
45
+ post "/validate"
46
+ assert_equal 204, last_response.status
47
+ end
48
+
49
+ it "passes through a valid response with prefix" do
50
+ @app = new_response_rack(JSON.generate(CHARACTERS_RESPONSE), {}, open_api_3: open_api_3_schema, prefix: "/v1")
51
+ get "/v1/characters"
52
+ assert_equal 200, last_response.status
53
+ end
54
+
55
+ it "passes through a invalid json with prefix" do
56
+ @app = new_response_rack("not_json", {}, open_api_3: open_api_3_schema, prefix: "/v1")
57
+
58
+ get "/v1/characters"
59
+
60
+ # TODO: support prefix
61
+ assert_equal 200, last_response.status
62
+ # assert_equal 500, last_response.status
63
+ # assert_equal "{\"id\":\"invalid_response\",\"message\":\"Response wasn't valid JSON.\"}", last_response.body
64
+ end
65
+
66
+ it "rescues JSON errors" do
67
+ @app = new_response_rack("_42", {}, open_api_3: open_api_3_schema, raise: true)
68
+ assert_raises(Committee::InvalidResponse) do
69
+ get "/characters"
70
+ end
71
+ end
72
+
73
+ it "not parameter requset" do
74
+ @app = new_response_rack({integer: '1'}.to_json, {}, open_api_3: open_api_3_schema)
75
+
76
+ # TODO: error change
77
+ assert_raises(Committee::InvalidRequest) do
78
+ patch "/validate_no_parameter", {no_schema: 'no'}
79
+ end
80
+ end
81
+
82
+ private
83
+
84
+ def new_response_rack(response, headers = {}, options = {}, rack_options = {})
85
+ status = rack_options[:status] || 200
86
+ headers = {
87
+ "Content-Type" => "application/json"
88
+ }.merge(headers)
89
+ Rack::Builder.new {
90
+ use Committee::Middleware::ResponseValidation, options
91
+ run lambda { |_|
92
+ [options.fetch(:app_status, status), headers, [response]]
93
+ }
94
+ }
95
+ end
96
+ end
@@ -15,8 +15,8 @@ describe Committee::Middleware::ResponseValidation do
15
15
 
16
16
  it "doesn't call error_handler when response is valid" do
17
17
  called = false
18
- pr = ->(_e) { called = true }
19
- @app = new_rack_app(JSON.generate([ValidApp]), {}, schema: hyper_schema, error_handler: pr)
18
+ pr = ->(e) { called = true }
19
+ @app = new_rack_app(JSON.generate([ValidApp]), {}, schema: hyper_schema)
20
20
  get "/apps"
21
21
  assert !called, "error_handler is called"
22
22
  end
@@ -29,7 +29,7 @@ describe Committee::Middleware::ResponseValidation do
29
29
  end
30
30
 
31
31
  it "detects a response invalid due to not being JSON" do
32
- @app = new_rack_app("{_}", {}, schema: hyper_schema)
32
+ @app = new_rack_app("", {}, schema: hyper_schema)
33
33
  get "/apps"
34
34
  assert_equal 500, last_response.status
35
35
  assert_match(/valid JSON/i, last_response.body)
@@ -41,26 +41,10 @@ describe Committee::Middleware::ResponseValidation do
41
41
  assert_equal 404, last_response.status
42
42
  end
43
43
 
44
- it "optionally validates non-2xx invalid responses and deprecated option" do
45
- mock(Committee).warn_deprecated.with_any_args
46
-
47
- @app = new_rack_app("{_}", {}, app_status: 404, validate_errors: true,
48
- schema: hyper_schema)
49
-
50
- get "/apps"
51
- assert_equal 500, last_response.status
52
- assert_match(/valid JSON/i, last_response.body)
53
- end
54
-
55
44
  it "optionally validates non-2xx invalid responses" do
56
- @app = new_rack_app("", {}, app_status: 404, validate_success_only: false, schema: hyper_schema)
57
- get "/apps"
58
- assert_equal 500, last_response.status
59
- assert_match(/Invalid response/i, last_response.body)
60
- end
45
+ @app = new_rack_app("", {}, app_status: 404, validate_errors: true,
46
+ schema: hyper_schema)
61
47
 
62
- it "optionally validates non-2xx invalid responses with invalid json" do
63
- @app = new_rack_app("{_}", {}, app_status: 404, validate_success_only: false, schema: hyper_schema)
64
48
  get "/apps"
65
49
  assert_equal 500, last_response.status
66
50
  assert_match(/valid JSON/i, last_response.body)
@@ -72,15 +56,8 @@ describe Committee::Middleware::ResponseValidation do
72
56
  assert_equal 204, last_response.status
73
57
  end
74
58
 
75
- it "skip validation when 4xx" do
76
- @app = new_rack_app("[{x:y}]", {}, schema: hyper_schema, validate_success_only: true, app_status: 400)
77
- get "/apps"
78
- assert_equal 400, last_response.status
79
- assert_match("[{x:y}]", last_response.body)
80
- end
81
-
82
59
  it "rescues JSON errors" do
83
- @app = new_rack_app("[{x:y}]", {}, schema: hyper_schema, validate_success_only: false)
60
+ @app = new_rack_app("[{x:y}]", {}, schema: hyper_schema)
84
61
  get "/apps"
85
62
  assert_equal 500, last_response.status
86
63
  assert_match(/valid json/i, last_response.body)
@@ -126,7 +103,7 @@ describe Committee::Middleware::ResponseValidation do
126
103
  end
127
104
 
128
105
  it "detects an invalid response for OpenAPI" do
129
- @app = new_rack_app("{_}", {}, schema: open_api_2_schema)
106
+ @app = new_rack_app("", {}, schema: open_api_2_schema)
130
107
  get "/api/pets"
131
108
  assert_equal 500, last_response.status
132
109
  assert_match(/valid JSON/i, last_response.body)
@@ -96,6 +96,15 @@ describe Committee::Middleware::Stub do
96
96
  assert_equal({ "cached" => true }, data)
97
97
  end
98
98
 
99
+ it "caches the response if called multiple times" do
100
+ cache = {}
101
+ @app = new_rack_app(cache: cache, open_api_3: open_api_3_schema)
102
+
103
+ assert_raises(Committee::NotSupportOpenAPI3) do
104
+ get "/characters"
105
+ end
106
+ end
107
+
99
108
  private
100
109
 
101
110
  def new_rack_app(options = {})
@@ -94,46 +94,80 @@ describe Committee::RequestUnpacker do
94
94
 
95
95
  it "coerces form params with coerce_form_params and a schema" do
96
96
  %w[application/x-www-form-urlencoded multipart/form-data].each do |content_type|
97
+ env = {
98
+ "CONTENT_TYPE" => content_type,
99
+ "rack.input" => StringIO.new("x=1"),
100
+ }
101
+ request = Rack::Request.new(env)
102
+
103
+ router = hyper_schema.build_router({})
104
+ validator = router.build_schema_validator(request)
105
+
97
106
  schema = JsonSchema::Schema.new
98
107
  schema.properties = { "x" => JsonSchema::Schema.new }
99
108
  schema.properties["x"].type = ["integer"]
100
109
 
101
- env = {
102
- "CONTENT_TYPE" => content_type,
103
- "rack.input" => StringIO.new("x=1"),
104
- }
105
- request = Rack::Request.new(env)
110
+ link_class = Struct.new(:schema)
111
+ link_object = link_class.new(schema)
112
+
113
+ validator.instance_variable_set(:@link, link_object)
114
+
106
115
  params, _ = Committee::RequestUnpacker.new(
107
116
  request,
108
117
  allow_form_params: true,
109
118
  coerce_form_params: true,
110
- schema: schema
119
+ schema_validator: validator,
111
120
  ).call
112
121
  assert_equal({ "x" => 1 }, params)
113
122
  end
114
123
  end
115
124
 
116
- it "coerces form params with coerce_form_params, coerce_recursive and a schema" do
125
+ it "coerces form params with coerce_form_params and a OpenAPI3 schema" do
117
126
  %w[application/x-www-form-urlencoded multipart/form-data].each do |content_type|
118
- schema = JsonSchema::Schema.new
119
- schema.properties = { "x" => JsonSchema::Schema.new }
120
- schema.properties["x"].type = ["object"]
121
- schema.properties["x"].properties = { "y" => JsonSchema::Schema.new }
122
- schema.properties["x"].properties["y"].type = ["integer"]
127
+ env = {
128
+ "CONTENT_TYPE" => content_type,
129
+ "rack.input" => StringIO.new("limit=20"),
130
+ "PATH_INFO" => "/characters",
131
+ "SCRIPT_NAME" => "",
132
+ "REQUEST_METHOD" => "GET",
133
+ }
134
+ request = Rack::Request.new(env)
135
+
136
+ router = open_api_3_schema.build_router({})
137
+ validator = router.build_schema_validator(request)
123
138
 
139
+ params, _ = Committee::RequestUnpacker.new(
140
+ request,
141
+ allow_form_params: true,
142
+ coerce_form_params: true,
143
+ schema_validator: validator,
144
+ ).call
145
+ # openapi3 not support coerce in request unpacker
146
+ assert_equal({ "limit" => '20' }, params)
147
+ end
148
+ end
149
+
150
+ it "coerces error params with coerce_form_params and a OpenAPI3 schema" do
151
+ %w[application/x-www-form-urlencoded multipart/form-data].each do |content_type|
124
152
  env = {
125
- "CONTENT_TYPE" => content_type,
126
- "rack.input" => StringIO.new("x[y]=1"),
153
+ "CONTENT_TYPE" => content_type,
154
+ "rack.input" => StringIO.new("limit=twenty"),
155
+ "PATH_INFO" => "/characters",
156
+ "SCRIPT_NAME" => "",
157
+ "REQUEST_METHOD" => "GET",
127
158
  }
128
159
  request = Rack::Request.new(env)
160
+
161
+ router = open_api_3_schema.build_router({})
162
+ validator = router.build_schema_validator(request)
163
+
129
164
  params, _ = Committee::RequestUnpacker.new(
130
- request,
131
- allow_form_params: true,
132
- coerce_form_params: true,
133
- coerce_recursive: true,
134
- schema: schema
135
- ).call
136
- assert_equal({ "x" => { "y" => 1 } }, params)
165
+ request,
166
+ allow_form_params: true,
167
+ coerce_form_params: true,
168
+ schema_validator: validator,
169
+ ).call
170
+ assert_equal({ "limit" => "twenty" }, params)
137
171
  end
138
172
  end
139
173
 
@@ -1,8 +1,8 @@
1
- require_relative "test_helper"
1
+ require_relative "../../test_helper"
2
2
 
3
3
  require "stringio"
4
4
 
5
- describe Committee::RequestValidator do
5
+ describe Committee::SchemaValidator::HyperSchema::RequestValidator do
6
6
  describe 'HyperSchema' do
7
7
  before do
8
8
  @schema = JsonSchema.parse!(hyper_schema_data)
@@ -100,7 +100,7 @@ describe Committee::RequestValidator do
100
100
  def call(data, headers={}, options={})
101
101
  # hyper-schema link should be dropped into driver wrapper before it's used
102
102
  link = Committee::Drivers::HyperSchema::Link.new(@link)
103
- Committee::RequestValidator.new(link, options).call(@request, data, headers)
103
+ Committee::SchemaValidator::HyperSchema::RequestValidator.new(link, options).call(@request, data, headers)
104
104
  end
105
105
  end
106
106
 
@@ -143,7 +143,7 @@ describe Committee::RequestValidator do
143
143
 
144
144
  def call(data, headers={}, options={})
145
145
  # hyper-schema link should be dropped into driver wrapper before it's used
146
- Committee::RequestValidator.new(@link, options).call(@request, data, headers)
146
+ Committee::SchemaValidator::HyperSchema::RequestValidator.new(@link, options).call(@request, data, headers)
147
147
  end
148
148
  end
149
149
  end
@@ -1,6 +1,6 @@
1
- require_relative "test_helper"
1
+ require_relative "../../test_helper"
2
2
 
3
- describe Committee::ResponseGenerator do
3
+ describe Committee::SchemaValidator::HyperSchema::ResponseGenerator do
4
4
  before do
5
5
  @schema = JsonSchema.parse!(hyper_schema_data)
6
6
  @schema.expand_references!
@@ -75,7 +75,7 @@ describe Committee::ResponseGenerator do
75
75
  link.target_schema = JsonSchema::Schema.new
76
76
  link.target_schema.enum = ["foo"]
77
77
  link.target_schema.type = ["string"]
78
- data, _schema = Committee::ResponseGenerator.new.call(link)
78
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
79
79
  assert_equal("foo", data)
80
80
  end
81
81
 
@@ -84,15 +84,15 @@ describe Committee::ResponseGenerator do
84
84
  link.target_schema = JsonSchema::Schema.new
85
85
 
86
86
  link.target_schema.type = ["integer"]
87
- data, _schema = Committee::ResponseGenerator.new.call(link)
87
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
88
88
  assert_equal 0, data
89
89
 
90
90
  link.target_schema.type = ["null"]
91
- data, _schema = Committee::ResponseGenerator.new.call(link)
91
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
92
92
  assert_nil data
93
93
 
94
94
  link.target_schema.type = ["string"]
95
- data, _schema = Committee::ResponseGenerator.new.call(link)
95
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
96
96
  assert_equal "", data
97
97
  end
98
98
 
@@ -100,7 +100,7 @@ describe Committee::ResponseGenerator do
100
100
  link = Committee::Drivers::OpenAPI2::Link.new
101
101
  link.target_schema = JsonSchema::Schema.new
102
102
  link.target_schema.type = ["array"]
103
- data, _schema = Committee::ResponseGenerator.new.call(link)
103
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
104
104
  assert_equal([], data)
105
105
  end
106
106
 
@@ -108,7 +108,7 @@ describe Committee::ResponseGenerator do
108
108
  link = Committee::Drivers::OpenAPI2::Link.new
109
109
  link.target_schema = JsonSchema::Schema.new
110
110
  link.target_schema.type = ["object"]
111
- data, _schema = Committee::ResponseGenerator.new.call(link)
111
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
112
112
  assert_equal({}, data)
113
113
  end
114
114
 
@@ -119,7 +119,7 @@ describe Committee::ResponseGenerator do
119
119
  link.target_schema.data = { "example" => 123 }
120
120
  link.target_schema.type = ["integer"]
121
121
 
122
- data, _schema = Committee::ResponseGenerator.new.call(link)
122
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
123
123
  assert_equal 123, data
124
124
  end
125
125
 
@@ -128,13 +128,13 @@ describe Committee::ResponseGenerator do
128
128
  link.target_schema = JsonSchema::Schema.new
129
129
 
130
130
  link.target_schema.type = ["null", "integer"]
131
- data, _schema = Committee::ResponseGenerator.new.call(link)
131
+ data, _schema = Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
132
132
  assert_equal 0, data
133
133
  end
134
134
 
135
135
  def call
136
136
  # hyper-schema link should be dropped into driver wrapper before it's used
137
137
  link = Committee::Drivers::HyperSchema::Link.new(@link)
138
- Committee::ResponseGenerator.new.call(link)
138
+ Committee::SchemaValidator::HyperSchema::ResponseGenerator.new.call(link)
139
139
  end
140
140
  end
@@ -1,6 +1,6 @@
1
- require_relative "test_helper"
1
+ require_relative "../../test_helper"
2
2
 
3
- describe Committee::ResponseValidator do
3
+ describe Committee::SchemaValidator::HyperSchema::ResponseValidator do
4
4
  before do
5
5
  @status = 200
6
6
  @headers = {
@@ -101,6 +101,6 @@ describe Committee::ResponseValidator do
101
101
  def call
102
102
  # hyper-schema link should be dropped into driver wrapper before it's used
103
103
  link = Committee::Drivers::HyperSchema::Link.new(@link)
104
- Committee::ResponseValidator.new(link).call(@status, @headers, @data)
104
+ Committee::SchemaValidator::HyperSchema::ResponseValidator.new(link).call(@status, @headers, @data)
105
105
  end
106
106
  end
@@ -1,6 +1,6 @@
1
- require_relative "test_helper"
1
+ require_relative "../../test_helper"
2
2
 
3
- describe Committee::Router do
3
+ describe Committee::SchemaValidator::HyperSchema::Router do
4
4
  it "builds routes without parameters" do
5
5
  link, _ = hyper_schema_router.find_link("GET", "/apps")
6
6
  refute_nil link
@@ -60,19 +60,17 @@ describe Committee::Router do
60
60
  assert_equal '/api/pets/dog', link.href
61
61
  end
62
62
 
63
- it "fewer match not support in HyperSchema" do
64
- link, _ = hyper_schema_router.find_link("GET", "/apps/abc")
65
- refute_nil link
66
- assert_equal '/apps/{(%23%2Fdefinitions%2Fapp%2Fdefinitions%2Fname)}', link.href
67
- end
68
-
69
63
  def hyper_schema_router(options = {})
70
64
  schema = Committee::Drivers::HyperSchema.new.parse(hyper_schema_data)
71
- Committee::Router.new(schema, options)
65
+ validator_option = Committee::SchemaValidator::Option.new(options, schema, :hyper_schema)
66
+
67
+ Committee::SchemaValidator::HyperSchema::Router.new(schema, validator_option)
72
68
  end
73
69
 
74
70
  def open_api_2_router(options = {})
75
71
  schema = Committee::Drivers::OpenAPI2.new.parse(open_api_2_data)
76
- Committee::Router.new(schema, options)
72
+ validator_option = Committee::SchemaValidator::Option.new(options, schema, :hyper_schema)
73
+
74
+ Committee::SchemaValidator::HyperSchema::Router.new(schema, validator_option)
77
75
  end
78
76
  end