Skip to content

Commit ac66756

Browse files
fix: read (Exclusive)Maximum and (Exclusive)Minimum values as strings and write their raw values during serialization (#2309)
* fix: read (Exclusive)Maximum and (Exclusive)Minimum values as strings and write their raw values * chore: clean up tests * chore: update public API * chore: remove bang operators for consistency * chore: remove depracated class and tests
1 parent 4bb924a commit ac66756

16 files changed

+92
-147
lines changed

src/Microsoft.OpenApi/Models/Interfaces/IOpenApiSchema.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -56,12 +56,12 @@ public interface IOpenApiSchema : IOpenApiDescribedElement, IOpenApiReadOnlyExte
5656
/// <summary>
5757
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00
5858
/// </summary>
59-
public decimal? ExclusiveMaximum { get; }
59+
public string? ExclusiveMaximum { get; }
6060

6161
/// <summary>
6262
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00
6363
/// </summary>
64-
public decimal? ExclusiveMinimum { get; }
64+
public string? ExclusiveMinimum { get; }
6565

6666
/// <summary>
6767
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00
@@ -84,12 +84,12 @@ public interface IOpenApiSchema : IOpenApiDescribedElement, IOpenApiReadOnlyExte
8484
/// <summary>
8585
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00
8686
/// </summary>
87-
public decimal? Maximum { get; }
87+
public string? Maximum { get; }
8888

8989
/// <summary>
9090
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00
9191
/// </summary>
92-
public decimal? Minimum { get; }
92+
public string? Minimum { get; }
9393

9494
/// <summary>
9595
/// Follow JSON Schema definition: https://tools.ietf.org/html/draft-fge-json-schema-validation-00

src/Microsoft.OpenApi/Models/OpenApiSchema.cs

+28-23
Original file line numberDiff line numberDiff line change
@@ -44,17 +44,17 @@ public class OpenApiSchema : IOpenApiExtensible, IOpenApiSchema
4444
/// <inheritdoc />
4545
public IDictionary<string, IOpenApiSchema>? Definitions { get; set; }
4646

47-
private decimal? _exclusiveMaximum;
47+
private string? _exclusiveMaximum;
4848
/// <inheritdoc />
49-
public decimal? ExclusiveMaximum
49+
public string? ExclusiveMaximum
5050
{
5151
get
5252
{
53-
if (_exclusiveMaximum.HasValue)
53+
if (!string.IsNullOrEmpty(_exclusiveMaximum))
5454
{
5555
return _exclusiveMaximum;
5656
}
57-
if (IsExclusiveMaximum == true && _maximum.HasValue)
57+
if (IsExclusiveMaximum == true && !string.IsNullOrEmpty(_maximum))
5858
{
5959
return _maximum;
6060
}
@@ -73,17 +73,17 @@ public decimal? ExclusiveMaximum
7373
/// DO NOT CHANGE THE VISIBILITY OF THIS PROPERTY TO PUBLIC
7474
internal bool? IsExclusiveMaximum { get; set; }
7575

76-
private decimal? _exclusiveMinimum;
76+
private string? _exclusiveMinimum;
7777
/// <inheritdoc />
78-
public decimal? ExclusiveMinimum
78+
public string? ExclusiveMinimum
7979
{
8080
get
8181
{
82-
if (_exclusiveMinimum.HasValue)
82+
if (!string.IsNullOrEmpty(_exclusiveMinimum))
8383
{
8484
return _exclusiveMinimum;
8585
}
86-
if (IsExclusiveMinimum == true && _minimum.HasValue)
86+
if (IsExclusiveMinimum == true && !string.IsNullOrEmpty(_minimum))
8787
{
8888
return _minimum;
8989
}
@@ -114,9 +114,9 @@ public decimal? ExclusiveMinimum
114114
/// <inheritdoc />
115115
public string? Description { get; set; }
116116

117-
private decimal? _maximum;
117+
private string? _maximum;
118118
/// <inheritdoc />
119-
public decimal? Maximum
119+
public string? Maximum
120120
{
121121
get
122122
{
@@ -132,10 +132,10 @@ public decimal? Maximum
132132
}
133133
}
134134

135-
private decimal? _minimum;
135+
private string? _minimum;
136136

137137
/// <inheritdoc />
138-
public decimal? Minimum
138+
public string? Minimum
139139
{
140140
get
141141
{
@@ -334,38 +334,43 @@ public void SerializeAsV3(IOpenApiWriter writer)
334334
SerializeInternal(writer, OpenApiSpecVersion.OpenApi3_0, (writer, element) => element.SerializeAsV3(writer));
335335
}
336336

337-
private static void SerializeBounds(IOpenApiWriter writer, OpenApiSpecVersion version, string propertyName, string exclusivePropertyName, string isExclusivePropertyName, decimal? value, decimal? exclusiveValue, bool? isExclusiveValue)
337+
private static void SerializeBounds(IOpenApiWriter writer, OpenApiSpecVersion version, string propertyName, string exclusivePropertyName, string isExclusivePropertyName, string? value, string? exclusiveValue, bool? isExclusiveValue)
338338
{
339339
if (version >= OpenApiSpecVersion.OpenApi3_1)
340340
{
341-
if (exclusiveValue.HasValue)
341+
if (!string.IsNullOrEmpty(exclusiveValue) && exclusiveValue is not null)
342342
{
343343
// was explicitly set in the document or object model
344-
writer.WriteProperty(exclusivePropertyName, exclusiveValue.Value);
344+
writer.WritePropertyName(exclusivePropertyName);
345+
writer.WriteRaw(exclusiveValue);
345346
}
346-
else if (isExclusiveValue == true && value.HasValue)
347+
else if (isExclusiveValue == true && !string.IsNullOrEmpty(value) && value is not null)
347348
{
348349
// came from parsing an old document
349-
writer.WriteProperty(exclusivePropertyName, value);
350+
writer.WritePropertyName(exclusivePropertyName);
351+
writer.WriteRaw(value);
350352
}
351-
else if (value.HasValue)
353+
else if (!string.IsNullOrEmpty(value) && value is not null)
352354
{
353355
// was explicitly set in the document or object model
354-
writer.WriteProperty(propertyName, value);
356+
writer.WritePropertyName(propertyName);
357+
writer.WriteRaw(value);
355358
}
356359
}
357360
else
358361
{
359-
if (exclusiveValue.HasValue)
362+
if (!string.IsNullOrEmpty(exclusiveValue) && exclusiveValue is not null)
360363
{
361364
// was explicitly set in a new document being downcast or object model
362-
writer.WriteProperty(propertyName, exclusiveValue.Value);
365+
writer.WritePropertyName(propertyName);
366+
writer.WriteRaw(exclusiveValue);
363367
writer.WriteProperty(isExclusivePropertyName, true);
364368
}
365-
else if (value.HasValue)
369+
else if (!string.IsNullOrEmpty(value) && value is not null)
366370
{
367371
// came from parsing an old document, we're just mirroring the information
368-
writer.WriteProperty(propertyName, value);
372+
writer.WritePropertyName(propertyName);
373+
writer.WriteRaw(value);
369374
if (isExclusiveValue.HasValue)
370375
writer.WriteProperty(isExclusivePropertyName, isExclusiveValue.Value);
371376
}

src/Microsoft.OpenApi/Models/References/OpenApiSchemaReference.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -60,19 +60,19 @@ public string? Description
6060
/// <inheritdoc/>
6161
public IDictionary<string, IOpenApiSchema>? Definitions { get => Target?.Definitions; }
6262
/// <inheritdoc/>
63-
public decimal? ExclusiveMaximum { get => Target?.ExclusiveMaximum; }
63+
public string? ExclusiveMaximum { get => Target?.ExclusiveMaximum; }
6464
/// <inheritdoc/>
65-
public decimal? ExclusiveMinimum { get => Target?.ExclusiveMinimum; }
65+
public string? ExclusiveMinimum { get => Target?.ExclusiveMinimum; }
6666
/// <inheritdoc/>
6767
public JsonSchemaType? Type { get => Target?.Type; }
6868
/// <inheritdoc/>
6969
public string? Const { get => Target?.Const; }
7070
/// <inheritdoc/>
7171
public string? Format { get => Target?.Format; }
7272
/// <inheritdoc/>
73-
public decimal? Maximum { get => Target?.Maximum; }
73+
public string? Maximum { get => Target?.Maximum; }
7474
/// <inheritdoc/>
75-
public decimal? Minimum { get => Target?.Minimum; }
75+
public string? Minimum { get => Target?.Minimum; }
7676
/// <inheritdoc/>
7777
public int? MaxLength { get => Target?.MaxLength; }
7878
/// <inheritdoc/>

src/Microsoft.OpenApi/Reader/ParseNodes/ParserHelper.cs

-35
This file was deleted.

src/Microsoft.OpenApi/Reader/V2/OpenApiHeaderDeserializer.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -62,9 +62,9 @@ internal static partial class OpenApiV2Deserializer
6262
(o, n, _) =>
6363
{
6464
var max = n.GetScalarValue();
65-
if (max != null)
65+
if (!string.IsNullOrEmpty(max))
6666
{
67-
GetOrCreateSchema(o).Maximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(max, decimal.MaxValue);
67+
GetOrCreateSchema(o).Maximum = max;
6868
}
6969
}
7070
},
@@ -77,9 +77,9 @@ internal static partial class OpenApiV2Deserializer
7777
(o, n, _) =>
7878
{
7979
var min = n.GetScalarValue();
80-
if (min != null)
80+
if (!string.IsNullOrEmpty(min))
8181
{
82-
GetOrCreateSchema(o).Minimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(min, decimal.MinValue);
82+
GetOrCreateSchema(o).Minimum = min;
8383
}
8484
}
8585
},

src/Microsoft.OpenApi/Reader/V2/OpenApiParameterDeserializer.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -106,9 +106,9 @@ internal static partial class OpenApiV2Deserializer
106106
(o, n, t) =>
107107
{
108108
var min = n.GetScalarValue();
109-
if (min != null)
109+
if (!string.IsNullOrEmpty(min))
110110
{
111-
GetOrCreateSchema(o).Minimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(min, decimal.MinValue);
111+
GetOrCreateSchema(o).Minimum = min;
112112
}
113113
}
114114
},
@@ -117,9 +117,9 @@ internal static partial class OpenApiV2Deserializer
117117
(o, n, t) =>
118118
{
119119
var max = n.GetScalarValue();
120-
if (max != null)
120+
if (!string.IsNullOrEmpty(max))
121121
{
122-
GetOrCreateSchema(o).Maximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(max, decimal.MaxValue);
122+
GetOrCreateSchema(o).Maximum = max;
123123
}
124124
}
125125
},

src/Microsoft.OpenApi/Reader/V2/OpenApiSchemaDeserializer.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,9 @@ internal static partial class OpenApiV2Deserializer
4141
(o, n,_) =>
4242
{
4343
var max = n.GetScalarValue();
44-
if (max != null)
44+
if (!string.IsNullOrEmpty(max))
4545
{
46-
o.Maximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(max, decimal.MaxValue);
46+
o.Maximum = max;
4747
}
4848
}
4949
},
@@ -56,9 +56,9 @@ internal static partial class OpenApiV2Deserializer
5656
(o, n, _) =>
5757
{
5858
var min = n.GetScalarValue();
59-
if (min != null)
59+
if (!string.IsNullOrEmpty(min))
6060
{
61-
o.Minimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(min, decimal.MinValue);
61+
o.Minimum = min;
6262
}
6363
}
6464
},

src/Microsoft.OpenApi/Reader/V3/OpenApiSchemaDeserializer.cs

+5-5
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,9 @@ internal static partial class OpenApiV3Deserializer
4141
(o, n,_) =>
4242
{
4343
var max = n.GetScalarValue();
44-
if (max != null)
44+
if (!string.IsNullOrEmpty(max))
4545
{
46-
o.Maximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(max, decimal.MaxValue);
46+
o.Maximum = max;
4747
}
4848
}
4949
},
@@ -52,13 +52,13 @@ internal static partial class OpenApiV3Deserializer
5252
(o, n, _) => o.IsExclusiveMaximum = bool.Parse(n.GetScalarValue())
5353
},
5454
{
55-
"minimum",
55+
"minimum",
5656
(o, n, _) =>
5757
{
5858
var min = n.GetScalarValue();
59-
if (min != null)
59+
if (!string.IsNullOrEmpty(min))
6060
{
61-
o.Minimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(min, decimal.MinValue);
61+
o.Minimum = min;
6262
}
6363
}
6464
},

