From a25307dc69093e051c36ded544d2b21b53d59016 Mon Sep 17 00:00:00 2001 From: Greg Myers Date: Sat, 21 Mar 2020 22:57:18 +0000 Subject: [PATCH] add support for openapi 3 securitySchemas --- .../lib/rswag/specs/request_factory.rb | 23 ++++++--- .../spec/rswag/specs/example_helpers_spec.rb | 1 + .../spec/rswag/specs/request_factory_spec.rb | 47 +++++++++++++++---- 3 files changed, 57 insertions(+), 14 deletions(-) diff --git a/rswag-specs/lib/rswag/specs/request_factory.rb b/rswag-specs/lib/rswag/specs/request_factory.rb index 23f74a1..00322ca 100644 --- a/rswag-specs/lib/rswag/specs/request_factory.rb +++ b/rswag-specs/lib/rswag/specs/request_factory.rb @@ -41,12 +41,8 @@ module Rswag def derive_security_params(metadata, swagger_doc) requirements = metadata[:operation][:security] || swagger_doc[:security] || [] - scheme_names = requirements.flat_map { |r| r.keys } - ## OA3 - # scheme_names = requirements.flat_map(&:keys) - # components = swagger_doc[:components] || {} - # schemes = (components[:securitySchemes] || {}).slice(*scheme_names).values - schemes = (swagger_doc[:securityDefinitions] || {}).slice(*scheme_names).values + scheme_names = requirements.flat_map(&:keys) + schemes = security_version(scheme_names, swagger_doc) schemes.map do |scheme| param = (scheme[:type] == :apiKey) ? scheme.slice(:name, :in) : { name: 'Authorization', in: :header } @@ -54,6 +50,20 @@ module Rswag end end + def security_version(scheme_names, swagger_doc) + if doc_version(swagger_doc).start_with?('2') + (swagger_doc[:securityDefinitions] || {}).slice(*scheme_names).values + else # Openapi3 + if swagger_doc.has_key?(:securityDefinitions) + ActiveSupport::Deprecation.warn('Rswag::Specs: WARNING: securityDefinitions is replaced in OpenAPI3! Rename to components/securitySchemes (in swagger_helper.rb)') + (swagger_doc[:securityDefinitions] || {}).slice(*scheme_names).values + else + components = swagger_doc[:components] || {} + (components[:securitySchemes] || {}).slice(*scheme_names).values + end + end + end + def resolve_parameter(ref, swagger_doc) key = key_version(ref, swagger_doc) definitions = definition_version(swagger_doc) @@ -80,6 +90,7 @@ module Rswag swagger_doc[:parameters] else # Openapi3 if swagger_doc.has_key?(:parameters) + ActiveSupport::Deprecation.warn('Rswag::Specs: WARNING: parameters is replaced in OpenAPI3! Rename to components/parameters (in swagger_helper.rb)') swagger_doc[:parameters] else components = swagger_doc[:components] || {} diff --git a/rswag-specs/spec/rswag/specs/example_helpers_spec.rb b/rswag-specs/spec/rswag/specs/example_helpers_spec.rb index e633e8e..51cac79 100644 --- a/rswag-specs/spec/rswag/specs/example_helpers_spec.rb +++ b/rswag-specs/spec/rswag/specs/example_helpers_spec.rb @@ -17,6 +17,7 @@ module Rswag let(:config) { double('config') } let(:swagger_doc) do { + swagger: '2.0', securityDefinitions: { api_key: { type: :apiKey, diff --git a/rswag-specs/spec/rswag/specs/request_factory_spec.rb b/rswag-specs/spec/rswag/specs/request_factory_spec.rb index ad96f52..4e97d1c 100644 --- a/rswag-specs/spec/rswag/specs/request_factory_spec.rb +++ b/rswag-specs/spec/rswag/specs/request_factory_spec.rb @@ -204,16 +204,45 @@ module Rswag end context 'basic auth' do - before do - swagger_doc[:securityDefinitions] = { basic: { type: :basic } } - ## OA3 - # swagger_doc[:components] = { securitySchemes: { basic: { type: :basic } } } - metadata[:operation][:security] = [ basic: [] ] - allow(example).to receive(:Authorization).and_return('Basic foobar') + context 'swagger 2.0' do + before do + swagger_doc[:securityDefinitions] = { basic: { type: :basic } } + metadata[:operation][:security] = [ basic: [] ] + allow(example).to receive(:Authorization).and_return('Basic foobar') + end + + it "sets 'HTTP_AUTHORIZATION' header to example value" do + expect(request[:headers]).to eq('HTTP_AUTHORIZATION' => 'Basic foobar') + end end - it "sets 'HTTP_AUTHORIZATION' header to example value" do - expect(request[:headers]).to eq('HTTP_AUTHORIZATION' => 'Basic foobar') + context 'openapi 3.0.1' do + let(:swagger_doc) { { openapi: '3.0.1' } } + before do + swagger_doc[:components] = { securitySchemes: { basic: { type: :basic } } } + metadata[:operation][:security] = [ basic: [] ] + allow(example).to receive(:Authorization).and_return('Basic foobar') + end + + it "sets 'HTTP_AUTHORIZATION' header to example value" do + expect(request[:headers]).to eq('HTTP_AUTHORIZATION' => 'Basic foobar') + end + end + + context 'openapi 3.0.1 upgrade notice' do + let(:swagger_doc) { { openapi: '3.0.1' } } + before do + allow(ActiveSupport::Deprecation).to receive(:warn) + swagger_doc[:securityDefinitions] = { basic: { type: :basic } } + metadata[:operation][:security] = [ basic: [] ] + allow(example).to receive(:Authorization).and_return('Basic foobar') + end + + it 'warns the user to upgrade' do + expect(request[:headers]).to eq('HTTP_AUTHORIZATION' => 'Basic foobar') + expect(ActiveSupport::Deprecation).to have_received(:warn) + .with('Rswag::Specs: WARNING: securityDefinitions is replaced in OpenAPI3! Rename to components/securitySchemes (in swagger_helper.rb)') + end end end @@ -352,6 +381,8 @@ module Rswag expect(request[:path]).to eq('/blogs?q1=foo') expect(ActiveSupport::Deprecation).to have_received(:warn) .with('Rswag::Specs: WARNING: #/parameters/ refs are replaced in OpenAPI3! Rename to #/components/parameters/') + expect(ActiveSupport::Deprecation).to have_received(:warn) + .with('Rswag::Specs: WARNING: parameters is replaced in OpenAPI3! Rename to components/parameters (in swagger_helper.rb)') end end end