diff --git a/src/Microsoft.OpenApi.OData.Reader/Edm/RecordExpressionExtensions.cs b/src/Microsoft.OpenApi.OData.Reader/Edm/RecordExpressionExtensions.cs
index 01cf7aea..5d8dc6d4 100644
--- a/src/Microsoft.OpenApi.OData.Reader/Edm/RecordExpressionExtensions.cs
+++ b/src/Microsoft.OpenApi.OData.Reader/Edm/RecordExpressionExtensions.cs
@@ -94,18 +94,30 @@ public static string GetString(this IEdmRecordExpression record, string property
/// The property name.
/// The Enum value or null.
public static T? GetEnum(this IEdmRecordExpression record, string propertyName)
- where T : struct
+ where T : struct, Enum
{
Utils.CheckArgumentNull(record, nameof(record));
Utils.CheckArgumentNull(propertyName, nameof(propertyName));
- return (record.Properties?.FirstOrDefault(e => propertyName.Equals(e.Name, StringComparison.Ordinal)) is IEdmPropertyConstructor property &&
+ if (record.Properties?.FirstOrDefault(e => propertyName.Equals(e.Name, StringComparison.Ordinal))
+ is IEdmPropertyConstructor property &&
property.Value is IEdmEnumMemberExpression value &&
value.EnumMembers != null &&
- value.EnumMembers.Any() &&
- Enum.TryParse(value.EnumMembers.First().Name, out T result)) ?
- result :
- null;
+ value.EnumMembers.Any())
+ {
+ long combinedValue = 0;
+ foreach (var enumMember in value.EnumMembers)
+ {
+ if (Enum.TryParse(enumMember.Name, out T enumValue))
+ {
+ combinedValue |= Convert.ToInt64(enumValue);
+ }
+ }
+
+ return (T)Enum.ToObject(typeof(T), combinedValue);
+ }
+
+ return null;
}
///
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 4283a792..feae9f0d 100644
--- a/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj
+++ b/src/Microsoft.OpenApi.OData.Reader/Microsoft.OpenAPI.OData.Reader.csproj
@@ -15,15 +15,16 @@
net8.0
Microsoft.OpenApi.OData
true
- 2.0.0-preview.1
+ 2.0.0-preview.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
- Upgraded to Microsoft.Odata.Edm 8.0.0
- - Cleaned up obsolete APIs
- - Changed target framework to net8.0
+ - Cleaned up obsolete APIs
+ - Changed target framework to net8.0
+ - Adds support for retrieving collection of enum values from UpdateMethod property of UpdateRestrictions annotation #564
Microsoft.OpenApi.OData.Reader
..\..\tool\Microsoft.OpenApi.OData.snk
diff --git a/src/Microsoft.OpenApi.OData.Reader/PathItem/ComplexPropertyItemHandler.cs b/src/Microsoft.OpenApi.OData.Reader/PathItem/ComplexPropertyItemHandler.cs
index 866dcef3..b08a2289 100644
--- a/src/Microsoft.OpenApi.OData.Reader/PathItem/ComplexPropertyItemHandler.cs
+++ b/src/Microsoft.OpenApi.OData.Reader/PathItem/ComplexPropertyItemHandler.cs
@@ -70,7 +70,12 @@ public void AddUpdateOperation(OpenApiPathItem item)
if ((Context.Settings.RequireRestrictionAnnotationsToGenerateComplexPropertyPaths && isUpdatable) ||
!Context.Settings.RequireRestrictionAnnotationsToGenerateComplexPropertyPaths)
{
- if (updateRestrictions != null && updateRestrictions.IsUpdateMethodPut)
+ if (updateRestrictions?.IsUpdateMethodPutAndPatch == true)
+ {
+ AddOperation(item, OperationType.Put);
+ AddOperation(item, OperationType.Patch);
+ }
+ else if (updateRestrictions?.IsUpdateMethodPut == true)
{
AddOperation(item, OperationType.Put);
}
diff --git a/src/Microsoft.OpenApi.OData.Reader/PathItem/EntityPathItemHandler.cs b/src/Microsoft.OpenApi.OData.Reader/PathItem/EntityPathItemHandler.cs
index 243d6f3b..0cbbb54c 100644
--- a/src/Microsoft.OpenApi.OData.Reader/PathItem/EntityPathItemHandler.cs
+++ b/src/Microsoft.OpenApi.OData.Reader/PathItem/EntityPathItemHandler.cs
@@ -40,7 +40,12 @@ protected override void SetOperations(OpenApiPathItem item)
updateRestrictions ??= entityUpdateRestrictions;
if (updateRestrictions?.IsUpdatable ?? true)
{
- if (updateRestrictions != null && updateRestrictions.IsUpdateMethodPut)
+ if (updateRestrictions?.IsUpdateMethodPutAndPatch == true)
+ {
+ AddOperation(item, OperationType.Put);
+ AddOperation(item, OperationType.Patch);
+ }
+ else if (updateRestrictions?.IsUpdateMethodPut == true)
{
AddOperation(item, OperationType.Put);
}
diff --git a/src/Microsoft.OpenApi.OData.Reader/PathItem/NavigationPropertyPathItemHandler.cs b/src/Microsoft.OpenApi.OData.Reader/PathItem/NavigationPropertyPathItemHandler.cs
index 57b36119..e66675f7 100644
--- a/src/Microsoft.OpenApi.OData.Reader/PathItem/NavigationPropertyPathItemHandler.cs
+++ b/src/Microsoft.OpenApi.OData.Reader/PathItem/NavigationPropertyPathItemHandler.cs
@@ -243,17 +243,23 @@ private void AddDeleteOperation(OpenApiPathItem item, NavigationPropertyRestrict
private void AddUpdateOperation(OpenApiPathItem item, UpdateRestrictionsType updateRestrictionsType)
{
- if (updateRestrictionsType == null || updateRestrictionsType.IsUpdatable)
- {
- if (updateRestrictionsType != null && updateRestrictionsType.IsUpdateMethodPut)
- {
- AddOperation(item, OperationType.Put);
- }
- else
- {
- AddOperation(item, OperationType.Patch);
- }
- }
+ if (updateRestrictionsType?.IsUpdatable ?? true)
+ {
+ if (updateRestrictionsType?.IsUpdateMethodPutAndPatch == true)
+ {
+ AddOperation(item, OperationType.Put);
+ AddOperation(item, OperationType.Patch);
+ }
+ else if (updateRestrictionsType?.IsUpdateMethodPut == true)
+ {
+ AddOperation(item, OperationType.Put);
+ }
+ else
+ {
+ AddOperation(item, OperationType.Patch);
+ }
+ }
+
}
///
diff --git a/src/Microsoft.OpenApi.OData.Reader/Vocabulary/Capabilities/UpdateRestrictionsType.cs b/src/Microsoft.OpenApi.OData.Reader/Vocabulary/Capabilities/UpdateRestrictionsType.cs
index 27e3e8f5..ff073e39 100644
--- a/src/Microsoft.OpenApi.OData.Reader/Vocabulary/Capabilities/UpdateRestrictionsType.cs
+++ b/src/Microsoft.OpenApi.OData.Reader/Vocabulary/Capabilities/UpdateRestrictionsType.cs
@@ -3,6 +3,7 @@
// Licensed under the MIT License (MIT). See LICENSE in the repo root for license information.
// ------------------------------------------------------------
+using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.OData.Edm.Vocabularies;
@@ -14,17 +15,18 @@ namespace Microsoft.OpenApi.OData.Vocabulary.Capabilities
///
/// Enumerates HTTP methods that can be used to update entities
///
+ [Flags]
internal enum HttpMethod
{
///
/// The HTTP PATCH Method
///
- PATCH,
+ PATCH = 1,
///
/// The HTTP PUT Method
///
- PUT
+ PUT = 2
}
///
/// Complex Type: Org.OData.Capabilities.V1.UpdateRestrictionsType
@@ -46,10 +48,10 @@ internal class UpdateRestrictionsType : IRecord
///
/// Gets the value indicating Entities can be inserted, updated, and deleted via a PATCH request with a delta payload.
///
- public bool? DeltaUpdateSupported { get; private set; }
-
+ public bool? DeltaUpdateSupported { get; private set; }
+
///
- /// Gets the value indicating the HTTP Method (PUT or PATCH) for updating an entity.
+ /// Gets the values indicating the HTTP Method (PUT and/or PATCH) for updating an entity.
/// If null, PATCH should be supported and PUT MAY be supported.
///
public HttpMethod? UpdateMethod { get; private set; }
@@ -124,10 +126,16 @@ public bool IsNonUpdatableNavigationProperty(string navigationPropertyPath)
}
///
- /// Tests whether the update method for the entity has been explicitly specified as PUT
+ /// Tests whether the update method for the target has been explicitly specified as PUT
///
public bool IsUpdateMethodPut => UpdateMethod.HasValue && UpdateMethod.Value == HttpMethod.PUT;
+ ///
+ /// Tests whether the update method for the target has been explicitly specified as PATCH and PUT
+ ///
+ public bool IsUpdateMethodPutAndPatch => UpdateMethod.HasValue &&
+ (UpdateMethod.Value & (HttpMethod.PUT | HttpMethod.PATCH)) == (HttpMethod.PUT | HttpMethod.PATCH);
+
///
/// Lists the media types acceptable for the request content
///
@@ -157,7 +165,7 @@ public void Initialize(IEdmRecordExpression record)
// DeltaUpdateSupported
DeltaUpdateSupported = record.GetBoolean("DeltaUpdateSupported");
- // UpdateMethod
+ // UpdateMethod
UpdateMethod = record.GetEnum("UpdateMethod");
// FilterSegmentSupported
diff --git a/test/Microsoft.OpenAPI.OData.Reader.Tests/PathItem/NavigationPropertyPathItemHandlerTests.cs b/test/Microsoft.OpenAPI.OData.Reader.Tests/PathItem/NavigationPropertyPathItemHandlerTests.cs
index 20e9c066..31eddf46 100644
--- a/test/Microsoft.OpenAPI.OData.Reader.Tests/PathItem/NavigationPropertyPathItemHandlerTests.cs
+++ b/test/Microsoft.OpenAPI.OData.Reader.Tests/PathItem/NavigationPropertyPathItemHandlerTests.cs
@@ -452,7 +452,7 @@ public void CreatePathItemForNavigationPropertyAndUpdateMethodUpdateRestrictions
- Org.OData.Capabilities.V1.HttpMethod/PUT
+ Org.OData.Capabilities.V1.HttpMethod/PUT Org.OData.Capabilities.V1.HttpMethod/PATCH
@@ -488,21 +488,21 @@ public void CreatePathItemForNavigationPropertyAndUpdateMethodUpdateRestrictions
if (isContainment)
{
expected = updatable
- ? (new[] { OperationType.Get, OperationType.Put, OperationType.Delete })
- : (new[] { OperationType.Get, OperationType.Delete });
+ ? ([OperationType.Get, OperationType.Put, OperationType.Patch, OperationType.Delete])
+ : ([OperationType.Get, OperationType.Delete]);
}
else
{
expected = updatable
- ? (new[] { OperationType.Get, OperationType.Put })
- : (new[] { OperationType.Get });
+ ? ([OperationType.Get, OperationType.Put, OperationType.Patch,])
+ : ([OperationType.Get]);
}
}
else
{
expected = isContainment
- ? (new[] { OperationType.Get, OperationType.Patch, OperationType.Delete })
- : (new[] { OperationType.Get });
+ ? ([OperationType.Get, OperationType.Patch, OperationType.Delete])
+ : ([OperationType.Get]);
}