grape-swagger 0.20.3 → 0.21.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (57) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop_todo.yml +10 -10
  3. data/.travis.yml +8 -3
  4. data/CHANGELOG.md +27 -0
  5. data/Gemfile +2 -0
  6. data/README.md +111 -12
  7. data/UPGRADING.md +9 -0
  8. data/grape-swagger.gemspec +1 -3
  9. data/lib/grape-swagger.rb +8 -1
  10. data/lib/grape-swagger/doc_methods/optional_object.rb +14 -2
  11. data/lib/grape-swagger/doc_methods/parse_params.rb +3 -4
  12. data/lib/grape-swagger/doc_methods/path_string.rb +4 -3
  13. data/lib/grape-swagger/endpoint.rb +25 -55
  14. data/lib/grape-swagger/errors.rb +3 -0
  15. data/lib/grape-swagger/grape/route.rb +2 -1
  16. data/lib/grape-swagger/model_parsers.rb +33 -0
  17. data/lib/grape-swagger/version.rb +1 -1
  18. data/spec/issues/403_versions_spec.rb +20 -4
  19. data/spec/lib/model_parsers_spec.rb +102 -0
  20. data/spec/lib/optional_object_spec.rb +15 -11
  21. data/spec/lib/path_string_spec.rb +72 -18
  22. data/spec/lib/produces_consumes_spec.rb +10 -5
  23. data/spec/spec_helper.rb +4 -2
  24. data/spec/support/empty_model_parser.rb +20 -0
  25. data/spec/support/mock_parser.rb +22 -0
  26. data/spec/support/model_parsers/entity_parser.rb +325 -0
  27. data/spec/support/{api_swagger_v2_result.rb → model_parsers/mock_parser.rb} +186 -60
  28. data/spec/support/model_parsers/representable_parser.rb +394 -0
  29. data/spec/support/the_paths_definitions.rb +7 -3
  30. data/spec/swagger_v2/api_swagger_v2_definitions-models_spec.rb +5 -4
  31. data/spec/swagger_v2/api_swagger_v2_detail_spec.rb +3 -3
  32. data/spec/swagger_v2/api_swagger_v2_extensions_spec.rb +1 -1
  33. data/spec/swagger_v2/api_swagger_v2_format-content_type_spec.rb +1 -1
  34. data/spec/swagger_v2/api_swagger_v2_headers_spec.rb +5 -3
  35. data/spec/swagger_v2/api_swagger_v2_hide_documentation_path_spec.rb +1 -1
  36. data/spec/swagger_v2/api_swagger_v2_mounted_spec.rb +1 -1
  37. data/spec/swagger_v2/api_swagger_v2_param_type_body_nested_spec.rb +25 -14
  38. data/spec/swagger_v2/api_swagger_v2_param_type_body_spec.rb +22 -12
  39. data/spec/swagger_v2/api_swagger_v2_param_type_spec.rb +30 -18
  40. data/spec/swagger_v2/api_swagger_v2_request_params_fix_spec.rb +6 -3
  41. data/spec/swagger_v2/api_swagger_v2_response_spec.rb +13 -40
  42. data/spec/swagger_v2/api_swagger_v2_spec.rb +4 -2
  43. data/spec/swagger_v2/api_swagger_v2_type-format_spec.rb +6 -36
  44. data/spec/swagger_v2/default_api_spec.rb +10 -2
  45. data/spec/swagger_v2/endpoint_versioned_path_spec.rb +30 -0
  46. data/spec/swagger_v2/errors_spec.rb +75 -0
  47. data/spec/swagger_v2/hide_api_spec.rb +22 -4
  48. data/spec/swagger_v2/mounted_target_class_spec.rb +6 -2
  49. data/spec/swagger_v2/namespace_tags_prefix_spec.rb +6 -3
  50. data/spec/swagger_v2/namespace_tags_spec.rb +6 -3
  51. data/spec/swagger_v2/params_array_spec.rb +4 -2
  52. data/spec/swagger_v2/params_hash_spec.rb +4 -2
  53. data/spec/swagger_v2/params_nested_spec.rb +4 -2
  54. data/spec/swagger_v2/simple_mounted_api_spec.rb +66 -24
  55. metadata +23 -40
  56. data/spec/support/the_api_entities.rb +0 -50
  57. data/spec/swagger_v2/response_model_spec.rb +0 -208
