apipie-rails 1.2.0 → 1.2.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 73f474f2a3ff7eda3acca1a76fb6199da314c0ad3c9a1241662bad03d3e762c9
4
- data.tar.gz: 677da6befb97f5eb0c6c761758c0e159cabe8de3d2bf15b2acdb2bc03f3d069f
3
+ metadata.gz: ebba895c2d4385bd3ccc47fe9663ca6e5b06f213308e09c5899e9f8b7ee6b74c
4
+ data.tar.gz: 11f9e1572ae63af8b463b4c42a2d9c0b74f094f4ef523060f6948cc11172e089
5
5
  SHA512:
6
- metadata.gz: 2fc436669c44ca181d6a1fce639762bba9ae7f508d9527c52bbcf1e9846135bc94de36f7148e8b29273cf6f6e389aa6104cf0da7410d18c33856afa0a7f264e2
7
- data.tar.gz: afaedf8cdb2c0d0e326dcc82d896e9dd524cbc91b5c914e44c0b62272076f4830f8318e14985e59dfdceb81b7d4d5b7865dd27b82ffb687f100943cba0d6ac6b
6
+ metadata.gz: 4fdb149329633f14091638be50d9b1f99c27bcdb4a5e279b042a835c16bc80b54fa750a7fe0fd69b3d0686badd82d93aef88b6b0c172a2ea9706509526f4dd0a
7
+ data.tar.gz: 98d1d2a93f9403b47dea88edec25761986b6bdc0fb0db9ed83737f72eb5ac3b3c3b4b1b1eddab54d6db48366ad0a3006c4e7bf58ce257586730ea9a3add04faf
data/.rubocop.yml CHANGED
@@ -46,7 +46,7 @@ Metrics/ClassLength:
46
46
  - spec/dummy/app/controllers/users_controller.rb
47
47
 
48
48
  Metrics/BlockLength:
49
- Max: 25 # default
49
+ Max: 26 # default
50
50
  Exclude:
51
51
  - app/controllers/apipie/apipies_controller.rb
52
52
  - lib/apipie/generator/swagger/param_description/composite.rb
data/.rubocop_todo.yml CHANGED
@@ -1,6 +1,6 @@
1
1
  # This configuration was generated by
2
2
  # `rubocop --auto-gen-config --exclude-limit 180`
3
- # on 2023-06-02 23:32:14 UTC using RuboCop version 1.52.0.
3
+ # on 2023-06-09 05:29:05 UTC using RuboCop version 1.52.0.
4
4
  # The point is for the user to remove these configuration records
5
5
  # one by one as the offenses are removed from the code base.
6
6
  # Note that changes in the inspected code, or installation of new
@@ -118,7 +118,7 @@ Layout/ElseAlignment:
118
118
  - 'lib/apipie/param_description.rb'
119
119
  - 'lib/apipie/resource_description.rb'
120
120
 
121
- # Offense count: 59
121
+ # Offense count: 58
122
122
  # This cop supports safe autocorrection (--autocorrect).
123
123
  Layout/EmptyLineAfterGuardClause:
124
124
  Exclude:
@@ -783,6 +783,12 @@ Lint/Void:
783
783
  Metrics/AbcSize:
784
784
  Max: 96
785
785
 
786
+ # Offense count: 1
787
+ # Configuration parameters: CountComments, CountAsOne, AllowedMethods, AllowedPatterns, inherit_mode.
788
+ # AllowedMethods: refine
789
+ Metrics/BlockLength:
790
+ Max: 26
791
+
786
792
  # Offense count: 4
787
793
  # Configuration parameters: CountBlocks.
788
794
  Metrics/BlockNesting:
@@ -793,11 +799,16 @@ Metrics/BlockNesting:
793
799
  Metrics/CyclomaticComplexity:
794
800
  Max: 24
795
801
 
796
- # Offense count: 78
802
+ # Offense count: 79
797
803
  # Configuration parameters: CountComments, CountAsOne, AllowedMethods, AllowedPatterns.
798
804
  Metrics/MethodLength:
799
805
  Max: 58
800
806
 
