diff --git a/src/Microsoft.OpenApi.Hidi/Microsoft.OpenApi.Hidi.csproj b/src/Microsoft.OpenApi.Hidi/Microsoft.OpenApi.Hidi.csproj index 7d41d9e90..98f250626 100644 --- a/src/Microsoft.OpenApi.Hidi/Microsoft.OpenApi.Hidi.csproj +++ b/src/Microsoft.OpenApi.Hidi/Microsoft.OpenApi.Hidi.csproj @@ -15,7 +15,7 @@ Microsoft.OpenApi.Hidi hidi ./../../artifacts - 1.2.3 + 1.2.4 OpenAPI.NET CLI tool for slicing OpenAPI documents © Microsoft Corporation. All rights reserved. OpenAPI .NET @@ -42,7 +42,7 @@ - + diff --git a/src/Microsoft.OpenApi.Hidi/OpenApiService.cs b/src/Microsoft.OpenApi.Hidi/OpenApiService.cs index 9fdca3f66..4d535ee02 100644 --- a/src/Microsoft.OpenApi.Hidi/OpenApiService.cs +++ b/src/Microsoft.OpenApi.Hidi/OpenApiService.cs @@ -324,27 +324,7 @@ public static async Task ConvertCsdlToOpenApi(Stream csdl, stri var edmModel = CsdlReader.Parse(XElement.Parse(csdlText).CreateReader()); var config = GetConfiguration(settingsFile); - var settings = new OpenApiConvertSettings() - { - AddSingleQuotesForStringParameters = true, - AddEnumDescriptionExtension = true, - DeclarePathParametersOnPathItem = true, - EnableKeyAsSegment = true, - EnableOperationId = true, - ErrorResponsesAsDefault = false, - PrefixEntityTypeNameBeforeKey = true, - TagDepth = 2, - EnablePagination = true, - EnableDiscriminatorValue = true, - EnableDerivedTypesReferencesForRequestBody = false, - EnableDerivedTypesReferencesForResponses = false, - ShowRootPath = false, - ShowLinks = false, - ExpandDerivedTypesNavigationProperties = false, - EnableCount = true, - UseSuccessStatusCodeRange = true, - EnableTypeDisambiguationForDefaultValueOfOdataTypeProperty = true - }; + var settings = new OpenApiConvertSettings(); config.GetSection("OpenApiConvertSettings").Bind(settings); OpenApiDocument document = edmModel.ConvertToOpenApi(settings); diff --git a/src/Microsoft.OpenApi.Readers/Microsoft.OpenApi.Readers.csproj b/src/Microsoft.OpenApi.Readers/Microsoft.OpenApi.Readers.csproj index e095c6c86..f037a02e7 100644 --- a/src/Microsoft.OpenApi.Readers/Microsoft.OpenApi.Readers.csproj +++ b/src/Microsoft.OpenApi.Readers/Microsoft.OpenApi.Readers.csproj @@ -10,7 +10,7 @@ Microsoft Microsoft.OpenApi.Readers Microsoft.OpenApi.Readers - 1.6.2 + 1.6.3 OpenAPI.NET Readers for JSON and YAML documents © Microsoft Corporation. All rights reserved. OpenAPI .NET diff --git a/src/Microsoft.OpenApi.Readers/OpenApiYamlDocumentReader.cs b/src/Microsoft.OpenApi.Readers/OpenApiYamlDocumentReader.cs index e43c64ac2..f6fd2325e 100644 --- a/src/Microsoft.OpenApi.Readers/OpenApiYamlDocumentReader.cs +++ b/src/Microsoft.OpenApi.Readers/OpenApiYamlDocumentReader.cs @@ -166,7 +166,6 @@ private void ResolveReferences(OpenApiDiagnostic diagnostic, OpenApiDocument doc } } - /// /// Reads the stream input and parses the fragment of an OpenAPI description into an Open API Element. /// diff --git a/src/Microsoft.OpenApi.Readers/V3/OpenApiSecuritySchemeDeserializer.cs b/src/Microsoft.OpenApi.Readers/V3/OpenApiSecuritySchemeDeserializer.cs index 0e7b1c39c..dd6ad4751 100644 --- a/src/Microsoft.OpenApi.Readers/V3/OpenApiSecuritySchemeDeserializer.cs +++ b/src/Microsoft.OpenApi.Readers/V3/OpenApiSecuritySchemeDeserializer.cs @@ -76,7 +76,11 @@ internal static partial class OpenApiV3Deserializer public static OpenApiSecurityScheme LoadSecurityScheme(ParseNode node) { var mapNode = node.CheckMapNode("securityScheme"); - + var pointer = mapNode.GetReferencePointer(); + if (pointer != null) + { + return mapNode.GetReferencedObject(ReferenceType.SecurityScheme, pointer); + } var securityScheme = new OpenApiSecurityScheme(); foreach (var property in mapNode) { diff --git a/src/Microsoft.OpenApi/Microsoft.OpenApi.csproj b/src/Microsoft.OpenApi/Microsoft.OpenApi.csproj index 92de7f8a0..43ef3876f 100644 --- a/src/Microsoft.OpenApi/Microsoft.OpenApi.csproj +++ b/src/Microsoft.OpenApi/Microsoft.OpenApi.csproj @@ -11,7 +11,7 @@ Microsoft Microsoft.OpenApi Microsoft.OpenApi - 1.6.2 + 1.6.3 .NET models with JSON and YAML writers for OpenAPI specification © Microsoft Corporation. All rights reserved. OpenAPI .NET diff --git a/src/Microsoft.OpenApi/Services/OpenApiWalker.cs b/src/Microsoft.OpenApi/Services/OpenApiWalker.cs index 8c469261c..3d9e978c9 100644 --- a/src/Microsoft.OpenApi/Services/OpenApiWalker.cs +++ b/src/Microsoft.OpenApi/Services/OpenApiWalker.cs @@ -1,4 +1,4 @@ -// Copyright (c) Microsoft Corporation. All rights reserved. +// Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the MIT license. using System; @@ -116,7 +116,18 @@ internal void Walk(OpenApiComponents components) } } }); - + + Walk(OpenApiConstants.SecuritySchemes, () => + { + if (components.SecuritySchemes != null) + { + foreach (var item in components.SecuritySchemes) + { + Walk(item.Key, () => Walk(item.Value, isComponent: true)); + } + } + }); + Walk(OpenApiConstants.Callbacks, () => { if (components.Callbacks != null) @@ -996,9 +1007,9 @@ internal void Walk(OpenApiSecurityRequirement securityRequirement) /// /// Visits and child objects /// - internal void Walk(OpenApiSecurityScheme securityScheme) + internal void Walk(OpenApiSecurityScheme securityScheme, bool isComponent = false) { - if (securityScheme == null || ProcessAsReference(securityScheme)) + if (securityScheme == null || ProcessAsReference(securityScheme, isComponent)) { return; } diff --git a/test/Microsoft.OpenApi.Readers.Tests/Microsoft.OpenApi.Readers.Tests.csproj b/test/Microsoft.OpenApi.Readers.Tests/Microsoft.OpenApi.Readers.Tests.csproj index 65833564f..aef3d92e0 100644 --- a/test/Microsoft.OpenApi.Readers.Tests/Microsoft.OpenApi.Readers.Tests.csproj +++ b/test/Microsoft.OpenApi.Readers.Tests/Microsoft.OpenApi.Readers.Tests.csproj @@ -137,6 +137,9 @@ Never + + Never + Never diff --git a/test/Microsoft.OpenApi.Readers.Tests/V3Tests/OpenApiDocumentTests.cs b/test/Microsoft.OpenApi.Readers.Tests/V3Tests/OpenApiDocumentTests.cs index 362609291..8a0da3481 100644 --- a/test/Microsoft.OpenApi.Readers.Tests/V3Tests/OpenApiDocumentTests.cs +++ b/test/Microsoft.OpenApi.Readers.Tests/V3Tests/OpenApiDocumentTests.cs @@ -3,6 +3,7 @@ using System; using System.Collections.Generic; +using System.Diagnostics.Contracts; using System.Globalization; using System.IO; using System.Linq; @@ -1334,10 +1335,10 @@ public void DoesNotChangeExternalReferences() { // Arrange using var stream = Resources.GetStream(Path.Combine(SampleFolderPath, "documentWithExternalRefs.yaml")); - + // Act var doc = new OpenApiStreamReader( - new OpenApiReaderSettings { ReferenceResolution = ReferenceResolutionSetting.DoNotResolveReferences}) + new OpenApiReaderSettings { ReferenceResolution = ReferenceResolutionSetting.DoNotResolveReferences }) .Read(stream, out var diagnostic); var externalRef = doc.Components.Schemas["Nested"].Properties["AnyOf"].AnyOf.First().Reference.ReferenceV3; @@ -1347,5 +1348,24 @@ public void DoesNotChangeExternalReferences() Assert.Equal("file:///C:/MySchemas.json#/definitions/ArrayObject", externalRef); Assert.Equal("../foo/schemas.yaml#/components/schemas/Number", externalRef2); } + + [Fact] + public void ParseDocumentWithReferencedSecuritySchemeWorks() + { + // Arrange + using var stream = Resources.GetStream(Path.Combine(SampleFolderPath, "docWithSecuritySchemeReference.yaml")); + + // Act + var doc = new OpenApiStreamReader(new OpenApiReaderSettings + { + ReferenceResolution = ReferenceResolutionSetting.ResolveLocalReferences + }).Read(stream, out var diagnostic); + + var securityScheme = doc.Components.SecuritySchemes["OAuth2"]; + + // Assert + Assert.False(securityScheme.UnresolvedReference); + Assert.NotNull(securityScheme.Flows); + } } } diff --git a/test/Microsoft.OpenApi.Readers.Tests/V3Tests/Samples/OpenApiDocument/docWithSecuritySchemeReference.yaml b/test/Microsoft.OpenApi.Readers.Tests/V3Tests/Samples/OpenApiDocument/docWithSecuritySchemeReference.yaml new file mode 100644 index 000000000..3608635a2 --- /dev/null +++ b/test/Microsoft.OpenApi.Readers.Tests/V3Tests/Samples/OpenApiDocument/docWithSecuritySchemeReference.yaml @@ -0,0 +1,17 @@ +openapi: 3.0.0 +info: + title: Example API + version: 1.0.0 +paths: { } +components: + securitySchemes: + OAuth2: + $ref: '#/components/securitySchemes/RefOAuth2' + RefOAuth2: + type: oauth2 + flows: + implicit: + authorizationUrl: https://example.com/api/oauth/dialog + scopes: + write:pets: modify pets in your account + read:pets: read your pets \ No newline at end of file diff --git a/test/Microsoft.OpenApi.Tests/Microsoft.OpenApi.Tests.csproj b/test/Microsoft.OpenApi.Tests/Microsoft.OpenApi.Tests.csproj index 481a53db8..b153ba204 100644 --- a/test/Microsoft.OpenApi.Tests/Microsoft.OpenApi.Tests.csproj +++ b/test/Microsoft.OpenApi.Tests/Microsoft.OpenApi.Tests.csproj @@ -35,7 +35,7 @@ runtime; build; native; contentfiles; analyzers; buildtransitive - + diff --git a/test/Microsoft.OpenApi.Tests/PublicApi/PublicApiTests.cs b/test/Microsoft.OpenApi.Tests/PublicApi/PublicApiTests.cs index fa413cd32..418a526d0 100755 --- a/test/Microsoft.OpenApi.Tests/PublicApi/PublicApiTests.cs +++ b/test/Microsoft.OpenApi.Tests/PublicApi/PublicApiTests.cs @@ -26,7 +26,7 @@ public void ReviewPublicApiChanges() // It takes a human to read the change, determine if it is breaking and update the PublicApi.approved.txt with the new approved API surface // Arrange - var publicApi = typeof(OpenApiSpecVersion).Assembly.GeneratePublicApi(new ApiGeneratorOptions() { WhitelistedNamespacePrefixes = new[] { "Microsoft.OpenApi" } } ); + var publicApi = typeof(OpenApiSpecVersion).Assembly.GeneratePublicApi(new ApiGeneratorOptions() { AllowNamespacePrefixes = new[] { "Microsoft.OpenApi" } } ); // Act var approvedFilePath = Path.Combine("PublicApi", "PublicApi.approved.txt");