@@ -0,0 +1,394 @@
1
+ require 'representable/json'
2
+
3
+ RSpec.shared_context 'representable swagger example' do
4
+ before :all do
5
+ module Entities
6
+ class Something < Representable::Decorator
7
+ include Representable::JSON
8
+
9
+ class << self
10
+ # Representable doesn't have documentation method, mock this
11
+ def documentation
12
+ {
13
+ id: { type: Integer, desc: 'Identity of Something' },
14
+ text: { type: String, desc: 'Content of something.' },
15
+ links: { type: 'link', is_array: true },
16
+ others: { type: 'text', is_array: false }
17
+ }
18
+ end
19
+ end
20
+
21
+ property :id, documentation: { type: Integer, desc: 'Identity of Something' }
22
+ property :text, documentation: { type: String, desc: 'Content of something.' }
23
+ property :links, documentation: { type: 'link', is_array: true }
24
+ property :others, documentation: { type: 'text', is_array: false }
25
+ end
26
+
27
+ class EnumValues < Representable::Decorator
28
+ include Representable::JSON
29
+
30
+ property :gender, documentation: { type: 'string', desc: 'Content of something.', values: %w(Male Female) }
31
+ property :number, documentation: { type: 'integer', desc: 'Content of something.', values: [1, 2] }
32
+ end
33
+
34
+ class AliasedThing < Representable::Decorator
35
+ include Representable::JSON
36
+
37
+ property :something, as: :post, decorator: Entities::Something, documentation: { type: 'Something', desc: 'Reference to something.' }
38
+ end
39
+
40
+ class FourthLevel < Representable::Decorator
41
+ include Representable::JSON
42
+
43
+ property :text, documentation: { type: 'string' }
44
+ end
45
+
46
+ class ThirdLevel < Representable::Decorator
47
+ include Representable::JSON
48
+
49
+ property :parts, decorator: Entities::FourthLevel, documentation: { type: 'FourthLevel' }
50
+ end
51
+
52
+ class SecondLevel < Representable::Decorator
53
+ include Representable::JSON
54
+
55
+ property :parts, decorator: Entities::ThirdLevel, documentation: { type: 'ThirdLevel' }
56
+ end
57
+
58
+ class FirstLevel < Representable::Decorator
59
+ include Representable::JSON
60
+
61
+ property :parts, decorator: Entities::SecondLevel, documentation: { type: 'SecondLevel' }
62
+ end
63
+
64
+ class QueryInputElement < Representable::Decorator
65
+ include Representable::JSON
66
+
67
+ property :key, documentation: {
68
+ type: String, desc: 'Name of parameter', required: true
69
+ }
70
+ property :value, documentation: {
71
+ type: String, desc: 'Value of parameter', required: true
72
+ }
73
+ end
74
+
75
+ class QueryInput < Representable::Decorator
76
+ include Representable::JSON
77
+
78
+ property :elements, decorator: Entities::QueryInputElement, documentation: {
79
+ type: 'QueryInputElement',
80
+ desc: 'Set of configuration',
81
+ param_type: 'body',
82
+ is_array: true,
83
+ required: true
84
+ }
85
+ end
86
+
87
+ class ApiError < Representable::Decorator
88
+ include Representable::JSON
89
+
90
+ property :code, documentation: { type: Integer, desc: 'status code' }
91
+ property :message, documentation: { type: String, desc: 'error message' }
92
+ end
93
+
94
+ class SecondApiError < Representable::Decorator
95
+ include Representable::JSON
96
+
97
+ property :code, documentation: { type: Integer }
98
+ property :severity, documentation: { type: String }
99
+ property :message, documentation: { type: String }
100
+ end
101
+
102
+ class ResponseItem < Representable::Decorator
103
+ include Representable::JSON
104
+
105
+ class << self
106
+ def documentation
107
+ {
108
+ id: { type: Integer },
109
+ name: { type: String }
110
+ }
111
+ end
112
+ end
113
+
114
+ property :id, documentation: { type: Integer }
115
+ property :name, documentation: { type: String }
116
+ end
117
+
118
+ class OtherItem < Representable::Decorator
119
+ include Representable::JSON
120
+
121
+ property :key, documentation: { type: Integer }
122
+ property :symbol, documentation: { type: String }
123
+ end
124
+
125
+ class UseResponse < Representable::Decorator
126
+ include Representable::JSON
127
+
128
+ class << self
129
+ def documentation
130
+ {
131
+ :description => { type: String },
132
+ '$responses' => { is_array: true }
133
+ }
134
+ end
135
+ end
136
+
137
+ property :description, documentation: { type: String }
138
+ property :items, as: '$responses', decorator: Entities::ResponseItem, documentation: { is_array: true }
139
+ end
140
+
141
+ class UseItemResponseAsType < Representable::Decorator
142
+ include Representable::JSON
143
+
144
+ property :description, documentation: { type: String }
145
+ property :responses, documentation: { type: Entities::ResponseItem, is_array: false }
146
+ end
147
+
148
+ class UseAddress < Representable::Decorator
149
+ include Representable::JSON
150
+
151
+ property :street, documentation: { type: String, desc: 'street' }
152
+ property :postcode, documentation: { type: String, desc: 'postcode' }
153
+ property :city, documentation: { type: String, desc: 'city' }
154
+ property :country, documentation: { type: String, desc: 'country' }
155
+ end
156
+
157
+ class UseNestedWithAddress < Representable::Decorator
158
+ include Representable::JSON
159
+
160
+ property :name, documentation: { type: String }
161
+ property :address, decorator: Entities::UseAddress
162
+ end
163
+
164
+ class TypedDefinition < Representable::Decorator
165
+ include Representable::JSON
166
+
167
+ property :prop_integer, documentation: { type: Integer, desc: 'prop_integer description' }
168
+ property :prop_long, documentation: { type: Numeric, desc: 'prop_long description' }
169
+ property :prop_float, documentation: { type: Float, desc: 'prop_float description' }
170
+ property :prop_double, documentation: { type: BigDecimal, desc: 'prop_double description' }
171
+ property :prop_string, documentation: { type: String, desc: 'prop_string description' }
172
+ property :prop_symbol, documentation: { type: Symbol, desc: 'prop_symbol description' }
173
+ property :prop_date, documentation: { type: Date, desc: 'prop_date description' }
174
+ property :prop_date_time, documentation: { type: DateTime, desc: 'prop_date_time description' }
175
+ property :prop_time, documentation: { type: Time, desc: 'prop_time description' }
176
+ property :prop_password, documentation: { type: 'password', desc: 'prop_password description' }
177
+ property :prop_email, documentation: { type: 'email', desc: 'prop_email description' }
178
+ property :prop_boolean, documentation: { type: Virtus::Attribute::Boolean, desc: 'prop_boolean description' }
179
+ property :prop_file, documentation: { type: File, desc: 'prop_file description' }
180
+ property :prop_json, documentation: { type: JSON, desc: 'prop_json description' }
181
+ end
182
+
183
+ class RecursiveModel < Representable::Decorator
184
+ include Representable::JSON
185
+
186
+ property :name, documentation: { type: String, desc: 'The name.' }
187
+ property :children, decorator: self, documentation: { type: 'RecursiveModel', is_array: true, desc: 'The child nodes.' }
188
+ end
189
+ end
190
+ end
191
+
192
+ let(:swagger_definitions_models) do
193
+ {
194
+ 'ApiError' => { 'type' => 'object', 'properties' => { 'code' => { 'description' => 'status code', 'type' => 'integer', 'format' => 'int32' }, 'message' => { 'description' => 'error message', 'type' => 'string' } } },
195
+ 'ResponseItem' => { 'type' => 'object', 'properties' => { 'id' => { 'description' => '', 'type' => 'integer', 'format' => 'int32' }, 'name' => { 'description' => '', 'type' => 'string' } } },
196
+ 'UseResponse' => { 'type' => 'object', 'properties' => { 'description' => { 'description' => '', 'type' => 'string' }, 'items' => { 'type' => 'array', 'items' => { '$ref' => '#/definitions/ResponseItem' }, 'description' => '' } } },
197
+ 'RecursiveModel' => { 'type' => 'object', 'properties' => { 'name' => { 'type' => 'string', 'description' => 'The name.' }, 'children' => { 'type' => 'array', 'items' => { '$ref' => '#/definitions/RecursiveModel' }, 'description' => 'The child nodes.' } } }
198
+ }
199
+ end
200
+
201
+ let(:swagger_nested_type) do
202
+ {
203
+ 'ApiError' => { 'type' => 'object', 'properties' => { 'code' => { 'description' => 'status code', 'type' => 'integer', 'format' => 'int32' }, 'message' => { 'description' => 'error message', 'type' => 'string' } }, 'description' => 'This returns something' },
204
+ 'UseItemResponseAsType' => { 'type' => 'object', 'properties' => { 'description' => { 'description' => '', 'type' => 'string' }, 'responses' => { 'description' => '', 'type' => 'ResponseItem' } }, 'description' => 'This returns something' }
205
+ }
206
+ end
207
+
208
+ let(:swagger_entity_as_response_object) do
209
+ {
210
+ 'ApiError' => { 'type' => 'object', 'properties' => { 'code' => { 'description' => 'status code', 'type' => 'integer', 'format' => 'int32' }, 'message' => { 'description' => 'error message', 'type' => 'string' } }, 'description' => 'This returns something' },
211
+ 'ResponseItem' => { 'type' => 'object', 'properties' => { 'id' => { 'description' => '', 'type' => 'integer', 'format' => 'int32' }, 'name' => { 'description' => '', 'type' => 'string' } } },
212
+ 'UseResponse' => { 'type' => 'object', 'properties' => { 'description' => { 'description' => '', 'type' => 'string' }, 'items' => { 'type' => 'array', 'items' => { '$ref' => '#/definitions/ResponseItem' }, 'description' => '' } }, 'description' => 'This returns something' }
213
+ }
214
+ end
215
+
216
+ let(:swagger_params_as_response_object) do
217
+ {
218
+ 'ApiError' => { 'type' => 'object', 'properties' => { 'code' => { 'description' => 'status code', 'type' => 'integer', 'format' => 'int32' }, 'message' => { 'description' => 'error message', 'type' => 'string' } }, 'description' => 'This returns something' }
219
+ }
220
+ end
221
+
222
+ let(:swagger_typed_defintion) do
223
+ {
224
+ 'prop_boolean' => { 'description' => 'prop_boolean description', 'type' => 'boolean' },
225
+ 'prop_date' => { 'description' => 'prop_date description', 'type' => 'string', 'format' => 'date' },
226
+ 'prop_date_time' => { 'description' => 'prop_date_time description', 'type' => 'string', 'format' => 'date-time' },
227
+ 'prop_double' => { 'description' => 'prop_double description', 'type' => 'number', 'format' => 'double' },
228
+ 'prop_email' => { 'description' => 'prop_email description', 'type' => 'string', 'format' => 'email' },
229
+ 'prop_file' => { 'description' => 'prop_file description', 'type' => 'file' },
230
+ 'prop_float' => { 'description' => 'prop_float description', 'type' => 'number', 'format' => 'float' },
231
+ 'prop_integer' => { 'description' => 'prop_integer description', 'type' => 'integer', 'format' => 'int32' },
232
+ 'prop_json' => { 'description' => 'prop_json description', 'type' => 'Representable::JSON' },
233
+ 'prop_long' => { 'description' => 'prop_long description', 'type' => 'integer', 'format' => 'int64' },
234
+ 'prop_password' => { 'description' => 'prop_password description', 'type' => 'string', 'format' => 'password' },
235
+ 'prop_string' => { 'description' => 'prop_string description', 'type' => 'string' },
236
+ 'prop_symbol' => { 'description' => 'prop_symbol description', 'type' => 'string' },
237
+ 'prop_time' => { 'description' => 'prop_time description', 'type' => 'string', 'format' => 'date-time' }
238
+ }
239
+ end
240
+
241
+ let(:swagger_json) do
242
+ {
243
+ 'info' => {
244
+ 'title' => 'The API title to be displayed on the API homepage.',
245
+ 'description' => 'A description of the API.',
246
+ 'termsOfServiceUrl' => 'www.The-URL-of-the-terms-and-service.com',
247
+ 'contact' => { 'name' => 'Contact name', 'email' => 'Contact@email.com', 'url' => 'Contact URL' },
248
+ 'license' => { 'name' => 'The name of the license.', 'url' => 'www.The-URL-of-the-license.org' },
249
+ 'version' => '0.0.1'
250
+ },
251
+ 'swagger' => '2.0',
252
+ 'produces' => ['application/json'],
253
+ 'host' => 'example.org',
254
+ 'basePath' => '/api',
255
+ 'tags' => [
256
+ { 'name' => 'other_thing', 'description' => 'Operations about other_things' },
257
+ { 'name' => 'thing', 'description' => 'Operations about things' },
258
+ { 'name' => 'thing2', 'description' => 'Operations about thing2s' },
259
+ { 'name' => 'dummy', 'description' => 'Operations about dummies' }
260
+ ],
261
+ 'paths' => {
262
+ '/v3/other_thing/{elements}' => {
263
+ 'get' => {
264
+ 'summary' => 'nested route inside namespace',
265
+ 'description' => 'nested route inside namespace',
266
+ 'produces' => ['application/json'],
267
+ 'parameters' => [{ 'in' => 'body', 'name' => 'elements', 'description' => 'Set of configuration', 'type' => 'array', 'items' => { 'type' => 'string' }, 'required' => true }],
268
+ 'responses' => { '200' => { 'description' => 'nested route inside namespace', 'schema' => { '$ref' => '#/definitions/QueryInput' } } },
269
+ 'tags' => ['other_thing'],
270
+ 'operationId' => 'getV3OtherThingElements',
271
+ 'x-amazon-apigateway-auth' => { 'type' => 'none' },
272
+ 'x-amazon-apigateway-integration' => { 'type' => 'aws', 'uri' => 'foo_bar_uri', 'httpMethod' => 'get' }
273
+ }
274
+ },
275
+ '/thing' => {
276
+ 'get' => {
277
+ 'summary' => 'This gets Things.',
278
+ 'description' => 'This gets Things.',
279
+ 'produces' => ['application/json'],
280
+ 'parameters' => [
281
+ { 'in' => 'query', 'name' => 'id', 'description' => 'Identity of Something', 'type' => 'integer', 'format' => 'int32', 'required' => false },
282
+ { 'in' => 'query', 'name' => 'text', 'description' => 'Content of something.', 'type' => 'string', 'required' => false },
283
+ { 'in' => 'formData', 'name' => 'links', 'type' => 'array', 'items' => { 'type' => 'link' }, 'required' => false },
284
+ { 'in' => 'query', 'name' => 'others', 'type' => 'text', 'required' => false }
285
+ ],
286
+ 'responses' => { '200' => { 'description' => 'This gets Things.' }, '401' => { 'description' => 'Unauthorized', 'schema' => { '$ref' => '#/definitions/ApiError' } } },
287
+ 'tags' => ['thing'],
288
+ 'operationId' => 'getThing'
289
+ },
290
+ 'post' => {
291
+ 'summary' => 'This creates Thing.',
292
+ 'description' => 'This creates Thing.',
293
+ 'produces' => ['application/json'],
294
+ 'consumes' => ['application/json'],
295
+ 'parameters' => [
296
+ { 'in' => 'formData', 'name' => 'text', 'description' => 'Content of something.', 'type' => 'string', 'required' => true },
297
+ { 'in' => 'formData', 'name' => 'links', 'type' => 'array', 'items' => { 'type' => 'string' }, 'required' => true }
298
+ ],
299
+ 'responses' => { '201' => { 'description' => 'This creates Thing.', 'schema' => { '$ref' => '#/definitions/Something' } }, '422' => { 'description' => 'Unprocessible Entity' } },
300
+ 'tags' => ['thing'],
301
+ 'operationId' => 'postThing'
302
+ }
303
+ },
304
+ '/thing/{id}' => {
305
+ 'get' => {
306
+ 'summary' => 'This gets Thing.',
307
+ 'description' => 'This gets Thing.',
308
+ 'produces' => ['application/json'],
309
+ 'parameters' => [{ 'in' => 'path', 'name' => 'id', 'type' => 'integer', 'format' => 'int32', 'required' => true }],
310
+ 'responses' => { '200' => { 'description' => 'getting a single thing' }, '401' => { 'description' => 'Unauthorized' } },
311
+ 'tags' => ['thing'],
312
+ 'operationId' => 'getThingId'
313
+ },
314
+ 'put' => {
315
+ 'summary' => 'This updates Thing.',
316
+ 'description' => 'This updates Thing.',
317
+ 'produces' => ['application/json'],
318
+ 'consumes' => ['application/json'],
319
+ 'parameters' => [
320
+ { 'in' => 'path', 'name' => 'id', 'type' => 'integer', 'format' => 'int32', 'required' => true },
321
+ { 'in' => 'formData', 'name' => 'text', 'description' => 'Content of something.', 'type' => 'string', 'required' => false },
322
+ { 'in' => 'formData', 'name' => 'links', 'type' => 'array', 'items' => { 'type' => 'string' }, 'required' => false }
323
+ ],
324
+ 'responses' => { '200' => { 'description' => 'This updates Thing.', 'schema' => { '$ref' => '#/definitions/Something' } } },
325
+ 'tags' => ['thing'],
326
+ 'operationId' => 'putThingId'
327
+ },
328
+ 'delete' => {
329
+ 'summary' => 'This deletes Thing.',
330
+ 'description' => 'This deletes Thing.',
331
+ 'produces' => ['application/json'],
332
+ 'parameters' => [{ 'in' => 'path', 'name' => 'id', 'type' => 'integer', 'format' => 'int32', 'required' => true }],
333
+ 'responses' => { '200' => { 'description' => 'This deletes Thing.', 'schema' => { '$ref' => '#/definitions/Something' } } },
334
+ 'tags' => ['thing'],
335
+ 'operationId' => 'deleteThingId'
336
+ }
337
+ },
338
+ '/thing2' => {
339
+ 'get' => {
340
+ 'summary' => 'This gets Things.',
341
+ 'description' => 'This gets Things.',
342
+ 'produces' => ['application/json'],
343
+ 'responses' => { '200' => { 'description' => 'get Horses', 'schema' => { '$ref' => '#/definitions/Something' } }, '401' => { 'description' => 'HorsesOutError', 'schema' => { '$ref' => '#/definitions/ApiError' } } },
344
+ 'tags' => ['thing2'],
345
+ 'operationId' => 'getThing2'
346
+ }
347
+ },
348
+ '/dummy/{id}' => {
349
+ 'delete' => {
350
+ 'summary' => 'dummy route.',
351
+ 'description' => 'dummy route.',
352
+ 'produces' => ['application/json'],
353
+ 'parameters' => [{ 'in' => 'path', 'name' => 'id', 'type' => 'integer', 'format' => 'int32', 'required' => true }],
354
+ 'responses' => { '204' => { 'description' => 'dummy route.' }, '401' => { 'description' => 'Unauthorized' } },
355
+ 'tags' => ['dummy'],
356
+ 'operationId' => 'deleteDummyId'
357
+ }
358
+ }
359
+ },
360
+ 'definitions' => {
361
+ 'QueryInput' => {
362
+ 'type' => 'object',
363
+ 'properties' => { 'elements' => { 'type' => 'array', 'items' => { '$ref' => '#/definitions/QueryInputElement' }, 'description' => 'Set of configuration' } },
364
+ 'description' => 'nested route inside namespace'
365
+ },
366
+ 'QueryInputElement' => {
367
+ 'type' => 'object',
368
+ 'properties' => { 'key' => { 'type' => 'string', 'description' => 'Name of parameter' }, 'value' => { 'type' => 'string', 'description' => 'Value of parameter' } }
369
+ },
370
+ 'ApiError' => {
371
+ 'type' => 'object',
372
+ 'properties' => { 'code' => { 'type' => 'integer', 'format' => 'int32', 'description' => 'status code' }, 'message' => { 'type' => 'string', 'description' => 'error message' } },
373
+ 'description' => 'This gets Things.'
374
+ },
375
+ 'Something' => {
376
+ 'type' => 'object',
377
+ 'properties' => {
378
+ 'id' => { 'type' => 'integer', 'format' => 'int32', 'description' => 'Identity of Something' },
379
+ 'text' => { 'type' => 'string', 'description' => 'Content of something.' },
380
+ 'links' => { 'type' => 'array', 'items' => { 'description' => '', 'type' => 'link' } },
381
+ 'others' => { 'description' => '', 'type' => 'text' }
382
+ },
383
+ 'description' => 'This gets Things.'
384
+ }
385
+ }
386
+ }
387
+ end
388
+
389
+ let(:http_verbs) { %w(get post put delete) }
390
+ end
391
+
392
+ def mounted_paths
393
+ %w( /thing /other_thing /dummy )
394
+ end
@@ -43,7 +43,8 @@ RSpec.shared_context 'the api paths/defs' do
43
43
  responses: { 200 => { description: 'get in path /wo entity', schema: { '$ref' => '#/definitions/InBody' } } },