807
+ # Offense count: 1
808
+ # Configuration parameters: CountComments, CountAsOne.
809
+ Metrics/ModuleLength:
810
+ Max: 101
811
+
801
812
  # Offense count: 4
802
813
  # Configuration parameters: CountKeywordArgs.
803
814
  Metrics/ParameterLists:
@@ -1048,7 +1059,7 @@ RSpec/EmptyLineAfterHook:
1048
1059
  RSpec/ExampleLength:
1049
1060
  Max: 85
1050
1061
 
1051
- # Offense count: 158
1062
+ # Offense count: 159
1052
1063
  # This cop supports safe autocorrection (--autocorrect).
1053
1064
  # Configuration parameters: CustomTransform, IgnoredWords, DisallowedExamples.
1054
1065
  # DisallowedExamples: works
@@ -1137,7 +1148,7 @@ RSpec/MessageSpies:
1137
1148
  RSpec/MultipleExpectations:
1138
1149
  Max: 19
1139
1150
 
1140
- # Offense count: 154
1151
+ # Offense count: 156
1141
1152
  # Configuration parameters: AllowSubject.
1142
1153
  RSpec/MultipleMemoizedHelpers:
1143
1154
  Max: 15
@@ -1162,18 +1173,17 @@ RSpec/NamedSubject:
1162
1173
  - 'spec/lib/swagger/rake_swagger_spec.rb'
1163
1174
  - 'spec/lib/swagger/swagger_dsl_spec.rb'
1164
1175
 
1165
- # Offense count: 93
1176
+ # Offense count: 94
1166
1177
  # Configuration parameters: AllowedGroups.
1167
1178
  RSpec/NestedGroups:
1168
1179
  Max: 6
1169
1180
 
1170
- # Offense count: 2
1181
+ # Offense count: 1
1171
1182
  # Configuration parameters: AllowedPatterns.
1172
1183
  # AllowedPatterns: ^expect_, ^assert_
1173
1184
  RSpec/NoExpectationExample:
1174
1185
  Exclude:
1175
1186
  - 'spec/controllers/users_controller_spec.rb'
1176
- - 'spec/test_engine/memes_controller_spec.rb'
1177
1187
 
1178
1188
  # Offense count: 2
1179
1189
  # This cop supports safe autocorrection (--autocorrect).
@@ -1232,6 +1242,7 @@ RSpec/VerifiedDoubles:
1232
1242
  - 'spec/lib/apipie/apipies_controller_spec.rb'
1233
1243
  - 'spec/lib/apipie/extractor/writer_spec.rb'
1234
1244
  - 'spec/lib/validators/array_validator_spec.rb'
1245
+ - 'spec/lib/apipie/extractor/recorder_spec.rb'
1235
1246
 
1236
1247
  # Offense count: 1
1237
1248
  RSpec/VoidExpect:
@@ -1366,7 +1377,7 @@ Style/AndOr:
1366
1377
  Exclude:
1367
1378
  - 'lib/apipie/param_description.rb'
1368
1379
 
1369
- # Offense count: 17
1380
+ # Offense count: 18
1370
1381
  # This cop supports safe autocorrection (--autocorrect).
1371
1382
  # Configuration parameters: EnforcedStyle, ProceduralMethods, FunctionalMethods, AllowedMethods, AllowedPatterns, AllowBracesOnProceduralOneLiners, BracesRequiredMethods.
1372
1383
  # SupportedStyles: line_count_based, semantic, braces_for_chaining, always_braces
@@ -1522,7 +1533,7 @@ Style/EmptyElse:
1522
1533
  - 'lib/apipie/extractor/recorder.rb'
1523
1534
  - 'lib/apipie/extractor/writer.rb'
1524
1535
 
1525
- # Offense count: 26
1536
+ # Offense count: 27
1526
1537
  # This cop supports safe autocorrection (--autocorrect).
1527
1538
  # Configuration parameters: EnforcedStyle.
1528
1539
  # SupportedStyles: compact, expanded
@@ -1765,7 +1776,6 @@ Style/Proc:
1765
1776
  Style/RaiseArgs:
1766
1777
  Exclude:
1767
1778
  - 'lib/apipie/application.rb'
