1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
use schema::validate_schema_object;
use schemars::{schema::RootSchema, schema_for, JsonSchema};
use serde::Serialize;
use serde_json::Value;
use thiserror::Error;
mod schema;
#[derive(Error, Debug)]
pub enum Error {
#[error("error serializing item")]
SerializationError(#[from] serde_json::Error),
#[error("invalid schema at {path}: {details}")]
InvalidSchema { path: String, details: String },
#[error("{value} did not conform to the schema at {path}: {details}")]
InvalidValue {
path: String,
value: Value,
details: String,
},
}
pub fn validate<T: JsonSchema + Serialize>(item: &T) -> Result<(), Error> {
let value = serde_json::to_value(item)?;
let RootSchema {
schema,
definitions,
..
} = schema_for!(T);
validate_schema_object("$", &schema, &definitions, &value)
}
pub fn validate_with_output<T: JsonSchema + Serialize>(item: &T) -> Result<(), String> {
validate(item).map_err(|e| {
let schema = schema_for!(T);
format!(
"error: {e}\nschema: {}\nvalue: {}",
serde_json::to_string_pretty(&schema).unwrap(),
serde_json::to_string_pretty(&item).unwrap(),
)
})
}