apipie-rails 0.9.1 → 0.9.2
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 +4 -4
- data/.rubocop.yml +75 -0
- data/.rubocop_todo.yml +780 -201
- data/CHANGELOG.md +8 -0
- data/app/controllers/apipie/apipies_controller.rb +5 -6
- data/lib/apipie/apipie_module.rb +2 -2
- data/lib/apipie/application.rb +6 -6
- data/lib/apipie/configuration.rb +11 -11
- data/lib/apipie/dsl_definition.rb +11 -10
- data/lib/apipie/error_description.rb +2 -2
- data/lib/apipie/extractor/writer.rb +11 -11
- data/lib/apipie/generator/swagger/context.rb +27 -0
- data/lib/apipie/generator/swagger/operation_id.rb +51 -0
- data/lib/apipie/generator/swagger/param_description/builder.rb +105 -0
- data/lib/apipie/generator/swagger/param_description/composite.rb +111 -0
- data/lib/apipie/generator/swagger/param_description/description.rb +15 -0
- data/lib/apipie/generator/swagger/param_description/in.rb +37 -0
- data/lib/apipie/generator/swagger/param_description/name.rb +18 -0
- data/lib/apipie/generator/swagger/param_description/type.rb +108 -0
- data/lib/apipie/generator/swagger/param_description.rb +18 -0
- data/lib/apipie/generator/swagger/type_extractor.rb +2 -2
- data/lib/apipie/method_description.rb +4 -5
- data/lib/apipie/param_description.rb +7 -7
- data/lib/apipie/resource_description.rb +3 -3
- data/lib/apipie/response_description.rb +2 -2
- data/lib/apipie/response_description_adapter.rb +7 -5
- data/lib/apipie/swagger_generator.rb +54 -202
- data/lib/apipie/validator.rb +3 -3
- data/lib/apipie/version.rb +1 -1
- data/lib/apipie-rails.rb +9 -0
- data/lib/tasks/apipie.rake +5 -6
- data/spec/controllers/users_controller_spec.rb +3 -2
- data/spec/lib/generator/swagger/context_spec.rb +35 -0
- data/spec/lib/generator/swagger/operation_id_spec.rb +63 -0
- data/spec/lib/generator/swagger/param_description/builder_spec.rb +163 -0
- data/spec/lib/generator/swagger/param_description/composite_spec.rb +95 -0
- data/spec/lib/generator/swagger/param_description/description_spec.rb +79 -0
- data/spec/lib/generator/swagger/param_description/in_spec.rb +86 -0
- data/spec/lib/generator/swagger/param_description/name_spec.rb +81 -0
- data/spec/lib/generator/swagger/param_description/type_spec.rb +178 -0
- data/spec/lib/generator/swagger/param_description_spec.rb +28 -0
- data/spec/lib/generator/swagger/type_extractor_spec.rb +38 -18
- data/spec/lib/param_group_spec.rb +5 -5
- metadata +20 -2
data/CHANGELOG.md
CHANGED
@@ -4,6 +4,14 @@
|
|
4
4
|
Also deleted the `Gemfile` that was now a broken symlink.
|
5
5
|
please use `export BUNDLE_GEMFILE='gemfiles/Gemfile.rails61'; bundle exec rspec` to run the test suite
|
6
6
|
|
7
|
+
## [v0.9.2](https://github.com/Apipie/apipie-rails/tree/v0.9.2) (2023-02-07)
|
8
|
+
[Full Changelog](https://github.com/Apipie/apipie-rails/compare/v0.9.1...v0.9.2)
|
9
|
+
* [Rubocop] More Rubocop Auto corrections [#795](https://github.com/Apipie/apipie-rails/pull/795)[#781](https://github.com/Apipie/apipie-rails/pull/781)[#791](https://github.com/Apipie/apipie-rails/pull/791)[#788](https://github.com/Apipie/apipie-rails/pull/788) (Rubocop Challenger)
|
10
|
+
* [Fix] Can't include translation in full description ([#446](https://github.com/Apipie/apipie-rails/issues/446)) [#808](https://github.com/Apipie/apipie-rails/pull/808)( Peter Nagy)
|
11
|
+
* [Refactor] Move swagger param description creation [#810](https://github.com/Apipie/apipie-rails/pull/810) (Panos Dalitsouris)
|
12
|
+
* [Rubocop] Redo rubocop TODOs, set HashSyntax config to most used style [#814](https://github.com/Apipie/apipie-rails/pull/814) (Mathieu Jobin)
|
13
|
+
* [Fix] Swagger missing i18n [#815](https://github.com/Apipie/apipie-rails/pull/815) (@jirubio)
|
14
|
+
|
7
15
|
## [v0.9.1](https://github.com/Apipie/apipie-rails/tree/v0.9.1) (2023-01-16)
|
8
16
|
[Full Changelog](https://github.com/Apipie/apipie-rails/compare/v0.9.0...v0.9.1)
|
9
17
|
* [Refactor] Create test cache files under a not version controlled directory [#809](https://github.com/Apipie/apipie-rails/pull/809) (Panos Dalitsouris)
|
@@ -98,12 +98,11 @@ module Apipie
|
|
98
98
|
return nil unless Apipie.configuration.translate
|
99
99
|
lang = Apipie.configuration.default_locale
|
100
100
|
[:resource, :method, :version].each do |par|
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
end
|
101
|
+
next unless params[par]
|
102
|
+
splitted = params[par].split('.')
|
103
|
+
if splitted.length > 1 && (Apipie.configuration.languages.include?(splitted.last) || Apipie.configuration.default_locale == splitted.last)
|
104
|
+
lang = splitted.last
|
105
|
+
params[par].sub!(".#{lang}", '')
|
107
106
|
end
|
108
107
|
end
|
109
108
|
lang
|
data/lib/apipie/apipie_module.rb
CHANGED
@@ -70,11 +70,11 @@ module Apipie
|
|
70
70
|
end
|
71
71
|
|
72
72
|
def self.app_info_version_valid?(version)
|
73
|
-
version && self.configuration.app_info.
|
73
|
+
version && self.configuration.app_info.key?(version)
|
74
74
|
end
|
75
75
|
|
76
76
|
def self.api_base_url_version_valid?(version)
|
77
|
-
version && self.configuration.api_base_url.
|
77
|
+
version && self.configuration.api_base_url.key?(version)
|
78
78
|
end
|
79
79
|
|
80
80
|
def self.record(record)
|
data/lib/apipie/application.rb
CHANGED
@@ -147,7 +147,7 @@ module Apipie
|
|
147
147
|
|
148
148
|
def get_param_group(controller, name)
|
149
149
|
key = "#{controller.name}##{name}"
|
150
|
-
if @param_groups.
|
150
|
+
if @param_groups.key?(key)
|
151
151
|
return @param_groups[key]
|
152
152
|
else
|
153
153
|
raise "param group #{key} not defined"
|
@@ -185,7 +185,7 @@ module Apipie
|
|
185
185
|
resource_description.method_description(method_name.to_sym)
|
186
186
|
end
|
187
187
|
end
|
188
|
-
alias
|
188
|
+
alias [] get_method_description
|
189
189
|
|
190
190
|
# options:
|
191
191
|
# => "users"
|
@@ -198,7 +198,7 @@ module Apipie
|
|
198
198
|
version = crumbs.first
|
199
199
|
end
|
200
200
|
version ||= Apipie.configuration.default_version
|
201
|
-
if @resource_descriptions.
|
201
|
+
if @resource_descriptions.key?(version)
|
202
202
|
return @resource_descriptions[version][crumbs.last]
|
203
203
|
end
|
204
204
|
else
|
@@ -373,7 +373,7 @@ module Apipie
|
|
373
373
|
def get_resource_name(klass)
|
374
374
|
if klass.class == String
|
375
375
|
klass
|
376
|
-
elsif @controller_to_resource_id.
|
376
|
+
elsif @controller_to_resource_id.key?(klass)
|
377
377
|
@controller_to_resource_id[klass]
|
378
378
|
elsif Apipie.configuration.namespaced_resources? && klass.respond_to?(:controller_path)
|
379
379
|
return nil if klass == ActionController::Base
|
@@ -408,9 +408,9 @@ module Apipie
|
|
408
408
|
# Make sure that the version/resource_name/method_name are valid combination
|
409
409
|
# resource_name and method_name can be nil
|
410
410
|
def valid_search_args?(version, resource_name, method_name)
|
411
|
-
return false unless self.resource_descriptions.
|
411
|
+
return false unless self.resource_descriptions.key?(version)
|
412
412
|
if resource_name
|
413
|
-
return false unless self.resource_descriptions[version].
|
413
|
+
return false unless self.resource_descriptions[version].key?(resource_name)
|
414
414
|
if method_name
|
415
415
|
resource_description = self.resource_descriptions[version][resource_name]
|
416
416
|
return false unless resource_description.valid_method_name?(method_name)
|
data/lib/apipie/configuration.rb
CHANGED
@@ -14,13 +14,13 @@ module Apipie
|
|
14
14
|
:swagger_allow_additional_properties_in_response, :swagger_responses_use_refs,
|
15
15
|
:swagger_schemes, :swagger_security_definitions, :swagger_global_security
|
16
16
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
17
|
+
alias validate? validate
|
18
|
+
alias required_by_default? required_by_default
|
19
|
+
alias namespaced_resources? namespaced_resources
|
20
|
+
alias swagger_include_warning_tags? swagger_include_warning_tags
|
21
|
+
alias swagger_json_input_uses_refs? swagger_json_input_uses_refs
|
22
|
+
alias swagger_responses_use_refs? swagger_responses_use_refs
|
23
|
+
alias swagger_generate_x_computed_id_field? swagger_generate_x_computed_id_field
|
24
24
|
|
25
25
|
# matcher to be used in Dir.glob to find controllers to be reloaded e.g.
|
26
26
|
#
|
@@ -51,17 +51,17 @@ module Apipie
|
|
51
51
|
def validate_value
|
52
52
|
return (validate? && @validate_value)
|
53
53
|
end
|
54
|
-
|
54
|
+
alias validate_value? validate_value
|
55
55
|
|
56
56
|
def validate_presence
|
57
57
|
return (validate? && @validate_presence)
|
58
58
|
end
|
59
|
-
|
59
|
+
alias validate_presence? validate_presence
|
60
60
|
|
61
61
|
def validate_key
|
62
62
|
return (validate? && @validate_key)
|
63
63
|
end
|
64
|
-
|
64
|
+
alias validate_key? validate_key
|
65
65
|
|
66
66
|
def process_value?
|
67
67
|
@process_params
|
@@ -73,7 +73,7 @@ module Apipie
|
|
73
73
|
#
|
74
74
|
# rake apipie:cache
|
75
75
|
attr_accessor :use_cache
|
76
|
-
|
76
|
+
alias use_cache? use_cache
|
77
77
|
|
78
78
|
attr_writer :cache_dir
|
79
79
|
def cache_dir
|
@@ -70,7 +70,7 @@ module Apipie
|
|
70
70
|
def short(short)
|
71
71
|
_apipie_dsl_data[:short_description] = short
|
72
72
|
end
|
73
|
-
alias
|
73
|
+
alias short_description short
|
74
74
|
|
75
75
|
def path(path)
|
76
76
|
_apipie_dsl_data[:path] = path
|
@@ -160,7 +160,7 @@ module Apipie
|
|
160
160
|
def api_versions(*versions)
|
161
161
|
_apipie_dsl_data[:api_versions].concat(versions)
|
162
162
|
end
|
163
|
-
alias
|
163
|
+
alias api_version api_versions
|
164
164
|
|
165
165
|
# Describe the next method.
|
166
166
|
#
|
@@ -177,8 +177,8 @@ module Apipie
|
|
177
177
|
end
|
178
178
|
_apipie_dsl_data[:description] = description
|
179
179
|
end
|
180
|
-
alias
|
181
|
-
alias
|
180
|
+
alias description desc
|
181
|
+
alias full_description desc
|
182
182
|
|
183
183
|
# describe next method with document in given path
|
184
184
|
# in convension, these doc located under "#{Rails.root}/doc"
|
@@ -246,14 +246,14 @@ module Apipie
|
|
246
246
|
if Apipie.configuration.validate_presence?
|
247
247
|
method_params.each do |_, param|
|
248
248
|
# check if required parameters are present
|
249
|
-
raise ParamMissing.new(param) if param.required && !params.
|
249
|
+
raise ParamMissing.new(param) if param.required && !params.key?(param.name)
|
250
250
|
end
|
251
251
|
end
|
252
252
|
|
253
253
|
if Apipie.configuration.validate_value?
|
254
254
|
method_params.each do |_, param|
|
255
255
|
# params validations
|
256
|
-
param.validate(params[:"#{param.name}"]) if params.
|
256
|
+
param.validate(params[:"#{param.name}"]) if params.key?(param.name)
|
257
257
|
end
|
258
258
|
end
|
259
259
|
|
@@ -272,7 +272,7 @@ module Apipie
|
|
272
272
|
@api_params ||= {}
|
273
273
|
method_params.each do |_, param|
|
274
274
|
# params processing
|
275
|
-
@api_params[param.as] = param.process_value(params[:"#{param.name}"]) if params.
|
275
|
+
@api_params[param.as] = param.process_value(params[:"#{param.name}"]) if params.key?(param.name)
|
276
276
|
end
|
277
277
|
end
|
278
278
|
end
|
@@ -293,9 +293,10 @@ module Apipie
|
|
293
293
|
end
|
294
294
|
|
295
295
|
def _apipie_handle_validate_key_error params, param
|
296
|
-
|
296
|
+
case Apipie.configuration.action_on_non_validated_keys
|
297
|
+
when :raise
|
297
298
|
raise UnknownParam, param
|
298
|
-
|
299
|
+
when :skip
|
299
300
|
params.delete(param)
|
300
301
|
Rails.logger.warn(UnknownParam.new(param).to_s)
|
301
302
|
end
|
@@ -525,7 +526,7 @@ module Apipie
|
|
525
526
|
end
|
526
527
|
end
|
527
528
|
# backwards compatibility
|
528
|
-
|
529
|
+
alias apipie_update_params apipie_update_methods
|
529
530
|
|
530
531
|
def _apipie_concern_subst
|
531
532
|
@_apipie_concern_subst ||= {:controller_path => self.controller_path,
|
@@ -103,7 +103,7 @@ module Apipie
|
|
103
103
|
call = call.stringify_keys
|
104
104
|
ordered_call = OrderedHash.new
|
105
105
|
%w[title verb path versions query request_data response_data code show_in_doc recorded].each do |k|
|
106
|
-
next unless call.
|
106
|
+
next unless call.key?(k)
|
107
107
|
ordered_call[k] = case call[k]
|
108
108
|
when ActiveSupport::HashWithIndifferentAccess
|
109
109
|
convert_file_value(call[k]).to_hash
|
@@ -116,9 +116,10 @@ module Apipie
|
|
116
116
|
|
117
117
|
def convert_file_value hash
|
118
118
|
hash.each do |k, v|
|
119
|
-
|
119
|
+
case v
|
120
|
+
when Rack::Test::UploadedFile, ActionDispatch::Http::UploadedFile
|
120
121
|
hash[k] = "<FILE CONTENT '#{v.original_filename}'>"
|
121
|
-
|
122
|
+
when Hash
|
122
123
|
hash[k] = convert_file_value(v)
|
123
124
|
end
|
124
125
|
end
|
@@ -134,8 +135,8 @@ module Apipie
|
|
134
135
|
old_examples = self.load_recorded_examples
|
135
136
|
merged_examples = []
|
136
137
|
(new_examples.keys + old_examples.keys).uniq.each do |key|
|
137
|
-
if new_examples.
|
138
|
-
if old_examples.
|
138
|
+
if new_examples.key?(key)
|
139
|
+
if old_examples.key?(key)
|
139
140
|
records = deep_merge_examples(new_examples[key], old_examples[key])
|
140
141
|
else
|
141
142
|
records = new_examples[key]
|
@@ -407,12 +408,11 @@ module Apipie
|
|
407
408
|
if line =~ /\s*\b(module|class|def)\b /
|
408
409
|
break
|
409
410
|
end
|
410
|
-
|
411
|
-
|
412
|
-
|
413
|
-
|
414
|
-
|
415
|
-
end
|
411
|
+
next unless line =~ /do\s*(\|.*?\|)?\s*$/
|
412
|
+
block_level -= 1
|
413
|
+
if block_level == 0
|
414
|
+
added_lines.concat(lines_to_add)
|
415
|
+
lines_to_add = []
|
416
416
|
end
|
417
417
|
end
|
418
418
|
return added_lines.reverse.join
|
@@ -0,0 +1,27 @@
|
|
1
|
+
class Apipie::Generator::Swagger::Context
|
2
|
+
attr_reader :default_in_value, :language, :http_method, :controller_method
|
3
|
+
|
4
|
+
def initialize(
|
5
|
+
allow_null:,
|
6
|
+
http_method:,
|
7
|
+
controller_method:,
|
8
|
+
default_in_value: nil,
|
9
|
+
language: nil,
|
10
|
+
in_schema: true
|
11
|
+
)
|
12
|
+
@default_in_value = default_in_value
|
13
|
+
@allow_null = allow_null
|
14
|
+
@language = language
|
15
|
+
@in_schema = in_schema
|
16
|
+
@http_method = http_method
|
17
|
+
@controller_method = controller_method
|
18
|
+
end
|
19
|
+
|
20
|
+
def allow_null?
|
21
|
+
@allow_null == true
|
22
|
+
end
|
23
|
+
|
24
|
+
def in_schema?
|
25
|
+
@in_schema == true
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,51 @@
|
|
1
|
+
class Apipie::Generator::Swagger::OperationId
|
2
|
+
def initialize(path:, http_method:, param: nil)
|
3
|
+
@path = path
|
4
|
+
@http_method = http_method
|
5
|
+
@param = param
|
6
|
+
end
|
7
|
+
|
8
|
+
# @return [String]
|
9
|
+
def to_s
|
10
|
+
base = normalized_http_method + path
|
11
|
+
|
12
|
+
if @param.present?
|
13
|
+
"#{base}_param_#{@param}"
|
14
|
+
else
|
15
|
+
base
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
# @param [Apipie::MethodDescription::Api, Apipie::MethodDescription] describable
|
20
|
+
# @param [String, Symbol, nil] param
|
21
|
+
#
|
22
|
+
# @return [Apipie::Generator::Swagger::OperationId]
|
23
|
+
def self.from(describable, param: nil)
|
24
|
+
path, http_method =
|
25
|
+
if describable.is_a?(Apipie::MethodDescription::Api)
|
26
|
+
[describable.path, describable.http_method]
|
27
|
+
elsif describable.is_a?(Apipie::MethodDescription)
|
28
|
+
[describable.apis.first.path, describable.apis.first.http_method]
|
29
|
+
end
|
30
|
+
|
31
|
+
new(path: path, http_method: http_method, param: param)
|
32
|
+
end
|
33
|
+
|
34
|
+
private
|
35
|
+
|
36
|
+
# Converts an http path for example `/api/concerns/:id` to `_api_concerns_id`
|
37
|
+
#
|
38
|
+
# @return [String]
|
39
|
+
def path
|
40
|
+
@path.gsub(/\//, '_').gsub(/:(\w+)/, '\1').gsub(/_$/, '')
|
41
|
+
end
|
42
|
+
|
43
|
+
# Converts an http method like `GET` to `get` Using lowercase http method,
|
44
|
+
# because the 'swagger-codegen' tool outputs strange method names if the
|
45
|
+
# http method is in uppercase
|
46
|
+
#
|
47
|
+
# @return [String]
|
48
|
+
def normalized_http_method
|
49
|
+
@http_method.to_s.downcase
|
50
|
+
end
|
51
|
+
end
|
@@ -0,0 +1,105 @@
|
|
1
|
+
class Apipie::Generator::Swagger::ParamDescription::Builder
|
2
|
+
# @param [Apipie::ParamDescription] param_description
|
3
|
+
# @param [TrueClass, FalseClass] in_schema
|
4
|
+
# @param [String] controller_method
|
5
|
+
def initialize(param_description, in_schema:, controller_method:)
|
6
|
+
@param_description = param_description
|
7
|
+
@in_schema = in_schema
|
8
|
+
@controller_method = controller_method
|
9
|
+
end
|
10
|
+
|
11
|
+
# @param [String, nil] prefix
|
12
|
+
def with_name(prefix: nil)
|
13
|
+
@name = Apipie::Generator::Swagger::ParamDescription::Name.
|
14
|
+
new(@param_description, prefixed_by: prefix)
|
15
|
+
|
16
|
+
self
|
17
|
+
end
|
18
|
+
|
19
|
+
# @param [String] language
|
20
|
+
def with_description(language:)
|
21
|
+
@description = Apipie::Generator::Swagger::ParamDescription::Description.
|
22
|
+
new(@param_description, language: language)
|
23
|
+
|
24
|
+
self
|
25
|
+
end
|
26
|
+
|
27
|
+
# @param [TrueClass, FalseClass] with_null
|
28
|
+
def with_type(with_null:)
|
29
|
+
@type = Apipie::Generator::Swagger::ParamDescription::Type.
|
30
|
+
new(@param_description, with_null: with_null, controller_method: @controller_method)
|
31
|
+
|
32
|
+
self
|
33
|
+
end
|
34
|
+
|
35
|
+
def with_in(http_method:, default_in_value: nil)
|
36
|
+
@in = Apipie::Generator::Swagger::ParamDescription::In.new(
|
37
|
+
@param_description,
|
38
|
+
in_schema: @in_schema,
|
39
|
+
default_in_value: default_in_value,
|
40
|
+
http_method: http_method
|
41
|
+
)
|
42
|
+
|
43
|
+
self
|
44
|
+
end
|
45
|
+
|
46
|
+
# @return [Hash]
|
47
|
+
def to_swagger
|
48
|
+
definition = {}
|
49
|
+
|
50
|
+
definition.merge!(@name.to_hash) if @name.present?
|
51
|
+
definition.merge!(@type.to_hash) if @type.present?
|
52
|
+
definition.merge!(@in.to_hash) if @in.present?
|
53
|
+
|
54
|
+
definition.merge!(for_default)
|
55
|
+
definition.merge!(for_required)
|
56
|
+
definition.merge!(@description.to_hash) if @description.present?
|
57
|
+
|
58
|
+
warn_optional_without_default_value(definition)
|
59
|
+
|
60
|
+
definition
|
61
|
+
end
|
62
|
+
|
63
|
+
private
|
64
|
+
|
65
|
+
def for_required
|
66
|
+
return {} if !required?
|
67
|
+
|
68
|
+
{
|
69
|
+
required: true
|
70
|
+
}
|
71
|
+
end
|
72
|
+
|
73
|
+
def for_default
|
74
|
+
return {} if @param_description.options[:default_value].blank?
|
75
|
+
|
76
|
+
{
|
77
|
+
default: @param_description.options[:default_value],
|
78
|
+
}
|
79
|
+
end
|
80
|
+
|
81
|
+
def required?
|
82
|
+
required_from_path? || (!@in_schema && @param_description.required)
|
83
|
+
end
|
84
|
+
|
85
|
+
def required_from_path?
|
86
|
+
@param_description.options[:added_from_path] == true
|
87
|
+
end
|
88
|
+
|
89
|
+
def warn_optional_without_default_value(definition)
|
90
|
+
if !required? && !definition.key?(:default)
|
91
|
+
method =
|
92
|
+
if @param_description.is_a?(Apipie::ResponseDescriptionAdapter::PropDesc)
|
93
|
+
@controller_method
|
94
|
+
else
|
95
|
+
@param_description.method_description.method
|
96
|
+
end
|
97
|
+
|
98
|
+
Apipie::Generator::Swagger::Warning.for_code(
|
99
|
+
Apipie::Generator::Swagger::Warning::OPTIONAL_WITHOUT_DEFAULT_VALUE_CODE,
|
100
|
+
method,
|
101
|
+
{ parameter: @param_description.name }
|
102
|
+
).warn_through_writer
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
@@ -0,0 +1,111 @@
|
|
1
|
+
class Apipie::Generator::Swagger::ParamDescription::Composite
|
2
|
+
# @param [Array<Apipie::ParamDescription>] param_descriptions
|
3
|
+
# @param [Apipie::Generator::Swagger::Context] context
|
4
|
+
def initialize(param_descriptions, context)
|
5
|
+
@param_descriptions = param_descriptions
|
6
|
+
@context = context
|
7
|
+
@schema = {
|
8
|
+
type: 'object',
|
9
|
+
properties: {}
|
10
|
+
}
|
11
|
+
@required_params = []
|
12
|
+
end
|
13
|
+
|
14
|
+
def to_swagger
|
15
|
+
return if @param_descriptions.blank?
|
16
|
+
|
17
|
+
@param_descriptions.each do |param_description|
|
18
|
+
validate(param_description)
|
19
|
+
|
20
|
+
if param_description.required
|
21
|
+
@required_params.push(param_description.name.to_sym)
|
22
|
+
end
|
23
|
+
|
24
|
+
param_type = Apipie::Generator::Swagger::TypeExtractor.
|
25
|
+
new(param_description.validator).
|
26
|
+
extract
|
27
|
+
|
28
|
+
has_nested_params = param_type == 'object' &&
|
29
|
+
param_description.validator.params_ordered.present?
|
30
|
+
|
31
|
+
if has_nested_params
|
32
|
+
schema = Apipie::Generator::Swagger::ParamDescription::Composite.new(
|
33
|
+
param_description.validator.params_ordered,
|
34
|
+
Apipie::Generator::Swagger::Context.new(
|
35
|
+
allow_null: @context.allow_null?,
|
36
|
+
http_method: @context.http_method,
|
37
|
+
controller_method: @context.controller_method
|
38
|
+
)
|
39
|
+
).to_swagger
|
40
|
+
|
41
|
+
return if schema.blank?
|
42
|
+
|
43
|
+
if param_description.additional_properties
|
44
|
+
schema[:additionalProperties] = true
|
45
|
+
end
|
46
|
+
|
47
|
+
if param_description.is_array?
|
48
|
+
schema = for_array(schema)
|
49
|
+
end
|
50
|
+
|
51
|
+
if @context.allow_null?
|
52
|
+
schema = with_null(schema)
|
53
|
+
end
|
54
|
+
|
55
|
+
if schema.present?
|
56
|
+
@schema[:properties][param_description.name.to_sym] = schema
|
57
|
+
end
|
58
|
+
else
|
59
|
+
param_entry = Apipie::Generator::Swagger::ParamDescription::Builder.
|
60
|
+
new(
|
61
|
+
param_description,
|
62
|
+
in_schema: @context.in_schema?,
|
63
|
+
controller_method: @context.controller_method
|
64
|
+
).
|
65
|
+
with_description(language: @context.language).
|
66
|
+
with_type(with_null: @context.allow_null?).
|
67
|
+
with_in(
|
68
|
+
default_in_value: @context.default_in_value,
|
69
|
+
http_method: @context.http_method
|
70
|
+
).
|
71
|
+
to_swagger
|
72
|
+
|
73
|
+
@schema[:properties][param_description.name.to_sym] = param_entry
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
if !Apipie.configuration.swagger_allow_additional_properties_in_response
|
78
|
+
@schema[:additionalProperties] = false
|
79
|
+
end
|
80
|
+
|
81
|
+
if @required_params.length > 0
|
82
|
+
@schema[:required] = @required_params
|
83
|
+
end
|
84
|
+
|
85
|
+
@schema
|
86
|
+
end
|
87
|
+
|
88
|
+
private
|
89
|
+
|
90
|
+
def for_array(schema)
|
91
|
+
{
|
92
|
+
type: 'array',
|
93
|
+
items: schema
|
94
|
+
}
|
95
|
+
end
|
96
|
+
|
97
|
+
def with_null(schema)
|
98
|
+
# Ideally we would write schema[:type] = ["object", "null"]
|
99
|
+
# but due to a bug in the json-schema gem, we need to use anyOf
|
100
|
+
# see https://github.com/ruby-json-schema/json-schema/issues/404
|
101
|
+
{
|
102
|
+
anyOf: [ schema, { type: 'null' } ]
|
103
|
+
}
|
104
|
+
end
|
105
|
+
|
106
|
+
def validate(param_description)
|
107
|
+
if !param_description.respond_to?(:required)
|
108
|
+
raise "Unexpected param_desc format"
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
class Apipie::Generator::Swagger::ParamDescription::Description
|
2
|
+
def initialize(param_description, language:)
|
3
|
+
@param_description = param_description
|
4
|
+
@language = language
|
5
|
+
end
|
6
|
+
|
7
|
+
# @return [Hash]
|
8
|
+
def to_hash
|
9
|
+
description = @param_description.options[:desc]
|
10
|
+
|
11
|
+
return {} if description.blank?
|
12
|
+
|
13
|
+
{ description: Apipie.app.translate(description, @language) }
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
class Apipie::Generator::Swagger::ParamDescription::In
|
2
|
+
IN_KEYWORD_DEFAULT_VALUES = {
|
3
|
+
form_data: 'formData',
|
4
|
+
query: 'query'
|
5
|
+
}
|
6
|
+
|
7
|
+
def initialize(param_description, in_schema:, default_in_value:, http_method:)
|
8
|
+
@param_description = param_description
|
9
|
+
@in_schema = in_schema
|
10
|
+
@default_in_value = default_in_value
|
11
|
+
@http_method = http_method
|
12
|
+
end
|
13
|
+
|
14
|
+
# @return [Hash]
|
15
|
+
def to_hash
|
16
|
+
# The "name" and "in" keys can only be set on root parameters (non-nested)
|
17
|
+
return {} if @in_schema
|
18
|
+
|
19
|
+
{ in: in_value }
|
20
|
+
end
|
21
|
+
|
22
|
+
private
|
23
|
+
|
24
|
+
def in_value
|
25
|
+
return @default_in_value if @default_in_value.present?
|
26
|
+
|
27
|
+
if body_allowed_for_current_method?
|
28
|
+
IN_KEYWORD_DEFAULT_VALUES[:form_data]
|
29
|
+
else
|
30
|
+
IN_KEYWORD_DEFAULT_VALUES[:query]
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def body_allowed_for_current_method?
|
35
|
+
['get', 'head'].exclude?(@http_method)
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
class Apipie::Generator::Swagger::ParamDescription::Name
|
2
|
+
def initialize(param_description, prefixed_by: nil)
|
3
|
+
@param_description = param_description
|
4
|
+
@prefixed_by = prefixed_by
|
5
|
+
end
|
6
|
+
|
7
|
+
# @return [Hash]
|
8
|
+
def to_hash
|
9
|
+
name =
|
10
|
+
if @prefixed_by.present?
|
11
|
+
"#{@prefixed_by}[#{@param_description.name}]"
|
12
|
+
else
|
13
|
+
@param_description.name
|
14
|
+
end
|
15
|
+
|
16
|
+
{ name: name }
|
17
|
+
end
|
18
|
+
end
|