Crate magnet_schema [−] [src]
Magnet, a JSON/BSON schema generator
These two related crates, magnet_schema
and magnet_derive
define
a trait, BsonSchema
, and a proc-macro derive for the same trait,
which allows types to easily implement JSON schema validation for
use with MongoDB.
The trait defines a single function, bson_schema()
, that returns
a BSON Document
describing the validation schema of the type based
on its fields (for struct
s and tuples), variants (for enum
s), or
elements/entries (for array- and map-like types).
The types are expected to be serialized and deserialized using Serde,
and generally Magnet will try very hard to respect #[serde(...)]
annotations as faithfully as possible, but no Serialize + Deserialize
trait bounds are enforced on the types as this is not strictly necessary.
Usage Example
#[macro_use] extern crate bson; #[macro_use] extern crate magnet_derive; extern crate magnet_schema; use std::collections::HashSet; use magnet_schema::BsonSchema; #[derive(BsonSchema)] struct Contact { name: String, nicknames: HashSet<String>, age: usize, email: Option<String>, } fn main() { let schema_doc = Contact::bson_schema(); println!("{:#?}", schema_doc); }
Custom Attributes
-
#[magnet(rename = "new_name")]
: applied to astruct
field or anenum
variant, it will rename it to the provided new name when generating the JSON schema. This attribute overrides#[serde(rename = "...")]
(in the generated JSON schema only!) if it is present on the same field. -
#[serde(rename = "new_name")]
: Magnet will respect Serde's field/variant renaming attribute by default, if Magnet's ownrename
is not present. -
#[serde(rename_all = "rename_rule")]
: it will also respect Serde'srename_all
rule if Magnet's ownrename
attribute is not specified.
Development Roadmap
-
[x]
DefineBsonSchema
trait -
[x]
impl BsonSchema
for most primitives/std::
types -
[x]
Cargofeature
s for implementingBsonSchema
for "atomic" types in foreign crates, for instance,url::Url
anduuid::Uuid
. -
[x]
#[derive(BsonSchema)]
on regular, named-field structs -
[x]
#[derive(BsonSchema)]
on newtype structs -
[x]
#[derive(BsonSchema)]
on tuple structs -
[x]
#[derive(BsonSchema)]
on unit structs -
[ ]
#[derive(BsonSchema)]
on enums-
[x]
unit variants -
[ ]
newtype variants-
[x]
newtype variants around structs and maps -
[ ]
newtype variants around inner, transitiveenum
s
-
-
[x]
tuple variants -
[x]
struct variants -
[x]
respect Serde tagging conventions: external/internal/adjacent
-
-
[x]
Respect more#[serde(...)]
attributes, for example:rename
,rename_all
-
[ ]
Respect more#[serde(...)]
attributes, for example:default
,skip
,skip_serializing
,skip_deserializing
-
[ ]
Handle generic types in proc-macro derive -
[ ]
Standard (non-MongoDB-specific) JSON schema support (approach?) -
[ ]
UNIT TESTS!!! -
[ ]
DOCUMENTATION FOR ATTRIBUTES!!! -
[ ]
impl BsonSchema
for more esoteric primitives/standard types such as specialization of[u8]
/Vec<u8>
as binary, adding a validation regex"pattern"
toPath
andPathBuf
, etc. -
[ ]
Add our own attributes-
[x]
magnet(rename = "...")
— renames the field or variant to the name specified as the value of therename
attribute -
[ ]
magnet(regex = "foo?|[ba]r{3,6}")
— custom validation; implies"type": "string"
. Patterns are implicitly enclosed between^...$
for robustness. -
[ ]
magnet(unsafe_regex = "^nasty-regex$")
— just likemagnet(regex)
, but no automatic enclosing in^...$
happens. This may allow invalid data to pass validation!!! -
[ ]
magnet(non_empty)
— for collections: same asmin_length = "1"
. -
[ ]
magnet(min_length = "16")
— for collections/tuples etc. -
[ ]
magnet(max_length = "32")
— for collections/tuples etc. -
[ ]
magnet(incl_min = "-1337")
— inclusive minimum for numbers -
[ ]
magnet(excl_min = "42")
— exclusive "minimum" (infimum) for numbers -
[ ]
magnet(incl_max = "63")
— inclusive maximum for numbers -
[ ]
magnet(excl_max = "64")
— exclusive "maximum" (supremum) for numbers -
[ ]
magnet(allow_extra_fields)
— sets"additionalProperties": true
. By default, Magnet sets this field tofalse
for maximal safety. Allowing arbitrary data to be inserted in a DB is generally a Bad Idea, as it may lead to code injection (MongoDB
supports storing JavaScript in a collection! Madness!) or at best, denial-of-service (DoS) attacks. -
[ ]
magnet(allow_extra_fields = "ExtraFieldType")
— sets"additionalProperties": ExtraFieldType::bson_schema()
, so that unlisted additional object fields are allowed provided that they conform to the schema of the specified type.
-
Traits
BsonSchema |
Types which can be expressed/validated by a MongoDB-flavored JSON schema. |