diff --git a/Assets/VRM/UniJSON/Editor/Tests/Json/ValidatorTests.cs b/Assets/VRM/UniJSON/Editor/Tests/Json/ValidatorTests.cs index d6a475251..7165a3d37 100644 --- a/Assets/VRM/UniJSON/Editor/Tests/Json/ValidatorTests.cs +++ b/Assets/VRM/UniJSON/Editor/Tests/Json/ValidatorTests.cs @@ -199,6 +199,41 @@ namespace UniJSON Assert.True(c.IsEmpty()); } + class NotRequired + { + [JsonSchema(Minimum = 1)] + public int Value; + } + + [Test] + public void ObjectValidatorForNotRequired() + { + { + var c = new JsonSchemaValidationContext("test") + { + EnableDiagnosisForNotRequiredFields = false, // Default behaviour + }; + + var s = JsonSchema.FromType(); + // An error is not returned because Value is not 'Required' and the diagnosis is not enabled + Assert.Null(s.Validator.Validate(c, new Hoge { Value = 0 })); + + Assert.True(c.IsEmpty()); + } + + { + var c = new JsonSchemaValidationContext("test") + { + EnableDiagnosisForNotRequiredFields = true, + }; + + var s = JsonSchema.FromType(); + Assert.NotNull(s.Validator.Validate(c, new Hoge { Value = 0 })); + + Assert.True(c.IsEmpty()); + } + } + [Test] public void DictionaryValidator() { diff --git a/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/IJsonSchemaValidator.cs b/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/IJsonSchemaValidator.cs index 6c500e0d3..9a53769d8 100644 --- a/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/IJsonSchemaValidator.cs +++ b/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/IJsonSchemaValidator.cs @@ -7,6 +7,8 @@ namespace UniJSON { Stack m_stack = new Stack(); + public bool EnableDiagnosisForNotRequiredFields = false; + public JsonSchemaValidationContext(object o) { Push(o.GetType().Name); diff --git a/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/JsonObjectValidator.cs b/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/JsonObjectValidator.cs index ae943ae65..a4dd1e8e6 100644 --- a/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/JsonObjectValidator.cs +++ b/Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/JsonObjectValidator.cs @@ -28,11 +28,11 @@ namespace UniJSON get; set; } - List m_required = new List(); + HashSet m_required = new HashSet(); /// /// http://json-schema.org/latest/json-schema-validation.html#rfc.section.6.5.3 /// - public List Required + public HashSet Required { get { return m_required; } } @@ -302,7 +302,7 @@ namespace UniJSON { class ObjectValidator { - delegate JsonSchemaValidationException FieldValidator(IJsonSchemaValidator v, + delegate JsonSchemaValidationException FieldValidator(IJsonSchemaValidator v, JsonSchemaValidationContext c, T o); Dictionary m_validators = new Dictionary(); @@ -341,32 +341,38 @@ namespace UniJSON } } - public JsonSchemaValidationException Validate(List required, Dictionary properties, + public JsonSchemaValidationException Validate( + HashSet required, + Dictionary properties, JsonSchemaValidationContext c, T o) { - foreach (var x in required) + foreach (var kv in properties) { - JsonSchema s; - if(properties.TryGetValue(x, out s)) + var fieldName = kv.Key; + var schema = kv.Value; + + FieldValidator fv; + if (m_validators.TryGetValue(fieldName, out fv)) { - FieldValidator fv; - if (m_validators.TryGetValue(x, out fv)) + var ex = fv(schema.Validator, c, o); + if (ex != null) { - var ex = fv(s.Validator, c, o); - if (ex != null) + if (required.Contains(fieldName) // required fields must be checked + || c.EnableDiagnosisForNotRequiredFields) { return ex; } } } } + return null; } } static ObjectValidator s_validator; - public static JsonSchemaValidationException Validate(List required, + public static JsonSchemaValidationException Validate(HashSet required, Dictionary properties, JsonSchemaValidationContext c, T o) { @@ -390,16 +396,7 @@ namespace UniJSON return new JsonSchemaValidationException(c, "no properties"); } - if (Required != null) - { - var ex = GenericValidator.Validate(Required, Properties, c, o); - if (ex != null) - { - return ex; - } - } - - return null; + return GenericValidator.Validate(Required, Properties, c, o); } static class GenericSerializer @@ -511,7 +508,7 @@ namespace UniJSON GenericSerializer.Serialize(this, f, c, value); } - static class GenericDeserializer + static class GenericDeserializer where S : IListTreeItem, IValue { delegate T Deserializer(ListTreeNode src); @@ -596,7 +593,7 @@ namespace UniJSON } } - public void Deserialize(ListTreeNode src, ref U dst) + public void Deserialize(ListTreeNode src, ref U dst) where T : IListTreeItem, IValue { GenericDeserializer.Deserialize(src, ref dst, Properties);