44
44
  tags: ['in_body'],
45
45
  operationId: 'getInBodyKey'
46
- } }
46
+ }
47
+ }
47
48
  }
48
49
  end
49
50
 
@@ -60,7 +61,8 @@ RSpec.shared_context 'the api paths/defs' do
60
61
  responses: { 201 => { description: 'post in body /wo entity', schema: { '$ref' => '#/definitions/InBody' } } },
61
62
  tags: ['in_body'],
62
63
  operationId: 'postInBody'
63
- } }
64
+ }
65
+ }
64
66
  end
65
67
 
66
68
  let(:definitions) do
@@ -72,7 +74,9 @@ RSpec.shared_context 'the api paths/defs' do
72
74
  in_body_2: { type: 'string' },
73
75
  in_body_3: { type: 'string' },
74
76
  key: { type: 'integer', format: 'int32' }
75
- } } }
77
+ }
78
+ }
79
+ }
76
80
  end
77
81
 
78
82
  let(:expected_post_defs) do
@@ -1,7 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe 'definitions/models' do
4
- include_context 'the api entities'
4
+ include_context "#{MODEL_PARSER} swagger example"
5
5
 
6
6
  before :all do
7
7
  module TheApi
@@ -9,8 +9,9 @@ describe 'definitions/models' do
9
9
  format :json
10
10
 
11
11
  add_swagger_documentation models: [
12
- TheApi::Entities::UseResponse,
13
- TheApi::Entities::ApiError
12
+ ::Entities::UseResponse,
13
+ ::Entities::ApiError,
14
+ ::Entities::RecursiveModel
14
15
  ]
15
16
  end
16
17
  end
@@ -27,6 +28,6 @@ describe 'definitions/models' do
27
28
 
28
29
  specify do
29
30
  expect(subject).to include 'definitions'
30
- expect(subject['definitions']).to include 'ResponseItem', 'UseResponse', 'ApiError'
31
+ expect(subject['definitions']).to include(swagger_definitions_models)
31
32
  end
32
33
  end