44using System ;
55using Microsoft . OpenApi . Extensions ;
66using Microsoft . OpenApi . Interfaces ;
7+ using Microsoft . OpenApi . Models . Interfaces ;
78using Microsoft . OpenApi . Writers ;
89
910namespace Microsoft . OpenApi . Models
1011{
1112 /// <summary>
1213 /// A simple object to allow referencing other components in the specification, internally and externally.
1314 /// </summary>
14- public class OpenApiReference : IOpenApiSerializable
15+ public class OpenApiReference : IOpenApiSerializable , IOpenApiDescribedElement , IOpenApiSummarizedElement
1516 {
1617 /// <summary>
1718 /// A short summary which by default SHOULD override that of the referenced component.
@@ -32,13 +33,13 @@ public class OpenApiReference : IOpenApiSerializable
3233 /// 1. a absolute/relative file path, for example: ../commons/pet.json
3334 /// 2. a Url, for example: http://localhost/pet.json
3435 /// </summary>
35- public string ExternalResource { get ; set ; }
36+ public string ExternalResource { get ; init ; }
3637
3738 /// <summary>
3839 /// The element type referenced.
3940 /// </summary>
4041 /// <remarks>This must be present if <see cref="ExternalResource"/> is not present.</remarks>
41- public ReferenceType ? Type { get ; set ; }
42+ public ReferenceType ? Type { get ; init ; }
4243
4344 /// <summary>
4445 /// The identifier of the reusable component of one particular ReferenceType.
@@ -47,7 +48,7 @@ public class OpenApiReference : IOpenApiSerializable
4748 /// If ExternalResource is not present, this is the name of the component without the reference type name.
4849 /// For example, if the reference is '#/components/schemas/componentName', the Id is 'componentName'.
4950 /// </summary>
50- public string Id { get ; set ; }
51+ public string Id { get ; init ; }
5152
5253 /// <summary>
5354 /// Gets a flag indicating whether this reference is an external reference.
@@ -62,12 +63,13 @@ public class OpenApiReference : IOpenApiSerializable
6263 /// <summary>
6364 /// Gets a flag indicating whether a file is a valid OpenAPI document or a fragment
6465 /// </summary>
65- public bool IsFragment = false ;
66+ public bool IsFragment { get ; init ; }
6667
68+ private OpenApiDocument hostDocument ;
6769 /// <summary>
6870 /// The OpenApiDocument that is hosting the OpenApiReference instance. This is used to enable dereferencing the reference.
6971 /// </summary>
70- public OpenApiDocument HostDocument { get ; set ; }
72+ public OpenApiDocument HostDocument { get => hostDocument ; init => hostDocument = value ; }
7173
7274 /// <summary>
7375 /// Gets the full reference string for v3.0.
@@ -145,12 +147,13 @@ public OpenApiReference() { }
145147 /// </summary>
146148 public OpenApiReference ( OpenApiReference reference )
147149 {
148- Summary = reference ? . Summary ;
149- Description = reference ? . Description ;
150- ExternalResource = reference ? . ExternalResource ;
151- Type = reference ? . Type ;
152- Id = reference ? . Id ;
153- HostDocument = reference ? . HostDocument ;
150+ Utils . CheckArgumentNull ( reference ) ;
151+ Summary = reference . Summary ;
152+ Description = reference . Description ;
153+ ExternalResource = reference . ExternalResource ;
154+ Type = reference . Type ;
155+ Id = reference . Id ;
156+ HostDocument = reference . HostDocument ;
154157 }
155158
156159 /// <summary>
@@ -276,5 +279,16 @@ private string GetReferenceTypeNameAsV2(ReferenceType type)
276279 // to indicate that the reference is not pointing to any object.
277280 } ;
278281 }
282+
283+ /// <summary>
284+ /// Sets the host document after deserialization or before serialization.
285+ /// This method is internal on purpose to avoid consumers mutating the host document.
286+ /// </summary>
287+ /// <param name="currentDocument">Host document to set if none is present</param>
288+ internal void EnsureHostDocumentIsSet ( OpenApiDocument currentDocument )
289+ {
290+ Utils . CheckArgumentNull ( currentDocument ) ;
291+ hostDocument ??= currentDocument ;
292+ }
279293 }
280294}
0 commit comments