diff --git a/src/Microsoft.OpenApi.Hidi/StatsVisitor.cs b/src/Microsoft.OpenApi.Hidi/StatsVisitor.cs
index 53f52ab3d..645f94319 100644
--- a/src/Microsoft.OpenApi.Hidi/StatsVisitor.cs
+++ b/src/Microsoft.OpenApi.Hidi/StatsVisitor.cs
@@ -41,7 +41,7 @@ public override void Visit(IOpenApiPathItem pathItem)
public int RequestBodyCount { get; set; }
- public override void Visit(OpenApiRequestBody requestBody)
+ public override void Visit(IOpenApiRequestBody requestBody)
{
RequestBodyCount++;
}
diff --git a/src/Microsoft.OpenApi.Workbench/StatsVisitor.cs b/src/Microsoft.OpenApi.Workbench/StatsVisitor.cs
index 6097f1f4e..fbf9f3c9a 100644
--- a/src/Microsoft.OpenApi.Workbench/StatsVisitor.cs
+++ b/src/Microsoft.OpenApi.Workbench/StatsVisitor.cs
@@ -41,7 +41,7 @@ public override void Visit(IOpenApiPathItem pathItem)
public int RequestBodyCount { get; set; }
- public override void Visit(OpenApiRequestBody requestBody)
+ public override void Visit(IOpenApiRequestBody requestBody)
{
RequestBodyCount++;
}
diff --git a/src/Microsoft.OpenApi/Models/Interfaces/IOpenApiRequestBody.cs b/src/Microsoft.OpenApi/Models/Interfaces/IOpenApiRequestBody.cs
new file mode 100644
index 000000000..f014d2b4d
--- /dev/null
+++ b/src/Microsoft.OpenApi/Models/Interfaces/IOpenApiRequestBody.cs
@@ -0,0 +1,35 @@
+using System.Collections.Generic;
+using Microsoft.OpenApi.Interfaces;
+using Microsoft.OpenApi.Writers;
+
+namespace Microsoft.OpenApi.Models.Interfaces;
+
+///
+/// Defines the base properties for the request body object.
+/// This interface is provided for type assertions but should not be implemented by package consumers beyond automatic mocking.
+///
+public interface IOpenApiRequestBody : IOpenApiDescribedElement, IOpenApiSerializable, IOpenApiReadOnlyExtensible
+{
+ ///
+ /// Determines if the request body is required in the request. Defaults to false.
+ ///
+ public bool Required { get; }
+
+ ///
+ /// REQUIRED. The content of the request body. The key is a media type or media type range and the value describes it.
+ /// For requests that match multiple keys, only the most specific key is applicable. e.g. text/plain overrides text/*
+ ///
+ public IDictionary Content { get; }
+ ///
+ /// Converts the request body to a body parameter in preparation for a v2 serialization.
+ ///
+ /// The writer to use to read settings from.
+ /// The converted OpenAPI parameter
+ IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer);
+ ///
+ /// Converts the request body to a set of form data parameters in preparation for a v2 serialization.
+ ///
+ /// The writer to use to read settings from
+ /// The converted OpenAPI parameters
+ IEnumerable ConvertToFormDataParameters(IOpenApiWriter writer);
+}
diff --git a/src/Microsoft.OpenApi/Models/OpenApiComponents.cs b/src/Microsoft.OpenApi/Models/OpenApiComponents.cs
index 7cd577397..f58d2644a 100644
--- a/src/Microsoft.OpenApi/Models/OpenApiComponents.cs
+++ b/src/Microsoft.OpenApi/Models/OpenApiComponents.cs
@@ -39,10 +39,10 @@ public class OpenApiComponents : IOpenApiSerializable, IOpenApiExtensible
public IDictionary? Examples { get; set; } = new Dictionary();
///
- /// An object to hold reusable Objects.
+ /// An object to hold reusable Objects.
///
- public IDictionary? RequestBodies { get; set; } =
- new Dictionary();
+ public IDictionary? RequestBodies { get; set; } =
+ new Dictionary();
///
/// An object to hold reusable Objects.
@@ -89,7 +89,7 @@ public OpenApiComponents(OpenApiComponents? components)
Responses = components?.Responses != null ? new Dictionary(components.Responses) : null;
Parameters = components?.Parameters != null ? new Dictionary(components.Parameters) : null;
Examples = components?.Examples != null ? new Dictionary(components.Examples) : null;
- RequestBodies = components?.RequestBodies != null ? new Dictionary(components.RequestBodies) : null;
+ RequestBodies = components?.RequestBodies != null ? new Dictionary(components.RequestBodies) : null;
Headers = components?.Headers != null ? new Dictionary(components.Headers) : null;
SecuritySchemes = components?.SecuritySchemes != null ? new Dictionary(components.SecuritySchemes) : null;
Links = components?.Links != null ? new Dictionary(components.Links) : null;
diff --git a/src/Microsoft.OpenApi/Models/OpenApiDocument.cs b/src/Microsoft.OpenApi/Models/OpenApiDocument.cs
index 6e733d0fa..52e2243b7 100644
--- a/src/Microsoft.OpenApi/Models/OpenApiDocument.cs
+++ b/src/Microsoft.OpenApi/Models/OpenApiDocument.cs
@@ -600,7 +600,7 @@ public bool AddComponent(string id, T componentToRegister)
Components.Responses.Add(id, openApiResponse);
break;
case OpenApiRequestBody openApiRequestBody:
- Components.RequestBodies ??= new Dictionary();
+ Components.RequestBodies ??= new Dictionary();
Components.RequestBodies.Add(id, openApiRequestBody);
break;
case OpenApiLink openApiLink:
diff --git a/src/Microsoft.OpenApi/Models/OpenApiOperation.cs b/src/Microsoft.OpenApi/Models/OpenApiOperation.cs
index 0a2f4259b..927bf839a 100644
--- a/src/Microsoft.OpenApi/Models/OpenApiOperation.cs
+++ b/src/Microsoft.OpenApi/Models/OpenApiOperation.cs
@@ -66,7 +66,7 @@ public class OpenApiOperation : IOpenApiSerializable, IOpenApiExtensible, IOpenA
/// has explicitly defined semantics for request bodies.
/// In other cases where the HTTP spec is vague, requestBody SHALL be ignored by consumers.
///
- public OpenApiRequestBody? RequestBody { get; set; }
+ public IOpenApiRequestBody? RequestBody { get; set; }
///
/// REQUIRED. The list of possible responses as they are returned from executing this operation.
@@ -128,7 +128,7 @@ public OpenApiOperation(OpenApiOperation? operation)
ExternalDocs = operation?.ExternalDocs != null ? new(operation?.ExternalDocs) : null;
OperationId = operation?.OperationId ?? OperationId;
Parameters = operation?.Parameters != null ? new List(operation.Parameters) : null;
- RequestBody = operation?.RequestBody != null ? new(operation?.RequestBody) : null;
+ RequestBody = operation?.RequestBody != null ? new OpenApiRequestBody(operation?.RequestBody) : null;
Responses = operation?.Responses != null ? new(operation?.Responses) : null;
Callbacks = operation?.Callbacks != null ? new Dictionary(operation.Callbacks) : null;
Deprecated = operation?.Deprecated ?? Deprecated;
@@ -235,15 +235,7 @@ public void SerializeAsV2(IOpenApiWriter writer)
// operationId
writer.WriteProperty(OpenApiConstants.OperationId, OperationId);
- List parameters;
- if (Parameters == null)
- {
- parameters = [];
- }
- else
- {
- parameters = [.. Parameters];
- }
+ List parameters = Parameters is null ? new() : new(Parameters);
if (RequestBody != null)
{
@@ -255,17 +247,17 @@ public void SerializeAsV2(IOpenApiWriter writer)
if (consumes.Contains("application/x-www-form-urlencoded") ||
consumes.Contains("multipart/form-data"))
{
- parameters.AddRange(RequestBody.ConvertToFormDataParameters());
+ parameters.AddRange(RequestBody.ConvertToFormDataParameters(writer));
}
else
{
parameters.Add(RequestBody.ConvertToBodyParameter(writer));
}
}
- else if (RequestBody.Reference != null && RequestBody.Reference.HostDocument is {} hostDocument)
+ else if (RequestBody is OpenApiRequestBodyReference requestBodyReference)
{
parameters.Add(
- new OpenApiParameterReference(RequestBody.Reference.Id, hostDocument));
+ new OpenApiParameterReference(requestBodyReference.Reference.Id, requestBodyReference.Reference.HostDocument));
}
if (consumes.Count > 0)
diff --git a/src/Microsoft.OpenApi/Models/OpenApiRequestBody.cs b/src/Microsoft.OpenApi/Models/OpenApiRequestBody.cs
index 2524c41d6..b5fd3f605 100644
--- a/src/Microsoft.OpenApi/Models/OpenApiRequestBody.cs
+++ b/src/Microsoft.OpenApi/Models/OpenApiRequestBody.cs
@@ -15,39 +15,19 @@ namespace Microsoft.OpenApi.Models
///
/// Request Body Object
///
- public class OpenApiRequestBody : IOpenApiReferenceable, IOpenApiExtensible
+ public class OpenApiRequestBody : IOpenApiReferenceable, IOpenApiExtensible, IOpenApiRequestBody
{
- ///
- /// Indicates if object is populated with data or is just a reference to the data
- ///
- public bool UnresolvedReference { get; set; }
-
- ///
- /// Reference object.
- ///
- public OpenApiReference Reference { get; set; }
-
- ///
- /// A brief description of the request body. This could contain examples of use.
- /// CommonMark syntax MAY be used for rich text representation.
- ///
- public virtual string Description { get; set; }
+ ///
+ public string Description { get; set; }
- ///
- /// Determines if the request body is required in the request. Defaults to false.
- ///
- public virtual bool Required { get; set; }
+ ///
+ public bool Required { get; set; }
- ///
- /// REQUIRED. The content of the request body. The key is a media type or media type range and the value describes it.
- /// For requests that match multiple keys, only the most specific key is applicable. e.g. text/plain overrides text/*
- ///
- public virtual IDictionary Content { get; set; } = new Dictionary();
+ ///
+ public IDictionary Content { get; set; } = new Dictionary();
- ///
- /// This object MAY be extended with Specification Extensions.
- ///
- public virtual IDictionary Extensions { get; set; } = new Dictionary();
+ ///
+ public IDictionary Extensions { get; set; } = new Dictionary();
///
/// Parameter-less constructor
@@ -55,12 +35,11 @@ public class OpenApiRequestBody : IOpenApiReferenceable, IOpenApiExtensible
public OpenApiRequestBody() { }
///
- /// Initializes a copy instance of an object
+ /// Initializes a copy instance of an object
///
- public OpenApiRequestBody(OpenApiRequestBody requestBody)
+ public OpenApiRequestBody(IOpenApiRequestBody requestBody)
{
- UnresolvedReference = requestBody?.UnresolvedReference ?? UnresolvedReference;
- Reference = requestBody?.Reference != null ? new(requestBody?.Reference) : null;
+ Utils.CheckArgumentNull(requestBody);
Description = requestBody?.Description ?? Description;
Required = requestBody?.Required ?? Required;
Content = requestBody?.Content != null ? new Dictionary(requestBody.Content) : null;
@@ -70,7 +49,7 @@ public OpenApiRequestBody(OpenApiRequestBody requestBody)
///
/// Serialize to Open Api v3.1
///
- public virtual void SerializeAsV31(IOpenApiWriter writer)
+ public void SerializeAsV31(IOpenApiWriter writer)
{
SerializeInternal(writer, OpenApiSpecVersion.OpenApi3_1, (writer, element) => element.SerializeAsV31(writer));
}
@@ -78,12 +57,12 @@ public virtual void SerializeAsV31(IOpenApiWriter writer)
///
/// Serialize to Open Api v3.0
///
- public virtual void SerializeAsV3(IOpenApiWriter writer)
+ public void SerializeAsV3(IOpenApiWriter writer)
{
SerializeInternal(writer, OpenApiSpecVersion.OpenApi3_0, (writer, element) => element.SerializeAsV3(writer));
}
- internal virtual void SerializeInternal(IOpenApiWriter writer, OpenApiSpecVersion version,
+ internal void SerializeInternal(IOpenApiWriter writer, OpenApiSpecVersion version,
Action callback)
{
Utils.CheckArgumentNull(writer);
@@ -113,7 +92,8 @@ public void SerializeAsV2(IOpenApiWriter writer)
// RequestBody object does not exist in V2.
}
- internal virtual IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer)
+ ///
+ public IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer)
{
var bodyParameter = new OpenApiBodyParameter
{
@@ -135,7 +115,8 @@ internal virtual IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer)
return bodyParameter;
}
- internal IEnumerable ConvertToFormDataParameters()
+ ///
+ public IEnumerable ConvertToFormDataParameters(IOpenApiWriter writer)
{
if (Content == null || !Content.Any())
yield break;
@@ -143,14 +124,14 @@ internal IEnumerable ConvertToFormDataParameters()
foreach (var property in Content.First().Value.Schema.Properties)
{
var paramSchema = property.Value;
- if ("string".Equals(paramSchema.Type.ToIdentifier(), StringComparison.OrdinalIgnoreCase)
+ if ((paramSchema.Type & JsonSchemaType.String) == JsonSchemaType.String
&& ("binary".Equals(paramSchema.Format, StringComparison.OrdinalIgnoreCase)
|| "base64".Equals(paramSchema.Format, StringComparison.OrdinalIgnoreCase)))
{
paramSchema.Type = "file".ToJsonSchemaType();
paramSchema.Format = null;
}
- yield return new()
+ yield return new OpenApiFormDataParameter()
{
Description = property.Value.Description,
Name = property.Key,
diff --git a/src/Microsoft.OpenApi/Models/References/OpenApiRequestBodyReference.cs b/src/Microsoft.OpenApi/Models/References/OpenApiRequestBodyReference.cs
index 5aa466415..d698dd092 100644
--- a/src/Microsoft.OpenApi/Models/References/OpenApiRequestBodyReference.cs
+++ b/src/Microsoft.OpenApi/Models/References/OpenApiRequestBodyReference.cs
@@ -3,6 +3,7 @@
using System;
using System.Collections.Generic;
+using System.Linq;
using Microsoft.OpenApi.Interfaces;
using Microsoft.OpenApi.Models.Interfaces;
using Microsoft.OpenApi.Writers;
@@ -12,29 +13,8 @@ namespace Microsoft.OpenApi.Models.References
///
/// Request Body Object Reference.
///
- public class OpenApiRequestBodyReference : OpenApiRequestBody, IOpenApiReferenceHolder
+ public class OpenApiRequestBodyReference : BaseOpenApiReferenceHolder, IOpenApiRequestBody
{
- internal OpenApiRequestBody _target;
- private readonly OpenApiReference _reference;
- private string _description;
-
- ///
- /// Gets the target request body.
- ///
- ///
- /// If the reference is not resolved, this will return null.
- ///
- public OpenApiRequestBody Target
- {
- get
- {
- _target ??= Reference.HostDocument.ResolveReferenceTo(_reference);
- OpenApiRequestBody resolved = new OpenApiRequestBody(_target);
- if (!string.IsNullOrEmpty(_description)) resolved.Description = _description;
- return resolved;
- }
- }
-
///
/// Constructor initializing the reference object.
///
@@ -45,93 +25,69 @@ public OpenApiRequestBody Target
/// 1. a absolute/relative file path, for example: ../commons/pet.json
/// 2. a Url, for example: http://localhost/pet.json
///
- public OpenApiRequestBodyReference(string referenceId, OpenApiDocument hostDocument, string externalResource = null)
+ public OpenApiRequestBodyReference(string referenceId, OpenApiDocument hostDocument, string externalResource = null):base(referenceId, hostDocument, ReferenceType.RequestBody, externalResource)
{
- Utils.CheckArgumentNullOrEmpty(referenceId);
-
- _reference = new OpenApiReference()
- {
- Id = referenceId,
- HostDocument = hostDocument,
- Type = ReferenceType.RequestBody,
- ExternalResource = externalResource
- };
-
- Reference = _reference;
}
-
- internal OpenApiRequestBodyReference(OpenApiRequestBody target, string referenceId)
+ internal OpenApiRequestBodyReference(OpenApiRequestBody target, string referenceId):base(target, referenceId, ReferenceType.RequestBody)
{
- _target = target;
-
- _reference = new OpenApiReference()
- {
- Id = referenceId,
- Type = ReferenceType.RequestBody,
- };
}
///
- public override string Description
+ public string Description
{
- get => string.IsNullOrEmpty(_description) ? Target.Description : _description;
- set => _description = value;
+ get => string.IsNullOrEmpty(Reference?.Description) ? Target?.Description : Reference.Description;
+ set
+ {
+ if (Reference is not null)
+ {
+ Reference.Description = value;
+ }
+ }
}
///
- public override IDictionary Content { get => Target.Content; set => Target.Content = value; }
+ public IDictionary Content { get => Target?.Content; }
///
- public override bool Required { get => Target.Required; set => Target.Required = value; }
+ public bool Required { get => Target?.Required ?? false; }
///
- public override IDictionary Extensions { get => Target.Extensions; set => Target.Extensions = value; }
+ public IDictionary Extensions { get => Target?.Extensions; }
///
- public override void SerializeAsV3(IOpenApiWriter writer)
+ public override IOpenApiRequestBody CopyReferenceAsTargetElementWithOverrides(IOpenApiRequestBody source)
{
- if (!writer.GetSettings().ShouldInlineReference(_reference))
- {
- _reference.SerializeAsV3(writer);
- }
- else
- {
- SerializeInternal(writer, (writer, element) => element.SerializeAsV3(writer));
- }
+ return source is OpenApiRequestBody ? new OpenApiRequestBody(this) : source;
}
-
///
- public override void SerializeAsV31(IOpenApiWriter writer)
+ public override void SerializeAsV2(IOpenApiWriter writer)
{
- if (!writer.GetSettings().ShouldInlineReference(_reference))
+ // doesn't exist in v2
+ }
+ ///
+ public IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer)
+ {
+ if (writer.GetSettings().ShouldInlineReference(Reference))
{
- _reference.SerializeAsV31(writer);
+ return Target.ConvertToBodyParameter(writer);
}
else
{
- SerializeInternal(writer, (writer, element) => element.SerializeAsV31(writer));
+ return new OpenApiParameterReference(Reference.Id, Reference.HostDocument);
}
}
-
- ///
- private void SerializeInternal(IOpenApiWriter writer,
- Action action)
- {
- Utils.CheckArgumentNull(writer);
- action(writer, Target);
- }
-
///
- internal override IOpenApiParameter ConvertToBodyParameter(IOpenApiWriter writer)
+ public IEnumerable ConvertToFormDataParameters(IOpenApiWriter writer)
{
- if (writer.GetSettings().ShouldInlineReference(_reference))
+ if (writer.GetSettings().ShouldInlineReference(Reference))
{
- return Target.ConvertToBodyParameter(writer);
- }
- else
- {
- return new OpenApiParameterReference(_reference.Id, _reference.HostDocument);
+ return Target.ConvertToFormDataParameters(writer);
}
+
+ if (Content == null || !Content.Any())
+ return [];
+
+ return Content.First().Value.Schema.Properties.Select(x => new OpenApiParameterReference(x.Key, Reference.HostDocument));
}
}
}
diff --git a/src/Microsoft.OpenApi/Reader/V2/OpenApiDocumentDeserializer.cs b/src/Microsoft.OpenApi/Reader/V2/OpenApiDocumentDeserializer.cs
index e24c10227..ee0bf0c8f 100644
--- a/src/Microsoft.OpenApi/Reader/V2/OpenApiDocumentDeserializer.cs
+++ b/src/Microsoft.OpenApi/Reader/V2/OpenApiDocumentDeserializer.cs
@@ -7,6 +7,7 @@
using System.Linq;
using Microsoft.OpenApi.Extensions;
using Microsoft.OpenApi.Models;
+using Microsoft.OpenApi.Models.Interfaces;
using Microsoft.OpenApi.Models.References;
using Microsoft.OpenApi.Reader.ParseNodes;
using Microsoft.OpenApi.Services;
@@ -303,8 +304,8 @@ private static bool IsHostValid(string host)
internal class RequestBodyReferenceFixer : OpenApiVisitorBase
{
- private readonly IDictionary _requestBodies;
- public RequestBodyReferenceFixer(IDictionary requestBodies)
+ private readonly IDictionary _requestBodies;
+ public RequestBodyReferenceFixer(IDictionary requestBodies)
{
_requestBodies = requestBodies;
}
@@ -318,15 +319,7 @@ public override void Visit(OpenApiOperation operation)
if (body != null)
{
operation.Parameters.Remove(body);
- operation.RequestBody = new()
- {
- UnresolvedReference = true,
- Reference = new()
- {
- Id = body.Reference.Id,
- Type = ReferenceType.RequestBody
- }
- };
+ operation.RequestBody = new OpenApiRequestBodyReference(body.Reference.Id, body.Reference.HostDocument);
}
}
}
diff --git a/src/Microsoft.OpenApi/Reader/V2/OpenApiOperationDeserializer.cs b/src/Microsoft.OpenApi/Reader/V2/OpenApiOperationDeserializer.cs
index 3fd5743c9..957a02ab7 100644
--- a/src/Microsoft.OpenApi/Reader/V2/OpenApiOperationDeserializer.cs
+++ b/src/Microsoft.OpenApi/Reader/V2/OpenApiOperationDeserializer.cs
@@ -179,7 +179,7 @@ private static OpenApiRequestBody CreateFormBody(ParsingContext context, List s.StartsWith("x-"), (o, p, n, _) => o.AddExtension(p, LoadExtension(p,n))}
};
- public static OpenApiRequestBody LoadRequestBody(ParseNode node, OpenApiDocument hostDocument)
+ public static IOpenApiRequestBody LoadRequestBody(ParseNode node, OpenApiDocument hostDocument)
{
var mapNode = node.CheckMapNode("requestBody");
diff --git a/src/Microsoft.OpenApi/Reader/V31/OpenApiRequestBodyDeserializer.cs b/src/Microsoft.OpenApi/Reader/V31/OpenApiRequestBodyDeserializer.cs
index e26ec20f9..db6792a5f 100644
--- a/src/Microsoft.OpenApi/Reader/V31/OpenApiRequestBodyDeserializer.cs
+++ b/src/Microsoft.OpenApi/Reader/V31/OpenApiRequestBodyDeserializer.cs
@@ -1,5 +1,6 @@
using Microsoft.OpenApi.Extensions;
using Microsoft.OpenApi.Models;
+using Microsoft.OpenApi.Models.Interfaces;
using Microsoft.OpenApi.Models.References;
using Microsoft.OpenApi.Reader.ParseNodes;
@@ -40,7 +41,7 @@ internal static partial class OpenApiV31Deserializer
{s => s.StartsWith("x-"), (o, p, n, _) => o.AddExtension(p, LoadExtension(p,n))}
};
- public static OpenApiRequestBody LoadRequestBody(ParseNode node, OpenApiDocument hostDocument)
+ public static IOpenApiRequestBody LoadRequestBody(ParseNode node, OpenApiDocument hostDocument)
{
var mapNode = node.CheckMapNode("requestBody");
diff --git a/src/Microsoft.OpenApi/Services/CopyReferences.cs b/src/Microsoft.OpenApi/Services/CopyReferences.cs
index 982162442..eadabbaaf 100644
--- a/src/Microsoft.OpenApi/Services/CopyReferences.cs
+++ b/src/Microsoft.OpenApi/Services/CopyReferences.cs
@@ -118,9 +118,9 @@ private void AddRequestBodyToComponents(OpenApiRequestBody requestBody, string r
{
EnsureComponentsExist();
EnsureRequestBodiesExist();
- if (!Components.RequestBodies.ContainsKey(referenceId ?? requestBody.Reference.Id))
+ if (!Components.RequestBodies.ContainsKey(referenceId))
{
- Components.RequestBodies.Add(referenceId ?? requestBody.Reference.Id, requestBody);
+ Components.RequestBodies.Add(referenceId, requestBody);
}
}
private void AddLinkToComponents(OpenApiLink link, string referenceId = null)
@@ -215,7 +215,7 @@ private void EnsureResponsesExist()
private void EnsureRequestBodiesExist()
{
- _target.Components.RequestBodies ??= new Dictionary();
+ _target.Components.RequestBodies ??= new Dictionary();
}
private void EnsureExamplesExist()
diff --git a/src/Microsoft.OpenApi/Services/OpenApiVisitorBase.cs b/src/Microsoft.OpenApi/Services/OpenApiVisitorBase.cs
index 63b065bbd..f118a3f06 100644
--- a/src/Microsoft.OpenApi/Services/OpenApiVisitorBase.cs
+++ b/src/Microsoft.OpenApi/Services/OpenApiVisitorBase.cs
@@ -153,9 +153,9 @@ public virtual void Visit(IOpenApiParameter parameter)
}
///
- /// Visits
+ /// Visits
///
- public virtual void Visit(OpenApiRequestBody requestBody)
+ public virtual void Visit(IOpenApiRequestBody requestBody)
{
}
diff --git a/src/Microsoft.OpenApi/Services/OpenApiWalker.cs b/src/Microsoft.OpenApi/Services/OpenApiWalker.cs
index 66ca7e6fe..b76f33ad9 100644
--- a/src/Microsoft.OpenApi/Services/OpenApiWalker.cs
+++ b/src/Microsoft.OpenApi/Services/OpenApiWalker.cs
@@ -713,9 +713,9 @@ internal void Walk(OpenApiResponse response, bool isComponent = false)
}
///
- /// Visits and child objects
+ /// Visits and child objects
///
- internal void Walk(OpenApiRequestBody requestBody, bool isComponent = false)
+ internal void Walk(IOpenApiRequestBody requestBody, bool isComponent = false)
{
if (requestBody == null)
{
diff --git a/src/Microsoft.OpenApi/Validations/OpenApiValidator.cs b/src/Microsoft.OpenApi/Validations/OpenApiValidator.cs
index 63076ed9d..a5a4885de 100644
--- a/src/Microsoft.OpenApi/Validations/OpenApiValidator.cs
+++ b/src/Microsoft.OpenApi/Validations/OpenApiValidator.cs
@@ -141,7 +141,7 @@ public void AddWarning(OpenApiValidatorWarning warning)
public override void Visit(OpenApiSecurityRequirement securityRequirement) => Validate(securityRequirement);
///
- public override void Visit(OpenApiRequestBody requestBody) => Validate(requestBody);
+ public override void Visit(IOpenApiRequestBody requestBody) => Validate(requestBody);
///
public override void Visit(OpenApiPaths paths) => Validate(paths);
diff --git a/test/Microsoft.OpenApi.Readers.Tests/V2Tests/OpenApiPathItemTests.cs b/test/Microsoft.OpenApi.Readers.Tests/V2Tests/OpenApiPathItemTests.cs
index be19365d5..35ffd15d5 100644
--- a/test/Microsoft.OpenApi.Readers.Tests/V2Tests/OpenApiPathItemTests.cs
+++ b/test/Microsoft.OpenApi.Readers.Tests/V2Tests/OpenApiPathItemTests.cs
@@ -60,7 +60,7 @@ public class OpenApiPathItemTests
}
}
],
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Content =
{
@@ -166,7 +166,7 @@ public class OpenApiPathItemTests
}
}
],
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Content =
{
diff --git a/test/Microsoft.OpenApi.Tests/Models/OpenApiCallbackTests.cs b/test/Microsoft.OpenApi.Tests/Models/OpenApiCallbackTests.cs
index a2ef27222..267e29ede 100644
--- a/test/Microsoft.OpenApi.Tests/Models/OpenApiCallbackTests.cs
+++ b/test/Microsoft.OpenApi.Tests/Models/OpenApiCallbackTests.cs
@@ -28,7 +28,7 @@ public class OpenApiCallbackTests
[OperationType.Post] =
new()
{
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Content =
{
@@ -68,7 +68,7 @@ public class OpenApiCallbackTests
[OperationType.Post] =
new()
{
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Content =
{
diff --git a/test/Microsoft.OpenApi.Tests/Models/OpenApiDocumentTests.cs b/test/Microsoft.OpenApi.Tests/Models/OpenApiDocumentTests.cs
index 19ebca7fb..c333fcdb7 100644
--- a/test/Microsoft.OpenApi.Tests/Models/OpenApiDocumentTests.cs
+++ b/test/Microsoft.OpenApi.Tests/Models/OpenApiDocumentTests.cs
@@ -1171,7 +1171,7 @@ public OpenApiDocumentTests()
{
Description = "Creates a new pet in the store. Duplicates are allowed",
OperationId = "addPet",
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Description = "Pet to add to the store",
Required = true,
diff --git a/test/Microsoft.OpenApi.Tests/Models/OpenApiOperationTests.cs b/test/Microsoft.OpenApi.Tests/Models/OpenApiOperationTests.cs
index 81da044bf..6b3c61417 100644
--- a/test/Microsoft.OpenApi.Tests/Models/OpenApiOperationTests.cs
+++ b/test/Microsoft.OpenApi.Tests/Models/OpenApiOperationTests.cs
@@ -39,7 +39,7 @@ public class OpenApiOperationTests
Name = "parameter2"
}
],
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Description = "description2",
Required = true,
@@ -113,7 +113,7 @@ public class OpenApiOperationTests
Name = "parameter2"
}
],
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Description = "description2",
Required = true,
@@ -191,7 +191,7 @@ public class OpenApiOperationTests
}
}
],
- RequestBody = new()
+ RequestBody = new OpenApiRequestBody()
{
Content =
{
diff --git a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=False.verified.txt b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=False.verified.txt
index a9be81418..716f480fd 100644
--- a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=False.verified.txt
+++ b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=False.verified.txt
@@ -1,3 +1,18 @@
{
- "$ref": "#/components/requestBodies/UserRequest"
+ "description": "User request body",
+ "content": {
+ "application/json": {
+ "schema": {
+ "type": "object",
+ "properties": {
+ "name": {
+ "type": "string"
+ },
+ "email": {
+ "type": "string"
+ }
+ }
+ }
+ }
+ }
}
\ No newline at end of file
diff --git a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=True.verified.txt b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=True.verified.txt
index 04f67afdd..161f80087 100644
--- a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=True.verified.txt
+++ b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.SerializeRequestBodyReferenceAsV31JsonWorks_produceTerseOutput=True.verified.txt
@@ -1 +1 @@
-{"$ref":"#/components/requestBodies/UserRequest"}
\ No newline at end of file
+{"description":"User request body","content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string"},"email":{"type":"string"}}}}}}
\ No newline at end of file
diff --git a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.cs b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.cs
index 0f1d8f634..9bcf15a03 100644
--- a/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.cs
+++ b/test/Microsoft.OpenApi.Tests/Models/References/OpenApiRequestBodyReferenceTests.cs
@@ -145,7 +145,7 @@ public async Task SerializeRequestBodyReferenceAsV31JsonWorks(bool produceTerseO
{
// Arrange
var outputStringWriter = new StringWriter(CultureInfo.InvariantCulture);
- var writer = new OpenApiJsonWriter(outputStringWriter, new OpenApiJsonWriterSettings { Terse = produceTerseOutput });
+ var writer = new OpenApiJsonWriter(outputStringWriter, new OpenApiJsonWriterSettings { Terse = produceTerseOutput, InlineLocalReferences = true });
// Act
_localRequestBodyReference.SerializeAsV31(writer);
diff --git a/test/Microsoft.OpenApi.Tests/PublicApi/PublicApi.approved.txt b/test/Microsoft.OpenApi.Tests/PublicApi/PublicApi.approved.txt
index cf54ef45a..93aef1c4b 100644
--- a/test/Microsoft.OpenApi.Tests/PublicApi/PublicApi.approved.txt
+++ b/test/Microsoft.OpenApi.Tests/PublicApi/PublicApi.approved.txt
@@ -392,6 +392,13 @@ namespace Microsoft.OpenApi.Models.Interfaces
System.Collections.Generic.IList Parameters { get; }
System.Collections.Generic.IList Servers { get; }
}
+ public interface IOpenApiRequestBody : Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiReadOnlyExtensible, Microsoft.OpenApi.Interfaces.IOpenApiSerializable, Microsoft.OpenApi.Models.Interfaces.IOpenApiDescribedElement
+ {
+ System.Collections.Generic.IDictionary Content { get; }
+ bool Required { get; }
+ Microsoft.OpenApi.Models.Interfaces.IOpenApiParameter ConvertToBodyParameter(Microsoft.OpenApi.Writers.IOpenApiWriter writer);
+ System.Collections.Generic.IEnumerable ConvertToFormDataParameters(Microsoft.OpenApi.Writers.IOpenApiWriter writer);
+ }
public interface IOpenApiSummarizedElement : Microsoft.OpenApi.Interfaces.IOpenApiElement
{
string Summary { get; set; }
@@ -432,7 +439,7 @@ namespace Microsoft.OpenApi.Models
public System.Collections.Generic.IDictionary? Links { get; set; }
public System.Collections.Generic.IDictionary? Parameters { get; set; }
public System.Collections.Generic.IDictionary? PathItems { get; set; }
- public System.Collections.Generic.IDictionary? RequestBodies { get; set; }
+ public System.Collections.Generic.IDictionary? RequestBodies { get; set; }
public System.Collections.Generic.IDictionary? Responses { get; set; }
public System.Collections.Generic.IDictionary? Schemas { get; set; }
public System.Collections.Generic.IDictionary? SecuritySchemes { get; set; }
@@ -820,7 +827,7 @@ namespace Microsoft.OpenApi.Models
public Microsoft.OpenApi.Models.OpenApiExternalDocs? ExternalDocs { get; set; }
public string? OperationId { get; set; }
public System.Collections.Generic.IList? Parameters { get; set; }
- public Microsoft.OpenApi.Models.OpenApiRequestBody? RequestBody { get; set; }
+ public Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody? RequestBody { get; set; }
public Microsoft.OpenApi.Models.OpenApiResponses? Responses { get; set; }
public System.Collections.Generic.IList? Security { get; set; }
public System.Collections.Generic.IList? Servers { get; set; }
@@ -891,19 +898,19 @@ namespace Microsoft.OpenApi.Models
public void SerializeAsV3(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
public void SerializeAsV31(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
}
- public class OpenApiRequestBody : Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiExtensible, Microsoft.OpenApi.Interfaces.IOpenApiReferenceable, Microsoft.OpenApi.Interfaces.IOpenApiSerializable
+ public class OpenApiRequestBody : Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiExtensible, Microsoft.OpenApi.Interfaces.IOpenApiReadOnlyExtensible, Microsoft.OpenApi.Interfaces.IOpenApiReferenceable, Microsoft.OpenApi.Interfaces.IOpenApiSerializable, Microsoft.OpenApi.Models.Interfaces.IOpenApiDescribedElement, Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody
{
public OpenApiRequestBody() { }
- public OpenApiRequestBody(Microsoft.OpenApi.Models.OpenApiRequestBody requestBody) { }
- public Microsoft.OpenApi.Models.OpenApiReference Reference { get; set; }
- public bool UnresolvedReference { get; set; }
- public virtual System.Collections.Generic.IDictionary Content { get; set; }
- public virtual string Description { get; set; }
- public virtual System.Collections.Generic.IDictionary Extensions { get; set; }
- public virtual bool Required { get; set; }
+ public OpenApiRequestBody(Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody requestBody) { }
+ public System.Collections.Generic.IDictionary Content { get; set; }
+ public string Description { get; set; }
+ public System.Collections.Generic.IDictionary Extensions { get; set; }
+ public bool Required { get; set; }
+ public Microsoft.OpenApi.Models.Interfaces.IOpenApiParameter ConvertToBodyParameter(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public System.Collections.Generic.IEnumerable ConvertToFormDataParameters(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
public void SerializeAsV2(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
- public virtual void SerializeAsV3(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
- public virtual void SerializeAsV31(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public void SerializeAsV3(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public void SerializeAsV31(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
}
public class OpenApiResponse : Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiExtensible, Microsoft.OpenApi.Interfaces.IOpenApiReferenceable, Microsoft.OpenApi.Interfaces.IOpenApiSerializable
{
@@ -1258,16 +1265,17 @@ namespace Microsoft.OpenApi.Models.References
public override Microsoft.OpenApi.Models.Interfaces.IOpenApiPathItem CopyReferenceAsTargetElementWithOverrides(Microsoft.OpenApi.Models.Interfaces.IOpenApiPathItem source) { }
public override void SerializeAsV2(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
}
- public class OpenApiRequestBodyReference : Microsoft.OpenApi.Models.OpenApiRequestBody, Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiReferenceHolder, Microsoft.OpenApi.Interfaces.IOpenApiReferenceHolder, Microsoft.OpenApi.Interfaces.IOpenApiSerializable
+ public class OpenApiRequestBodyReference : Microsoft.OpenApi.Models.References.BaseOpenApiReferenceHolder, Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiReadOnlyExtensible, Microsoft.OpenApi.Interfaces.IOpenApiSerializable, Microsoft.OpenApi.Models.Interfaces.IOpenApiDescribedElement, Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody
{
public OpenApiRequestBodyReference(string referenceId, Microsoft.OpenApi.Models.OpenApiDocument hostDocument, string externalResource = null) { }
- public Microsoft.OpenApi.Models.OpenApiRequestBody Target { get; }
- public override System.Collections.Generic.IDictionary Content { get; set; }
- public override string Description { get; set; }
- public override System.Collections.Generic.IDictionary Extensions { get; set; }
- public override bool Required { get; set; }
- public override void SerializeAsV3(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
- public override void SerializeAsV31(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public System.Collections.Generic.IDictionary Content { get; }
+ public string Description { get; set; }
+ public System.Collections.Generic.IDictionary Extensions { get; }
+ public bool Required { get; }
+ public Microsoft.OpenApi.Models.Interfaces.IOpenApiParameter ConvertToBodyParameter(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public System.Collections.Generic.IEnumerable ConvertToFormDataParameters(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
+ public override Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody CopyReferenceAsTargetElementWithOverrides(Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody source) { }
+ public override void SerializeAsV2(Microsoft.OpenApi.Writers.IOpenApiWriter writer) { }
}
public class OpenApiResponseReference : Microsoft.OpenApi.Models.OpenApiResponse, Microsoft.OpenApi.Interfaces.IOpenApiElement, Microsoft.OpenApi.Interfaces.IOpenApiReferenceHolder, Microsoft.OpenApi.Interfaces.IOpenApiReferenceHolder, Microsoft.OpenApi.Interfaces.IOpenApiSerializable
{
@@ -1556,6 +1564,7 @@ namespace Microsoft.OpenApi.Services
public virtual void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiLink link) { }
public virtual void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiParameter parameter) { }
public virtual void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiPathItem pathItem) { }
+ public virtual void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody requestBody) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiComponents components) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiContact contact) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiDocument doc) { }
@@ -1567,7 +1576,6 @@ namespace Microsoft.OpenApi.Services
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiOAuthFlow openApiOAuthFlow) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiOperation operation) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiPaths paths) { }
- public virtual void Visit(Microsoft.OpenApi.Models.OpenApiRequestBody requestBody) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiResponse response) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiResponses response) { }
public virtual void Visit(Microsoft.OpenApi.Models.OpenApiSchema schema) { }
@@ -1655,6 +1663,7 @@ namespace Microsoft.OpenApi.Validations
public override void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiLink link) { }
public override void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiParameter parameter) { }
public override void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiPathItem pathItem) { }
+ public override void Visit(Microsoft.OpenApi.Models.Interfaces.IOpenApiRequestBody requestBody) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiComponents components) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiContact contact) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiDocument doc) { }
@@ -1666,7 +1675,6 @@ namespace Microsoft.OpenApi.Validations
public override void Visit(Microsoft.OpenApi.Models.OpenApiOAuthFlow openApiOAuthFlow) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiOperation operation) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiPaths paths) { }
- public override void Visit(Microsoft.OpenApi.Models.OpenApiRequestBody requestBody) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiResponse response) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiResponses response) { }
public override void Visit(Microsoft.OpenApi.Models.OpenApiSchema schema) { }
diff --git a/test/Microsoft.OpenApi.Tests/Visitors/InheritanceTests.cs b/test/Microsoft.OpenApi.Tests/Visitors/InheritanceTests.cs
index fd65e7dd4..49595a1be 100644
--- a/test/Microsoft.OpenApi.Tests/Visitors/InheritanceTests.cs
+++ b/test/Microsoft.OpenApi.Tests/Visitors/InheritanceTests.cs
@@ -32,7 +32,7 @@ public void ExpectedVirtualsInvolved()
visitor.Visit(default(OpenApiOperation));
visitor.Visit(default(IList));
visitor.Visit(default(IOpenApiParameter));
- visitor.Visit(default(OpenApiRequestBody));
+ visitor.Visit(default(IOpenApiRequestBody));
visitor.Visit(default(IDictionary));
visitor.Visit(default(IDictionary));
visitor.Visit(default(OpenApiResponse));
@@ -166,7 +166,7 @@ public override void Visit(IOpenApiParameter parameter)
base.Visit(parameter);
}
- public override void Visit(OpenApiRequestBody requestBody)
+ public override void Visit(IOpenApiRequestBody requestBody)
{
EncodeCall();
base.Visit(requestBody);