jspg checkpoint
This commit is contained in:
@ -1,5 +1,7 @@
|
||||
use std::collections::HashMap;
|
||||
|
||||
use crate::database::object::{is_primitive_type, SchemaTypeOrArray};
|
||||
use crate::database::schema::Schema;
|
||||
use crate::validator::context::ValidationContext;
|
||||
use crate::validator::error::ValidationError;
|
||||
use crate::validator::result::ValidationResult;
|
||||
@ -16,6 +18,49 @@ impl<'a> ValidationContext<'a> {
|
||||
Ok(true)
|
||||
}
|
||||
|
||||
pub(crate) fn schema_expects_primitive(&self, schema: &Schema, primitive: &str) -> bool {
|
||||
match &schema.type_ {
|
||||
None => true, // Any type is allowed
|
||||
Some(SchemaTypeOrArray::Single(t)) => {
|
||||
if t == primitive {
|
||||
true
|
||||
} else if !is_primitive_type(t) {
|
||||
if primitive == "object" {
|
||||
true
|
||||
} else {
|
||||
// Custom type - resolve recursively
|
||||
if let Some(parent) = self.db.schemas.get(t) {
|
||||
self.schema_expects_primitive(parent, primitive)
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
Some(SchemaTypeOrArray::Multiple(types)) => {
|
||||
types.iter().any(|t| {
|
||||
if t == primitive {
|
||||
true
|
||||
} else if !is_primitive_type(t) {
|
||||
if primitive == "object" {
|
||||
true
|
||||
} else {
|
||||
if let Some(parent) = self.db.schemas.get(t) {
|
||||
self.schema_expects_primitive(parent, primitive)
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
} else {
|
||||
false
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn validate_strictness(
|
||||
&self,
|
||||
result: &mut ValidationResult,
|
||||
@ -24,38 +69,18 @@ impl<'a> ValidationContext<'a> {
|
||||
return Ok(true);
|
||||
}
|
||||
|
||||
if let Some(obj) = self.instance.as_object() {
|
||||
for key in obj.keys() {
|
||||
if !result.evaluated_keys.contains(key) && !self.overrides.contains(key) {
|
||||
result.errors.push(ValidationError {
|
||||
code: "STRICT_PROPERTY_VIOLATION".to_string(),
|
||||
values: Some(HashMap::from([
|
||||
("property_name".to_string(), key.to_string()),
|
||||
])),
|
||||
path: self.join_path(key),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(arr) = self.instance.as_array() {
|
||||
for i in 0..arr.len() {
|
||||
if !result.evaluated_indices.contains(&i) {
|
||||
let mut item_path = self.join_path(&i.to_string());
|
||||
if let Some(child_instance) = arr.get(i) {
|
||||
if let Some(obj) = child_instance.as_object() {
|
||||
if let Some(id_str) = obj.get("id").and_then(|v| v.as_str()) {
|
||||
item_path = self.join_path(id_str);
|
||||
}
|
||||
}
|
||||
if self.schema_expects_primitive(self.schema, "object") || self.schema_expects_primitive(self.schema, "dict") {
|
||||
if let Some(obj) = self.instance.as_object() {
|
||||
for key in obj.keys() {
|
||||
if !result.evaluated_keys.contains(key) && !self.overrides.contains(key) {
|
||||
result.errors.push(ValidationError {
|
||||
code: "STRICT_PROPERTY_VIOLATION".to_string(),
|
||||
values: Some(HashMap::from([
|
||||
("property_name".to_string(), key.to_string()),
|
||||
])),
|
||||
path: self.join_path(key),
|
||||
});
|
||||
}
|
||||
result.errors.push(ValidationError {
|
||||
code: "STRICT_ITEM_VIOLATION".to_string(),
|
||||
values: Some(HashMap::from([
|
||||
("index".to_string(), i.to_string()),
|
||||
])),
|
||||
path: item_path,
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user