1768
- - 'lib/apipie/dsl_definition.rb'
1769
1779
  - 'lib/apipie/extractor/writer.rb'
1770
1780
  - 'lib/apipie/param_description.rb'
1771
1781
  - 'lib/apipie/see_description.rb'
@@ -1917,7 +1927,7 @@ Style/StringConcatenation:
1917
1927
  - 'lib/apipie/application.rb'
1918
1928
  - 'lib/apipie/extractor/writer.rb'
1919
1929
 
1920
- # Offense count: 1210
1930
+ # Offense count: 1212
1921
1931
  # This cop supports safe autocorrection (--autocorrect).
1922
1932
  # Configuration parameters: EnforcedStyle, ConsistentQuotesInMultiline.
1923
1933
  # SupportedStyles: single_quotes, double_quotes
data/CHANGELOG.md CHANGED
@@ -1,6 +1,20 @@
1
1
  Changelog
2
2
  ===========
3
3
 
4
+ ## [v1.2.2](https://github.com/Apipie/apipie-rails/tree/v1.2.2) (2023-07-18)
5
+ [Full Changelog](https://github.com/Apipie/apipie-rails/compare/v1.2.1...v1.2.2)
6
+ * Fixed Swagger warnings for properties ([#892](https://github.com/Apipie/apipie-rails/pull/892)) (shev-vadim-net)
7
+ * Improved support for multipart/form-data example recording ([#891](https://github.com/Apipie/apipie-rails/pull/891)) (Butiri Cristian & hossenlopp)
8
+ * rubocop (1.54.2) fixes required with latest version ([#893](https://github.com/Apipie/apipie-rails/pull/893)) (Mathieu Jobin)
9
+
10
+ ## [v1.2.1](https://github.com/Apipie/apipie-rails/tree/v1.2.1) (2023-06-09)
11
+ [Full Changelog](https://github.com/Apipie/apipie-rails/compare/v1.2.0...v1.2.1)
12
+ * rspec: Fixes deprecated matcher ([#882](https://github.com/Apipie/apipie-rails/pull/882)) (David Wessman)
13
+ * Fix streaming bug ([#677](https://github.com/Apipie/apipie-rails/pull/677)) (Hunter Braun)
14
+ * Update README URLs based on HTTP redirects ([#448](https://github.com/Apipie/apipie-rails/pull/448)) (ReadmeCritic)
15
+ * Swagger: Adds option to skip default tags ([#881](https://github.com/Apipie/apipie-rails/pull/881)) (David Wessman)
16
+ * Parameter validation: Raises error for all missing ([#886](https://github.com/Apipie/apipie-rails/pull/886)) (David Wessman)
17
+
4
18
  ## [v1.2.0](https://github.com/Apipie/apipie-rails/tree/v1.2.0) (2023-06-03)
5
19
  [Full Changelog](https://github.com/Apipie/apipie-rails/compare/v1.1.0...v1.2.0)
6
20
  * Allow resource_name to be inherited ([#872](https://github.com/Apipie/apipie-rails/pull/872)) (Eric Hankins)
data/README.rst CHANGED
@@ -56,7 +56,7 @@ Run your application and see the result at
56
56
  use ``http://localhost:3000/apipie.json``.
57
57
 
58
58
  For a more comprehensive getting started guide, see
59
- `this demo <https://github.com/iNecas/apipie-demo>`_, which includes
59
+ `this demo <https://github.com/Apipie/apipie-demo>`_, which includes
60
60
  features such as generating documentation from tests, recording examples etc.
61
61
 
62
62
  Screenshots
@@ -78,7 +78,7 @@ See `Contributors page <https://github.com/Apipie/apipie-rails/graphs/contribut
78
78
  License
79
79
  -------
80
80
 
81
- Apipie-rails is released under the `MIT License <http://opensource.org/licenses/MIT>`_
81
+ Apipie-rails is released under the `MIT License <https://opensource.org/licenses/MIT>`_
82
82
 
83
83
  ===============
84
84
  Documentation
@@ -1730,6 +1730,9 @@ There are several configuration parameters that determine the structure of the g
1730
1730
  See [https://swagger.io/docs/specification/2-0/authentication/] for details of what values can be specified
1731
1731
  By default, no security is defined.
1732
1732
 
1733
+ ``config.generator.swagger.skip_default_tags``
1734
+ By setting ``false`` (default): The resource name for e.g. ``/pets/{petId}`` will automatically be added as a tag ``pets``.
1735
+ By setting ``true``: The tags needs to be explicitly added to the resource using the DSL.
1733
1736
 
1734
1737
  Known limitations of the current implementation
1735
1738
  -------------------------------------------------
@@ -1940,7 +1943,7 @@ Then, you can install dependencies and run the test suite:
1940
1943
  Disqus Integration
1941
1944
  ====================
1942
1945
 
1943
- You can setup `Disqus <http://www.disqus.com>`_ discussion within
1946
+ You can setup `Disqus <https://disqus.com/>`_ discussion within
1944
1947
  your documentation. Just set the credentials in the Apipie
1945
1948
  configuration:
1946
1949
 
@@ -405,12 +405,10 @@ module Apipie
405
405
  version_prefix = version_prefix(klass)
406
406
  path = klass.controller_path
407
407
 
408
- path =
409
- if version_prefix == '/'
410
- path
411
- else
408
+ unless version_prefix == '/'
409
+ path =
412
410
  path.gsub(version_prefix, '')
413
- end
411
+ end
414
412
 
415
413
  path.gsub('/', '-')
416
414
  elsif klass.respond_to?(:controller_name)
@@ -241,9 +241,11 @@ module Apipie
241
241
  method_params = self.class._apipie_get_method_params(action_name)
242
242
 
243
243
  if Apipie.configuration.validate_presence?
244
- method_params.each do |_, param|
245
- # check if required parameters are present
246
- raise ParamMissing.new(param) if param.required && !params.key?(param.name)
244
+ Validator::BaseValidator.raise_if_missing_params do |missing|
245
+ method_params.each do |_, param|
246
+ # check if required parameters are present
247
+ missing << param if param.required && !params.key?(param.name)
248
+ end
247
249
  end
248
250
  end
249
251
 
@@ -285,7 +287,6 @@ module Apipie
285
287
  old_method.bind(self).call(*args)
286
288
  end
287
289
  end
288
-
289
290
  end
290
291
  end
291
292
 
data/lib/apipie/errors.rb CHANGED
@@ -24,6 +24,20 @@ module Apipie
24
24
  end
25
25
  end
26
26
 
27
+ class ParamMultipleMissing < ParamError
28
+ attr_accessor :params
29
+
30
+ def initialize(params)
31
+ @params = params
32
+ end
33
+
34
+ def to_s
35
+ params.map do |param|
36
+ ParamMissing.new(param).to_s
37
+ end.join("\n")
38
+ end
39
+ end
40
+
27
41
  class ParamMissing < DefinedParamError
28
42
  def to_s
29
43
  unless @param.options[:missing_message].nil?
@@ -24,10 +24,10 @@ module Apipie
24
24
  end
25
25
 
26
26
  def handle_record(record)
27
- add_to_records(record)
28
27
  if ignore_call?(record)
29
28
  Extractor.logger.info("REST_API: skipping #{record_to_s(record)}")
30
29
  else
30
+ add_to_records(record)
31
31
  refine_description(record)
32
32
  end
33
33
  end
@@ -114,4 +114,3 @@ module Apipie
114
114
  end
115
115
  end
116
116
  end
117
-
@@ -44,7 +44,7 @@ module Apipie
44
44
  @path = request.path
45
45
  @params = request.request_parameters
46
46
  if [:POST, :PUT, :PATCH, :DELETE].include?(@verb)
47
- @request_data = @params
47
+ @request_data = request.content_type == "multipart/form-data" ? reformat_multipart_data(@params) : @params
48
48
  else
49
49
  @query = request.query_string
50
50
  end
@@ -66,8 +66,14 @@ module Apipie
66
66
  lines = ["Content-Type: multipart/form-data; boundary=#{MULTIPART_BOUNDARY}",'']
67
67
  boundary = "--#{MULTIPART_BOUNDARY}"
68
68
  form.each do |key, attrs|
69
- if attrs.is_a?(String)
69
+ if attrs.is_a?(String) # rubocop:disable Style/CaseLikeIf
70
70
  lines << boundary << content_disposition(key) << "Content-Length: #{attrs.size}" << '' << attrs
71
+ elsif attrs.is_a?(Rack::Test::UploadedFile) || attrs.is_a?(ActionDispatch::Http::UploadedFile)
72
+ reformat_uploaded_file(boundary, attrs, key, lines)
73
+ elsif attrs.is_a?(Array)
74
+ reformat_array(boundary, attrs, key, lines)
75
+ elsif attrs.is_a?(TrueClass) || attrs.is_a?(FalseClass)
76
+ reformat_boolean(boundary, attrs, key, lines)
71
77
  else
72
78
  reformat_hash(boundary, attrs, lines)
73
79
  end
@@ -88,6 +94,24 @@ module Apipie
88
94
  end
89
95
  end
90
96
 
97
+ def reformat_boolean(boundary, attrs, key, lines)
98
+ lines << boundary << content_disposition(key)
99
+ lines << '' << attrs.to_s
100
+ end
101
+
102
+ def reformat_array(boundary, attrs, key, lines)
103
+ attrs.each do |item|
104
+ lines << boundary << content_disposition("#{key}[]")
105
+ lines << '' << item
106
+ end
107
+ end
108
+
109
+ def reformat_uploaded_file(boundary, file, key, lines)
110
+ lines << boundary << %{#{content_disposition(key)}; filename="#{file.original_filename}"}
111
+ lines << "Content-Length: #{file.size}" << "Content-Type: #{file.content_type}" << "Content-Transfer-Encoding: binary"
112
+ lines << '' << %{... contents of "#{key}" ...}
113
+ end
114
+
91
115
  def content_disposition(name)
92
116
  %{Content-Disposition: form-data; name="#{name}"}
93
117
  end
@@ -15,10 +15,13 @@ class Apipie::Railtie
15
15
  end
16
16
  end
17
17
  end
18
- app.middleware.use ::Apipie::Extractor::Recorder::Middleware
19
18
 
20
- ActionController::TestCase.send(:prepend, Apipie::Extractor::Recorder::FunctionalTestRecording)
21
- ActionController::TestCase::Behavior.send(:prepend, Apipie::Extractor::Recorder::FunctionalTestRecording)
19
+ if Apipie.configuration.record
20
+ app.middleware.use ::Apipie::Extractor::Recorder::Middleware
21
+
22
+ ActionController::TestCase.send(:prepend, Apipie::Extractor::Recorder::FunctionalTestRecording)
23
+ ActionController::TestCase::Behavior.send(:prepend, Apipie::Extractor::Recorder::FunctionalTestRecording)
24
+ end
22
25
  end
23
26
  end
24
27
 
@@ -10,7 +10,7 @@ module Apipie
10
10
  :json_input_uses_refs, :suppress_warnings, :api_host,
11
11
  :generate_x_computed_id_field, :allow_additional_properties_in_response,
12
12
  :responses_use_refs, :schemes, :security_definitions,
13
- :global_security].freeze
13
+ :global_security, :skip_default_tags].freeze
14
14
 
15
15
  attr_accessor(*CONFIG_ATTRIBUTES)
16
16
 
@@ -43,6 +43,7 @@ module Apipie
43
43
  alias include_warning_tags? include_warning_tags
44
44
  alias json_input_uses_refs? json_input_uses_refs
45
45
  alias responses_use_refs? responses_use_refs
46
+ alias skip_default_tags? skip_default_tags
46
47
  alias generate_x_computed_id_field? generate_x_computed_id_field
47
48
  alias swagger_include_warning_tags? swagger_include_warning_tags
48
49
  alias swagger_json_input_uses_refs? swagger_json_input_uses_refs
@@ -61,6 +62,7 @@ module Apipie
61
62
  @schemes = [:https]
62
63
  @security_definitions = {}
63
64
  @global_security = []
65
+ @skip_default_tags = false
64
66
  end
65
67
 
66
68
  def self.deprecated_methods
@@ -47,9 +47,12 @@ class Apipie::Generator::Swagger::MethodDescription::ApiSchemaService
47
47
  end
48
48
 
49
49
  def tags
50
- [@method_description.resource._id] +
51
- warning_tags +
52
- @method_description.tag_list.tags
50
+ tags = if Apipie.configuration.generator.swagger.skip_default_tags?
51
+ []
52
+ else
53
+ [@method_description.resource._id]
54
+ end
55
+ tags + warning_tags + @method_description.tag_list.tags
53
56
  end
54
57
 
55
58
  def warning_tags
@@ -79,7 +79,7 @@ class Apipie::Generator::Swagger::ParamDescription::Builder
79
79
  end
80
80
 
81
81
  def required?
82
- required_from_path? || (!@in_schema && @param_description.required)
82
+ required_from_path? || @param_description.required
83
83
  end
84
84
 
85
85
  def required_from_path?
@@ -11,7 +11,7 @@ module Apipie
11
11
  # Replace all null bytes
12
12
  path = ::Rack::Utils.unescape(path || '')
13
13
  .encode(Encoding::UTF_8, invalid: :replace, replace: '')
14
- .gsub(/\x0/, '')
14
+ .gsub("\x0", '')
15
15
 
16
16
  full_path = path.empty? ? @root : File.join(@root, path)
17
17
  paths = "#{full_path}#{ext}"
@@ -38,6 +38,16 @@ module Apipie
38
38
  return nil
39
39
  end
40
40
 
41
+ def self.raise_if_missing_params
42
+ missing_params = []
43
+ yield missing_params
44
+ if missing_params.size > 1
45
+ raise ParamMultipleMissing.new(missing_params)
46
+ elsif missing_params.size == 1
47
+ raise ParamMissing.new(missing_params.first)
48
+ end
49
+ end
50
+
41
51
  # check if value is valid
42
52
  def valid?(value)
43
53
  if self.validate(value)
@@ -345,14 +355,18 @@ module Apipie
345
355
 
346
356
  def validate(value)
347
357
  return false if !value.is_a? Hash
348
- @hash_params&.each do |k, p|
349
- if Apipie.configuration.validate_presence?
350
- raise ParamMissing.new(p) if p.required && !value.key?(k)
351
- end
352
- if Apipie.configuration.validate_value?
353
- p.validate(value[k]) if value.key?(k)
358
+
359
+ BaseValidator.raise_if_missing_params do |missing|
360
+ @hash_params&.each do |k, p|
361
+ if Apipie.configuration.validate_presence?
362
+ missing << p if p.required && !value.key?(k)
363
+ end
364
+ if Apipie.configuration.validate_value?
365
+ p.validate(value[k]) if value.key?(k)
366
+ end
354
367
  end
355
368
  end
369
+
356
370
  return true
357
371
  end
358
372
 
@@ -1,3 +1,3 @@
1
1
  module Apipie
2
- VERSION = "1.2.0"
2
+ VERSION = "1.2.2"
3
3
  end
@@ -37,6 +37,7 @@ describe UsersController do
37
37
  expect(methods.keys).to include(:update)
38
38
  expect(methods.keys).to include(:two_urls)
39
39
  expect(methods.keys).to include(:action_with_headers)
40
+ expect(methods.keys).to include(:multiple_required_params)
40
41
  end
41
42
 
42
43
  it "should contain info about resource" do
@@ -101,6 +102,10 @@ describe UsersController do
101
102
  expect { get :show, :params => { :id => 5 }}.to raise_error(Apipie::ParamMissing, /session_parameter_is_required/)
102
103
  end
103
104
 
105
+ it "should fail if multiple required parameters are missing" do
106
+ expect { get :multiple_required_params }.to raise_error(Apipie::ParamMultipleMissing, /required_param1.*\n.*required_param2|required_param2.*\n.*required_parameter1/)
107
+ end
108
+
104
109
  it "should pass if required parameter has wrong type" do
105
110
  expect { get :show, :params => { :id => 5 , :session => "secret_hash" }}.not_to raise_error
106
111
  expect { get :show, :params => { :id => "ten" , :session => "secret_hash" }}.not_to raise_error
@@ -246,6 +251,11 @@ describe UsersController do
246
251
  post :create, :params => { :user => { :name => "root", :pass => "12345", :membership => "____" } }
247
252
  }.to raise_error(Apipie::ParamInvalid, /membership/)
248
253
 
254
+ # Should include both pass and name
255
+ expect {
256
+ post :create, :params => { :user => { :membership => "standard" } }
257
+ }.to raise_error(Apipie::ParamMultipleMissing, /pass.*\n.*name|name.*\n.*pass/)
258
+
249
259
  expect {
250
260
  post :create, :params => { :user => { :name => "root" } }
251
261
  }.to raise_error(Apipie::ParamMissing, /pass/)
@@ -301,4 +301,10 @@ class UsersController < ApplicationController
301
301
  header :HeaderNameWithDefaultValue, 'Header with default value', required: true, default: 'default value'
302
302
  def action_with_headers
303
303
  end
304
+
305
+ api :GET, '/users/multiple_required_params'
306
+ param :required_param1, String, required: true
307
+ param :required_param2, String, required: true
308
+ def multiple_required_params
309
+ end
304
310
  end
@@ -8,6 +8,7 @@ Dummy::Application.routes.draw do
8
8
  resources :users do
9
9
  collection do
10
10
  post :create_route
11
+ get :multiple_required_params
11
12
  end
12
13
  end
13
14
  resources :concerns, :only => [:index, :show]
@@ -4,6 +4,11 @@ require 'spec_helper'
4
4
 
5
5
  describe 'Apipie::Extractor::Recorder' do
6
6
  let(:recorder) { Apipie::Extractor::Recorder.new }
7
+ let(:controller) do
8
+ controller = ActionController::Metal.new
9
+ controller.set_request!(request)
10
+ controller
11
+ end
7
12
 
8
13
  describe '#analyse_controller' do
9
14
  subject do
@@ -19,12 +24,6 @@ describe 'Apipie::Extractor::Recorder' do
19
24
  request
20
25
  end
21
26
 
22
- let(:controller) do
23
- controller = ActionController::Metal.new
24
- controller.set_request!(request)
25
- controller
26
- end
27
-
28
27
  it { is_expected.to eq(action) }
29
28
 
30
29
  context 'when a api_action_matcher is configured' do
@@ -37,4 +36,42 @@ describe 'Apipie::Extractor::Recorder' do
37
36
  it { is_expected.to eq(matcher_action) }
38
37
  end
39
38
  end
39
+
40
+ describe '#analyse_functional_test' do
41
+ context 'with multipart-form data' do
42
+ subject do
43
+ recorder.analyse_controller(controller)
44
+ recorder.analyze_functional_test(test_context)
45
+ recorder.record[:request_data]
46
+ end
47
+
48
+ let(:test_context) do
49
+ double(controller: controller, request: request, response: ActionDispatch::Response.new(200))
50
+ end
51
+
52
+ let(:file) do
53
+ instance_double(
54
+ ActionDispatch::Http::UploadedFile,
55
+ original_filename: 'file.txt',
56
+ content_type: 'text/plain',
57
+ size: '1MB'
58
+ )
59
+ end
60
+
61
+ let(:request) do
62
+ request = ActionDispatch::Request.new({})
63
+ request.request_method = 'POST'
64
+ request.headers['Content-Type'] = 'multipart/form-data'
65
+ request.request_parameters = { file: file }
66
+ request
67
+ end
68
+
69
+ before do
70
+ allow(file).to receive(:is_a?).and_return(false)
71
+ allow(file).to receive(:is_a?).with(ActionDispatch::Http::UploadedFile).and_return(true)
72
+ end
73
+
74
+ it { is_expected.to include("filename=\"#{file.original_filename}\"") }
75
+ end
76
+ end
40
77
  end
@@ -64,6 +64,19 @@ describe Apipie::Generator::Swagger::MethodDescription::ApiSchemaService do
64
64
  it { is_expected.to include(*tags) }
65
65
  end
66
66
 
67
+ context 'when Apipie.configuration.generator.swagger.skip_default_tags is enabled' do
68
+ before { Apipie.configuration.generator.swagger.skip_default_tags = true }
69
+ after { Apipie.configuration.generator.swagger.skip_default_tags = false }
70
+
71
+ it { is_expected.to be_empty }
72
+
73
+ context 'when tags are available' do
74
+ let(:tags) { ['Tag 1', 'Tag 2'] }
75
+
76
+ it { is_expected.to eq(tags) }
77
+ end
78
+ end
79
+
67
80
  context 'when Apipie.configuration.generator.swagger.include_warning_tags is enabled' do
68
81
  before { Apipie.configuration.generator.swagger.include_warning_tags = true }
69
82
 
@@ -56,7 +56,7 @@ describe Apipie::Generator::Swagger::MethodDescription::ResponseSchemaService do
56
56
  expect(properties).to eq(
57
57
  {
58
58
  a_number: {
59
- type: 'number'
59
+ type: 'number', required: true
60
60
  },
61
61
  an_optional_number: {
62
62
  type: 'number'
@@ -72,7 +72,7 @@ describe Apipie::Generator::Swagger::MethodDescription::ResponseSchemaService do
72
72
  expect(properties).to eq(
73
73
  {
74
74
  a_number: {
75
- type: %w[number null]
75
+ type: %w[number null], required: true
76
76
  },
77
77
  an_optional_number: {
78
78
  type: %w[number null]
@@ -78,6 +78,12 @@ describe Apipie::Generator::Swagger::ParamDescription::Builder do
78
78
 
79
79
  it { is_expected.to be_blank }
80
80
 
81
+ context 'when is required' do
82
+ let(:base_param_description_options) { { required: true } }
83
+
84
+ it { is_expected.to eq(true) }
85
+ end
86
+
81
87
  context 'when in_schema is false' do
82
88
  let(:in_schema) { false }
83
89
 
@@ -107,6 +113,14 @@ describe Apipie::Generator::Swagger::ParamDescription::Builder do
107
113
  end
108
114
  end
109
115
  end
116
+
117
+ context 'when is required' do
118
+ let(:base_param_description_options) { { required: true } }
119
+
120
+ it 'does not output an option without default warning' do
121
+ expect { subject }.not_to output(/is optional but default value is not specified/).to_stderr
122
+ end
123
+ end
110
124
  end
111
125
 
112
126
  describe '.with_type' do
@@ -61,7 +61,7 @@ describe Apipie::SwaggerGenerator do
61
61
  expect(properties).to eq(
62
62
  {
63
63
  a_number: {
64
- type: 'number'
64
+ type: 'number', required: true
65
65
  },
66
66
  an_optional_number: {
67
67
  type: 'number'
@@ -996,7 +996,14 @@
996
996
  "$ref": "http://json-schema.org/draft-04/schema#/definitions/positiveIntegerDefault0"
997
997
  },
998
998
  "required": {
999
- "$ref": "http://json-schema.org/draft-04/schema#/definitions/stringArray"
999
+ "anyOf": [
1000
+ {
1001
+ "$ref": "http://json-schema.org/draft-04/schema#/definitions/stringArray"
1002
+ },
1003
+ {
1004
+ "type": "boolean"
1005
+ }
1006
+ ]
1000
1007
  },
1001
1008
  "enum": {
1002
1009
  "$ref": "http://json-schema.org/draft-04/schema#/properties/enum"
@@ -4,7 +4,7 @@ describe TestEngine::MemesController do
4
4
 
5
5
  describe "#index" do
6
6
  it "should have the full mounted path of engine" do
7
- Apipie.routes_for_action(TestEngine::MemesController, :index, {}).first[:path].should eq("/test/memes")
7
+ expect(Apipie.routes_for_action(TestEngine::MemesController, :index, {}).first[:path]).to eq("/test/memes")
8
8
  end
9
9
  end
10
10
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: apipie-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.0
4
+ version: 1.2.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Pavel Pokorny
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2023-06-03 00:00:00.000000000 Z
12
+ date: 2023-07-18 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: actionpack
@@ -472,7 +472,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
472
472
  - !ruby/object:Gem::Version
473
473
  version: '0'
474
474
  requirements: []
475
- rubygems_version: 3.4.11
475
+ rubygems_version: 3.4.14
476
476
  signing_key:
477
477
  specification_version: 4
478
478
  summary: Rails REST API documentation tool