json_model/attribute/
const_value.rs

1use super::{AllowedType, Attribute};
2use crate::definition::Type;
3use crate::error::{Error, ValidationError};
4use crate::validator::{Context, DocumentPath, State};
5
6use std::collections::HashSet;
7
8use serde_json;
9
10#[derive(Debug)]
11pub struct ConstValue {
12    name: String,
13    value: serde_json::Value,
14}
15
16impl ConstValue {
17    pub fn new(path: DocumentPath, ctx: &Context) -> Result<Self, Error> {
18        let obj = ctx.raw_definition();
19
20        match Type::new(obj, path.clone())? {
21            Type::Const => (),
22            typ => return Err(Error::ForbiddenType { path, typ }),
23        };
24
25        let value = match obj.get(ctx.name().as_str()) {
26            Some(value) => value.clone(),
27            None => {
28                return Err(Error::MissingAttribute {
29                    path,
30                    attr: ctx.name(),
31                })
32            }
33        };
34
35        Ok(ConstValue {
36            name: ctx.name(),
37            value,
38        })
39    }
40
41    pub fn allowed_types() -> HashSet<AllowedType> {
42        let mut set = HashSet::<AllowedType>::new();
43        set.insert(AllowedType::new(Type::Const, true));
44        set
45    }
46
47    pub fn build(
48        _: &mut State,
49        path: DocumentPath,
50        ctx: &Context,
51    ) -> Result<Box<Attribute>, Error> {
52        Ok(Box::new(ConstValue::new(path, ctx)?))
53    }
54}
55
56impl Attribute for ConstValue {
57    fn validate(
58        &self,
59        _: &State,
60        path: Vec<String>,
61        input: &serde_json::Value,
62    ) -> Result<(), ValidationError> {
63        if self.value != *input {
64            return Err(ValidationError::Failure {
65                rule: "value".to_string(),
66                path: path,
67                message: format!("Value must be {:?}.", self.value),
68            });
69        }
70        Ok(())
71    }
72}