diff --git a/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj b/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj index f35693c8..d8b32420 100644 --- a/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj +++ b/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj @@ -15,13 +15,13 @@ netstandard2.0 Microsoft.OpenApi.OData true - 1.7.1 + 1.7.2 This package contains the codes you need to convert OData CSDL to Open API Document of Model. © Microsoft Corporation. All rights reserved. Microsoft OpenApi OData EDM https://github.com/Microsoft/OpenAPI.NET.OData - - Further fix for generating unique operation ids for navigation property paths with composable overloaded functions #596 + - Adds action/function suffix to tag names for actions/functions operations in #642 Microsoft.OpenApi.OData.Reader ..\..\tool\Microsoft.OpenApi.OData.snk @@ -66,4 +66,4 @@ - + \ No newline at end of file diff --git a/src/Microsoft.OpenApi.OData.Reader/Operation/EdmOperationOperationHandler.cs b/src/Microsoft.OpenApi.OData.Reader/Operation/EdmOperationOperationHandler.cs index d5e1f555..a9b5ebac 100644 --- a/src/Microsoft.OpenApi.OData.Reader/Operation/EdmOperationOperationHandler.cs +++ b/src/Microsoft.OpenApi.OData.Reader/Operation/EdmOperationOperationHandler.cs @@ -81,12 +81,11 @@ protected override void SetBasicInfo(OpenApiOperation operation) // duplicates in entity vs entityset functions/actions List identifiers = new(); - string pathHash = string.Empty; foreach (ODataSegment segment in Path.Segments) { if (segment is ODataKeySegment keySegment) { - if (!keySegment.IsAlternateKey) + if (!keySegment.IsAlternateKey) { identifiers.Add(segment.EntityType.Name); continue; @@ -102,18 +101,6 @@ protected override void SetBasicInfo(OpenApiOperation operation) identifiers.Add(keySegment.Identifier); } } - else if (segment is ODataOperationSegment opSegment) - { - if (opSegment.Operation is IEdmFunction function && Context.Model.IsOperationOverload(function)) - { - // Hash the segment to avoid duplicate operationIds - pathHash = string.IsNullOrEmpty(pathHash) - ? opSegment.GetPathHash(Context.Settings) - : (pathHash + opSegment.GetPathHash(Context.Settings)).GetHashSHA256().Substring(0, 4); - } - - identifiers.Add(segment.Identifier); - } else { identifiers.Add(segment.Identifier); @@ -122,13 +109,21 @@ protected override void SetBasicInfo(OpenApiOperation operation) string operationId = string.Join(".", identifiers); - if (!string.IsNullOrEmpty(pathHash)) + if (EdmOperation.IsAction()) { - operation.OperationId = operationId + "-" + pathHash; + operation.OperationId = operationId; } else { - operation.OperationId = operationId; + if (Path.LastSegment is ODataOperationSegment operationSegment && + Context.Model.IsOperationOverload(operationSegment.Operation)) + { + operation.OperationId = operationId + "-" + Path.LastSegment.GetPathHash(Context.Settings); + } + else + { + operation.OperationId = operationId; + } } } @@ -152,12 +147,12 @@ protected override void SetTags(OpenApiOperation operation) } /// - /// Genrates the tag name for the operation. + /// Genrates the tag name for the operation. Adds Action or Function name to the tag name if the operation is an action or function. /// /// The generated tag name. /// The number of segments to skip. private void GenerateTagName(out string tagName, int skip = 1) - { + { var targetSegment = Path.Segments.Reverse().Skip(skip).FirstOrDefault(); switch (targetSegment) @@ -165,16 +160,23 @@ private void GenerateTagName(out string tagName, int skip = 1) case ODataNavigationPropertySegment: tagName = EdmModelHelper.GenerateNavigationPropertyPathTagName(Path, Context); break; - case ODataOperationSegment: case ODataOperationImportSegment: // Previous segmment could be a navigation property or a navigation source segment case ODataKeySegment: skip += 1; GenerateTagName(out tagName, skip); break; - // ODataNavigationSourceSegment default: tagName = NavigationSource.Name + "." + NavigationSource.EntityType().Name; + if (EdmOperation.IsAction()) + { + tagName += ".Actions"; + } + else if (EdmOperation.IsFunction()) + { + tagName += ".Functions"; + } + break; } } @@ -192,7 +194,7 @@ protected override void SetParameters(OpenApiOperation operation) } /// - protected override void SetResponses(OpenApiOperation operation) + protected override void SetResponses(OpenApiOperation operation) { operation.Responses = Context.CreateResponses(EdmOperation); base.SetResponses(operation); @@ -292,10 +294,10 @@ protected override void SetCustomLinkRelType() { LinkRelKey key = EdmOperation.IsAction() ? LinkRelKey.Action : LinkRelKey.Function; Context.Settings.CustomHttpMethodLinkRelMapping.TryGetValue(key, out string linkRelValue); - CustomLinkRel = linkRelValue; + CustomLinkRel = linkRelValue; } } - + /// protected override void SetExternalDocs(OpenApiOperation operation) { diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmActionOperationHandlerTests.cs b/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmActionOperationHandlerTests.cs index dca92aeb..f664f0d8 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmActionOperationHandlerTests.cs +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmActionOperationHandlerTests.cs @@ -40,7 +40,7 @@ public void CreateOperationForEdmActionReturnsCorrectOperation() Assert.Equal("Details of the shared trip.", operation.Description); Assert.NotNull(operation.Tags); var tag = Assert.Single(operation.Tags); - Assert.Equal("People.Person", tag.Name); + Assert.Equal("People.Person.Actions", tag.Name); Assert.NotNull(operation.Parameters); Assert.Single(operation.Parameters); @@ -79,7 +79,7 @@ public void CreateOperationForEdmActionReturnsCorrectOperationHierarchicalClass( Assert.Equal($"Invoke action {actionName}", operation.Summary); Assert.NotNull(operation.Tags); var tag = Assert.Single(operation.Tags); - Assert.Equal($"{entitySetName}.AccountApiModel", tag.Name); + Assert.Equal($"{entitySetName}.AccountApiModel.Actions", tag.Name); Assert.NotNull(operation.Parameters); Assert.Single(operation.Parameters); diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmFunctionOperationHandlerTests.cs b/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmFunctionOperationHandlerTests.cs index d1b0c2fc..dd0fa6ba 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmFunctionOperationHandlerTests.cs +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Operation/EdmFunctionOperationHandlerTests.cs @@ -100,7 +100,7 @@ public void CreateOperationForEdmFunctionReturnsCorrectOperation(bool useHTTPSta Assert.Equal("Invoke function GetFavoriteAirline", operation.Summary); Assert.NotNull(operation.Tags); var tag = Assert.Single(operation.Tags); - Assert.Equal("People.Person", tag.Name); + Assert.Equal("People.Person.Functions", tag.Name); Assert.NotNull(operation.Parameters); Assert.Single(operation.Parameters); @@ -138,7 +138,7 @@ public void CreateOperationForEdmFunctionReturnsCorrectOperationHierarchicalClas Assert.Equal("Collection of contract attachments.", operation.Description); Assert.NotNull(operation.Tags); var tag = Assert.Single(operation.Tags); - Assert.Equal($"{entitySetName}.AccountApiModel", tag.Name); + Assert.Equal($"{entitySetName}.AccountApiModel.Functions", tag.Name); Assert.NotNull(operation.Parameters); Assert.Equal(6, operation.Parameters.Count); // id, top, skip, count, search, filter @@ -378,10 +378,10 @@ public void CreateOperationForComposableOverloadEdmFunctionReturnsCorrectOperati if (enableOperationId) { - Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-c53d", operation1.OperationId); - Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-4d93", operation2.OperationId); - Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-a2b2", operation3.OperationId); - Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-7bea", operation4.OperationId); + Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-6b6d", operation1.OperationId); + Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-2636", operation2.OperationId); + Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-6b6d", operation3.OperationId); + Assert.Equal("Customers.Customer.MyFunction1.MyFunction2-2636", operation4.OperationId); } else { @@ -575,35 +575,35 @@ public void CreateOperationForFunctionWithDateTimeParametersReturnsCorrectPathIt } [Fact] - public void CreateFunctionOperationWithAlternateKeyReturnsCorrectOperationId() - { - // Arrange + public void CreateFunctionOperationWithAlternateKeyReturnsCorrectOperationId() + { + // Arrange IEdmModel model = EdmModelHelper.GraphBetaModel; - ODataContext context = new(model, new OpenApiConvertSettings() + ODataContext context = new(model, new OpenApiConvertSettings() { - EnableOperationId = true + EnableOperationId = true }); - IEdmSingleton singleton = model.EntityContainer.FindSingleton("communications"); - IEdmEntityType entityType = model.SchemaElements.OfType().First(c => c.Name == "cloudCommunications"); - IEdmNavigationProperty navProp = entityType.DeclaredNavigationProperties().First(c => c.Name == "onlineMeetings"); - IEdmOperation action = model.SchemaElements.OfType().First(f => f.Name == "sendVirtualAppointmentReminderSms"); - IDictionary keyMappings = new Dictionary { { "joinWebUrl", "joinWebUrl" } }; - - ODataPath path = new(new ODataNavigationSourceSegment(singleton), - new ODataNavigationPropertySegment(navProp), - new ODataKeySegment(entityType, keyMappings) - { - IsAlternateKey = true - }, - new ODataOperationSegment(action)); - + IEdmSingleton singleton = model.EntityContainer.FindSingleton("communications"); + IEdmEntityType entityType = model.SchemaElements.OfType().First(c => c.Name == "cloudCommunications"); + IEdmNavigationProperty navProp = entityType.DeclaredNavigationProperties().First(c => c.Name == "onlineMeetings"); + IEdmOperation action = model.SchemaElements.OfType().First(f => f.Name == "sendVirtualAppointmentReminderSms"); + IDictionary keyMappings = new Dictionary { { "joinWebUrl", "joinWebUrl" } }; + + ODataPath path = new(new ODataNavigationSourceSegment(singleton), + new ODataNavigationPropertySegment(navProp), + new ODataKeySegment(entityType, keyMappings) + { + IsAlternateKey = true + }, + new ODataOperationSegment(action)); + // Act - var operation = _operationHandler.CreateOperation(context, path); - - // Assert - Assert.NotNull(operation); - Assert.Equal("communications.onlineMeetings.joinWebUrl.sendVirtualAppointmentReminderSms", operation.OperationId); + var operation = _operationHandler.CreateOperation(context, path); + + // Assert + Assert.NotNull(operation); + Assert.Equal("communications.onlineMeetings.joinWebUrl.sendVirtualAppointmentReminderSms", operation.OperationId); } } -} +} \ No newline at end of file diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.json b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.json index 4626b31e..49e62c4e 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.json +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.json @@ -591,7 +591,7 @@ "/Documents({Id})/Default.Upload": { "post": { "tags": [ - "Documents.DocumentDto" + "Documents.DocumentDto.Actions" ], "summary": "Invoke action Upload", "operationId": "Documents.DocumentDto.Upload", @@ -3519,7 +3519,7 @@ "/Tasks({Id})/Default.Upload": { "post": { "tags": [ - "Tasks.DocumentDto" + "Tasks.DocumentDto.Actions" ], "summary": "Invoke action Upload", "operationId": "Tasks.DocumentDto.Upload", @@ -6275,6 +6275,10 @@ "name": "Documents.DocumentDto", "x-ms-docs-toc-type": "page" }, + { + "name": "Documents.DocumentDto.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "Documents.RevisionDto", "x-ms-docs-toc-type": "page" @@ -6315,6 +6319,10 @@ "name": "Tasks.DocumentDto", "x-ms-docs-toc-type": "page" }, + { + "name": "Tasks.DocumentDto.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "Tasks.RevisionDto", "x-ms-docs-toc-type": "page" diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.yaml b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.yaml index ffb97bf3..37ae6c97 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.yaml +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.V2.yaml @@ -413,7 +413,7 @@ paths: '/Documents({Id})/Default.Upload': post: tags: - - Documents.DocumentDto + - Documents.DocumentDto.Actions summary: Invoke action Upload operationId: Documents.DocumentDto.Upload parameters: @@ -2495,7 +2495,7 @@ paths: '/Tasks({Id})/Default.Upload': post: tags: - - Tasks.DocumentDto + - Tasks.DocumentDto.Actions summary: Invoke action Upload operationId: Tasks.DocumentDto.Upload parameters: @@ -4545,6 +4545,8 @@ tags: x-ms-docs-toc-type: page - name: Documents.DocumentDto x-ms-docs-toc-type: page + - name: Documents.DocumentDto.Actions + x-ms-docs-toc-type: container - name: Documents.RevisionDto x-ms-docs-toc-type: page - name: Documents.DocumentTagRelDto @@ -4565,6 +4567,8 @@ tags: x-ms-docs-toc-type: page - name: Tasks.DocumentDto x-ms-docs-toc-type: page + - name: Tasks.DocumentDto.Actions + x-ms-docs-toc-type: container - name: Tasks.RevisionDto x-ms-docs-toc-type: page - name: Tasks.DocumentTagRelDto diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.json b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.json index e6af74cf..02c621ba 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.json +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.json @@ -663,7 +663,7 @@ "description": "Provides operations to call the Upload method.", "post": { "tags": [ - "Documents.DocumentDto" + "Documents.DocumentDto.Actions" ], "summary": "Invoke action Upload", "operationId": "Documents.DocumentDto.Upload", @@ -3940,7 +3940,7 @@ "description": "Provides operations to call the Upload method.", "post": { "tags": [ - "Tasks.DocumentDto" + "Tasks.DocumentDto.Actions" ], "summary": "Invoke action Upload", "operationId": "Tasks.DocumentDto.Upload", @@ -7481,6 +7481,10 @@ "name": "Documents.DocumentDto", "x-ms-docs-toc-type": "page" }, + { + "name": "Documents.DocumentDto.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "Documents.RevisionDto", "x-ms-docs-toc-type": "page" @@ -7521,6 +7525,10 @@ "name": "Tasks.DocumentDto", "x-ms-docs-toc-type": "page" }, + { + "name": "Tasks.DocumentDto.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "Tasks.RevisionDto", "x-ms-docs-toc-type": "page" diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.yaml b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.yaml index cd3fc34e..fae5ab93 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.yaml +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/Multiple.Schema.OpenApi.yaml @@ -460,7 +460,7 @@ paths: description: Provides operations to call the Upload method. post: tags: - - Documents.DocumentDto + - Documents.DocumentDto.Actions summary: Invoke action Upload operationId: Documents.DocumentDto.Upload parameters: @@ -2771,7 +2771,7 @@ paths: description: Provides operations to call the Upload method. post: tags: - - Tasks.DocumentDto + - Tasks.DocumentDto.Actions summary: Invoke action Upload operationId: Tasks.DocumentDto.Upload parameters: @@ -5384,6 +5384,8 @@ tags: x-ms-docs-toc-type: page - name: Documents.DocumentDto x-ms-docs-toc-type: page + - name: Documents.DocumentDto.Actions + x-ms-docs-toc-type: container - name: Documents.RevisionDto x-ms-docs-toc-type: page - name: Documents.DocumentTagRelDto @@ -5404,6 +5406,8 @@ tags: x-ms-docs-toc-type: page - name: Tasks.DocumentDto x-ms-docs-toc-type: page + - name: Tasks.DocumentDto.Actions + x-ms-docs-toc-type: container - name: Tasks.RevisionDto x-ms-docs-toc-type: page - name: Tasks.DocumentTagRelDto diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.json b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.json index 2d2dfadb..609eb6e0 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.json +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.json @@ -7696,7 +7696,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline()": { "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "Me.GetFavoriteAirline", @@ -7722,7 +7722,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName='{userName}')": { "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "Me.GetFriendsTrips", @@ -7799,7 +7799,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip": { "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "Me.GetPeersForTrip", @@ -10930,7 +10930,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire": { "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -11768,7 +11768,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip": { "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -11800,7 +11800,7 @@ "/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName='{lastName}')": { "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "Me.UpdatePersonLastName", @@ -15601,7 +15601,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline()": { "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "NewComePeople.Person.GetFavoriteAirline", @@ -15630,7 +15630,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName='{userName}')": { "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "NewComePeople.Person.GetFriendsTrips", @@ -15715,7 +15715,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip": { "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "NewComePeople.Person.GetPeersForTrip", @@ -15747,7 +15747,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire": { "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -15794,7 +15794,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip": { "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -15827,7 +15827,7 @@ "/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName='{lastName}')": { "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "NewComePeople.Person.UpdatePersonLastName", @@ -24492,7 +24492,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline()": { "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "People.Person.GetFavoriteAirline", @@ -24528,7 +24528,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName='{userName}')": { "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "People.Person.GetFriendsTrips", @@ -24613,7 +24613,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip": { "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "People.Person.GetPeersForTrip", @@ -28312,7 +28312,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire": { "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -29262,7 +29262,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip": { "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -29302,7 +29302,7 @@ "/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName='{lastName}')": { "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "People.Person.UpdatePersonLastName", @@ -31840,6 +31840,14 @@ "name": "Me.Trips.PlanItem", "x-ms-docs-toc-type": "page" }, + { + "name": "Me.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "Me.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "NewComePeople.Person", "x-ms-docs-toc-type": "page" @@ -31852,6 +31860,14 @@ "name": "NewComePeople.Person.Location", "x-ms-docs-toc-type": "page" }, + { + "name": "NewComePeople.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "NewComePeople.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "NewComePeople.Trip", "x-ms-docs-toc-type": "page" @@ -31880,6 +31896,14 @@ "name": "People.Trips.PlanItem", "x-ms-docs-toc-type": "page" }, + { + "name": "People.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "People.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "ResetDataSource", "x-ms-docs-toc-type": "container" diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.yaml b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.yaml index a725e263..d03261ed 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.yaml +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.V2.yaml @@ -5174,7 +5174,7 @@ paths: /Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline(): get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function GetFavoriteAirline operationId: Me.GetFavoriteAirline responses: @@ -5193,7 +5193,7 @@ paths: '/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName=''{userName}'')': get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function GetFriendsTrips operationId: Me.GetFriendsTrips parameters: @@ -5241,7 +5241,7 @@ paths: /Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip: post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action GetPeersForTrip operationId: Me.GetPeersForTrip parameters: @@ -7352,7 +7352,7 @@ paths: /Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire: post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: Me.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -7927,7 +7927,7 @@ paths: /Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip: post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: Me.ShareTrip @@ -7949,7 +7949,7 @@ paths: '/Me/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName=''{lastName}'')': get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function UpdatePersonLastName operationId: Me.UpdatePersonLastName parameters: @@ -10502,7 +10502,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline()': get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function GetFavoriteAirline operationId: NewComePeople.Person.GetFavoriteAirline parameters: @@ -10522,7 +10522,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName=''{userName}'')': get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function GetFriendsTrips operationId: NewComePeople.Person.GetFriendsTrips parameters: @@ -10576,7 +10576,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip': post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action GetPeersForTrip operationId: NewComePeople.Person.GetPeersForTrip parameters: @@ -10597,7 +10597,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire': post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: NewComePeople.Person.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -10629,7 +10629,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip': post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: NewComePeople.Person.ShareTrip @@ -10651,7 +10651,7 @@ paths: '/NewComePeople/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName=''{lastName}'')': get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function UpdatePersonLastName operationId: NewComePeople.Person.UpdatePersonLastName parameters: @@ -16576,7 +16576,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFavoriteAirline()': get: tags: - - People.Person + - People.Person.Functions summary: Invoke function GetFavoriteAirline operationId: People.Person.GetFavoriteAirline parameters: @@ -16602,7 +16602,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetFriendsTrips(userName=''{userName}'')': get: tags: - - People.Person + - People.Person.Functions summary: Invoke function GetFriendsTrips operationId: People.Person.GetFriendsTrips parameters: @@ -16656,7 +16656,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.GetPeersForTrip': post: tags: - - People.Person + - People.Person.Actions summary: Invoke action GetPeersForTrip operationId: People.Person.GetPeersForTrip parameters: @@ -19189,7 +19189,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager/Microsoft.OData.Service.Sample.TrippinInMemory.Models.Hire': post: tags: - - People.Person + - People.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: People.Person.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -19848,7 +19848,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.ShareTrip': post: tags: - - People.Person + - People.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: People.Person.ShareTrip @@ -19876,7 +19876,7 @@ paths: '/People/{UserName}/Microsoft.OData.Service.Sample.TrippinInMemory.Models.UpdatePersonLastName(lastName=''{lastName}'')': get: tags: - - People.Person + - People.Person.Functions summary: Invoke function UpdatePersonLastName operationId: People.Person.UpdatePersonLastName parameters: @@ -21580,12 +21580,20 @@ tags: x-ms-docs-toc-type: page - name: Me.Trips.PlanItem x-ms-docs-toc-type: page + - name: Me.Person.Functions + x-ms-docs-toc-type: container + - name: Me.Person.Actions + x-ms-docs-toc-type: container - name: NewComePeople.Person x-ms-docs-toc-type: page - name: NewComePeople.Location x-ms-docs-toc-type: page - name: NewComePeople.Person.Location x-ms-docs-toc-type: page + - name: NewComePeople.Person.Functions + x-ms-docs-toc-type: container + - name: NewComePeople.Person.Actions + x-ms-docs-toc-type: container - name: NewComePeople.Trip x-ms-docs-toc-type: page - name: NewComePeople.Trips.PlanItem @@ -21600,5 +21608,9 @@ tags: x-ms-docs-toc-type: page - name: People.Trips.PlanItem x-ms-docs-toc-type: page + - name: People.Person.Functions + x-ms-docs-toc-type: container + - name: People.Person.Actions + x-ms-docs-toc-type: container - name: ResetDataSource x-ms-docs-toc-type: container \ No newline at end of file diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.json b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.json index 8872302d..146b726d 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.json +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.json @@ -8518,7 +8518,7 @@ "description": "Provides operations to call the GetFavoriteAirline method.", "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "Me.GetFavoriteAirline", @@ -8544,7 +8544,7 @@ "description": "Provides operations to call the GetFriendsTrips method.", "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "Me.GetFriendsTrips", @@ -8638,7 +8638,7 @@ "description": "Provides operations to call the GetPeersForTrip method.", "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "Me.GetPeersForTrip", @@ -12054,7 +12054,7 @@ "description": "Provides operations to call the Hire method.", "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -12990,7 +12990,7 @@ "description": "Provides operations to call the ShareTrip method.", "post": { "tags": [ - "Me.Person" + "Me.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -13020,7 +13020,7 @@ "description": "Provides operations to call the UpdatePersonLastName method.", "get": { "tags": [ - "Me.Person" + "Me.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "Me.UpdatePersonLastName", @@ -17309,7 +17309,7 @@ "description": "Provides operations to call the GetFavoriteAirline method.", "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "NewComePeople.Person.GetFavoriteAirline", @@ -17340,7 +17340,7 @@ "description": "Provides operations to call the GetFriendsTrips method.", "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "NewComePeople.Person.GetFriendsTrips", @@ -17444,7 +17444,7 @@ "description": "Provides operations to call the GetPeersForTrip method.", "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "NewComePeople.Person.GetPeersForTrip", @@ -17478,7 +17478,7 @@ "description": "Provides operations to call the Hire method.", "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -17534,7 +17534,7 @@ "description": "Provides operations to call the ShareTrip method.", "post": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -17569,7 +17569,7 @@ "description": "Provides operations to call the UpdatePersonLastName method.", "get": { "tags": [ - "NewComePeople.Person" + "NewComePeople.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "NewComePeople.Person.UpdatePersonLastName", @@ -27318,7 +27318,7 @@ "description": "Provides operations to call the GetFavoriteAirline method.", "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function GetFavoriteAirline", "operationId": "People.Person.GetFavoriteAirline", @@ -27356,7 +27356,7 @@ "description": "Provides operations to call the GetFriendsTrips method.", "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function GetFriendsTrips", "operationId": "People.Person.GetFriendsTrips", @@ -27460,7 +27460,7 @@ "description": "Provides operations to call the GetPeersForTrip method.", "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action GetPeersForTrip", "operationId": "People.Person.GetPeersForTrip", @@ -31602,7 +31602,7 @@ "description": "Provides operations to call the Hire method.", "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action Hire", "description": "Hires someone for the company.", @@ -32682,7 +32682,7 @@ "description": "Provides operations to call the ShareTrip method.", "post": { "tags": [ - "People.Person" + "People.Person.Actions" ], "summary": "Invoke action ShareTrip", "description": "Details of the shared trip.", @@ -32724,7 +32724,7 @@ "description": "Provides operations to call the UpdatePersonLastName method.", "get": { "tags": [ - "People.Person" + "People.Person.Functions" ], "summary": "Invoke function UpdatePersonLastName", "operationId": "People.Person.UpdatePersonLastName", @@ -35875,6 +35875,14 @@ "name": "Me.Trips.PlanItem", "x-ms-docs-toc-type": "page" }, + { + "name": "Me.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "Me.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "NewComePeople.Person", "x-ms-docs-toc-type": "page" @@ -35887,6 +35895,14 @@ "name": "NewComePeople.Person.Location", "x-ms-docs-toc-type": "page" }, + { + "name": "NewComePeople.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "NewComePeople.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "NewComePeople.Trip", "x-ms-docs-toc-type": "page" @@ -35915,6 +35931,14 @@ "name": "People.Trips.PlanItem", "x-ms-docs-toc-type": "page" }, + { + "name": "People.Person.Functions", + "x-ms-docs-toc-type": "container" + }, + { + "name": "People.Person.Actions", + "x-ms-docs-toc-type": "container" + }, { "name": "ResetDataSource", "x-ms-docs-toc-type": "container" diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.yaml b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.yaml index a26b7b90..6773a8b8 100644 --- a/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.yaml +++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/Resources/TripService.OpenApi.yaml @@ -5701,7 +5701,7 @@ paths: description: Provides operations to call the GetFavoriteAirline method. get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function GetFavoriteAirline operationId: Me.GetFavoriteAirline responses: @@ -5720,7 +5720,7 @@ paths: description: Provides operations to call the GetFriendsTrips method. get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function GetFriendsTrips operationId: Me.GetFriendsTrips parameters: @@ -5781,7 +5781,7 @@ paths: description: Provides operations to call the GetPeersForTrip method. post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action GetPeersForTrip operationId: Me.GetPeersForTrip requestBody: @@ -8079,7 +8079,7 @@ paths: description: Provides operations to call the Hire method. post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: Me.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -8718,7 +8718,7 @@ paths: description: Provides operations to call the ShareTrip method. post: tags: - - Me.Person + - Me.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: Me.ShareTrip @@ -8740,7 +8740,7 @@ paths: description: Provides operations to call the UpdatePersonLastName method. get: tags: - - Me.Person + - Me.Person.Functions summary: Invoke function UpdatePersonLastName operationId: Me.UpdatePersonLastName parameters: @@ -11598,7 +11598,7 @@ paths: description: Provides operations to call the GetFavoriteAirline method. get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function GetFavoriteAirline operationId: NewComePeople.Person.GetFavoriteAirline parameters: @@ -11619,7 +11619,7 @@ paths: description: Provides operations to call the GetFriendsTrips method. get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function GetFriendsTrips operationId: NewComePeople.Person.GetFriendsTrips parameters: @@ -11687,7 +11687,7 @@ paths: description: Provides operations to call the GetPeersForTrip method. post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action GetPeersForTrip operationId: NewComePeople.Person.GetPeersForTrip parameters: @@ -11710,7 +11710,7 @@ paths: description: Provides operations to call the Hire method. post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: NewComePeople.Person.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -11745,7 +11745,7 @@ paths: description: Provides operations to call the ShareTrip method. post: tags: - - NewComePeople.Person + - NewComePeople.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: NewComePeople.Person.ShareTrip @@ -11769,7 +11769,7 @@ paths: description: Provides operations to call the UpdatePersonLastName method. get: tags: - - NewComePeople.Person + - NewComePeople.Person.Functions summary: Invoke function UpdatePersonLastName operationId: NewComePeople.Person.UpdatePersonLastName parameters: @@ -18357,7 +18357,7 @@ paths: description: Provides operations to call the GetFavoriteAirline method. get: tags: - - People.Person + - People.Person.Functions summary: Invoke function GetFavoriteAirline operationId: People.Person.GetFavoriteAirline parameters: @@ -18384,7 +18384,7 @@ paths: description: Provides operations to call the GetFriendsTrips method. get: tags: - - People.Person + - People.Person.Functions summary: Invoke function GetFriendsTrips operationId: People.Person.GetFriendsTrips parameters: @@ -18452,7 +18452,7 @@ paths: description: Provides operations to call the GetPeersForTrip method. post: tags: - - People.Person + - People.Person.Actions summary: Invoke action GetPeersForTrip operationId: People.Person.GetPeersForTrip parameters: @@ -21251,7 +21251,7 @@ paths: description: Provides operations to call the Hire method. post: tags: - - People.Person + - People.Person.Actions summary: Invoke action Hire description: Hires someone for the company. operationId: People.Person.Microsoft.OData.Service.Sample.TrippinInMemory.Models.Manager.Hire @@ -21990,7 +21990,7 @@ paths: description: Provides operations to call the ShareTrip method. post: tags: - - People.Person + - People.Person.Actions summary: Invoke action ShareTrip description: Details of the shared trip. operationId: People.Person.ShareTrip @@ -22020,7 +22020,7 @@ paths: description: Provides operations to call the UpdatePersonLastName method. get: tags: - - People.Person + - People.Person.Functions summary: Invoke function UpdatePersonLastName operationId: People.Person.UpdatePersonLastName parameters: @@ -24080,12 +24080,20 @@ tags: x-ms-docs-toc-type: page - name: Me.Trips.PlanItem x-ms-docs-toc-type: page + - name: Me.Person.Functions + x-ms-docs-toc-type: container + - name: Me.Person.Actions + x-ms-docs-toc-type: container - name: NewComePeople.Person x-ms-docs-toc-type: page - name: NewComePeople.Location x-ms-docs-toc-type: page - name: NewComePeople.Person.Location x-ms-docs-toc-type: page + - name: NewComePeople.Person.Functions + x-ms-docs-toc-type: container + - name: NewComePeople.Person.Actions + x-ms-docs-toc-type: container - name: NewComePeople.Trip x-ms-docs-toc-type: page - name: NewComePeople.Trips.PlanItem @@ -24100,5 +24108,9 @@ tags: x-ms-docs-toc-type: page - name: People.Trips.PlanItem x-ms-docs-toc-type: page + - name: People.Person.Functions + x-ms-docs-toc-type: container + - name: People.Person.Actions + x-ms-docs-toc-type: container - name: ResetDataSource x-ms-docs-toc-type: container \ No newline at end of file