src/Microsoft.OpenApi/Reader/V31/OpenApiSchemaDeserializer.cs

+6-6
Original file line numberDiff line numberDiff line change
@@ -65,30 +65,30 @@ internal static partial class OpenApiV31Deserializer
6565
(o, n,_) =>
6666
{
6767
var max = n.GetScalarValue();
68-
if (max != null)
68+
if (!string.IsNullOrEmpty(max))
6969
{
70-
o.Maximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(max, decimal.MaxValue);
70+
o.Maximum = max;
7171
}
7272
}
7373
},
7474
{
7575
"exclusiveMaximum",
76-
(o, n, _) => o.ExclusiveMaximum = ParserHelper.ParseDecimalWithFallbackOnOverflow(n.GetScalarValue(), decimal.MaxValue)
76+
(o, n, _) => o.ExclusiveMaximum = n.GetScalarValue()
7777
},
7878
{
7979
"minimum",
8080
(o, n, _) =>
8181
{
8282
var min = n.GetScalarValue();
83-
if (min != null)
83+
if (!string.IsNullOrEmpty(min))
8484
{
85-
o.Minimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(min, decimal.MinValue);
85+
o.Minimum = min;
8686
}
8787
}
8888
},
8989
{
9090
"exclusiveMinimum",
91-
(o, n, _) => o.ExclusiveMinimum = ParserHelper.ParseDecimalWithFallbackOnOverflow(n.GetScalarValue(), decimal.MaxValue)
91+
(o, n, _) => o.ExclusiveMinimum = n.GetScalarValue()
9292
},
9393
{
9494
"maxLength",

test/Microsoft.OpenApi.Readers.Tests/ParseNodes/ParserHelperTests.cs

-25
This file was deleted.

test/Microsoft.OpenApi.Readers.Tests/V2Tests/OpenApiDocumentTests.cs

+2-2
Original file line numberDiff line numberDiff line change
@@ -62,8 +62,8 @@ public void ParseDocumentWithDifferentCultureShouldSucceed(string culture)
6262
var expectedPropertySchema = new OpenApiSchema()
6363
{
6464
Type = JsonSchemaType.Number,
65-
Minimum = (decimal)100.54,
66-
ExclusiveMaximum = (decimal)60000000.35,
65+
Minimum = "100.54",
66+
ExclusiveMaximum = "60000000.35",
6767
};
6868

6969
Assert.Equivalent(expectedPropertySchema, samplePropertySchema);

0 commit comments

Comments
 (0)