diff --git a/README.md b/README.md index 6a2fd72c..acc21459 100644 --- a/README.md +++ b/README.md @@ -67,6 +67,7 @@ your Schemas automatically. - [uuid][uuid] - [url][url] - [chrono][chrono] +- [bson][bson] ### Web Frameworks @@ -105,4 +106,5 @@ Juniper has not reached 1.0 yet, thus some API instability should be expected. [uuid]: https://crates.io/crates/uuid [url]: https://crates.io/crates/url [chrono]: https://crates.io/crates/chrono +[bson]: https://crates.io/crates/bson [juniper-from-schema]: https://github.com/davidpdrsn/juniper-from-schema diff --git a/docs/book/content/README.md b/docs/book/content/README.md index 30bc7476..86d74a12 100644 --- a/docs/book/content/README.md +++ b/docs/book/content/README.md @@ -41,6 +41,7 @@ your Schemas automatically. - [uuid][uuid] - [url][url] - [chrono][chrono] +- [bson][bson] ### Web Frameworks @@ -72,3 +73,4 @@ Juniper has not reached 1.0 yet, thus some API instability should be expected. [uuid]: https://crates.io/crates/uuid [url]: https://crates.io/crates/url [chrono]: https://crates.io/crates/chrono +[bson]: https://crates.io/crates/bson diff --git a/docs/book/content/types/scalars.md b/docs/book/content/types/scalars.md index c630f66f..70938fc2 100644 --- a/docs/book/content/types/scalars.md +++ b/docs/book/content/types/scalars.md @@ -35,6 +35,7 @@ crates. They are enabled via features that are on by default. * uuid::Uuid * chrono::DateTime * url::Url +* bson::oid::ObjectId ## newtype pattern diff --git a/juniper/Cargo.toml b/juniper/Cargo.toml index 23329d2c..fcc7ef45 100644 --- a/juniper/Cargo.toml +++ b/juniper/Cargo.toml @@ -27,6 +27,7 @@ path = "benches/bench.rs" async = ["juniper_codegen/async", "futures"] expose-test-schema = [] default = [ + "bson", "chrono", "url", "uuid", @@ -35,6 +36,7 @@ default = [ [dependencies] juniper_codegen = { version = "0.14.2", path = "../juniper_codegen" } +bson = { version = "0.14.0", optional = true } chrono = { version = "0.4.0", optional = true } fnv = "1.0.3" futures = { version = "0.3.1", optional = true } diff --git a/juniper/src/integrations/mod.rs b/juniper/src/integrations/mod.rs index 201f3f2d..7be248a9 100644 --- a/juniper/src/integrations/mod.rs +++ b/juniper/src/integrations/mod.rs @@ -13,3 +13,7 @@ pub mod url; #[cfg(feature = "uuid")] /// GraphQL support for [uuid](https://doc.rust-lang.org/uuid/uuid/struct.Uuid.html) types. pub mod uuid; + +#[cfg(feature = "bson")] +/// GraphQL support for [bson](https://github.com/mongodb/bson-rust) types. +pub mod objectid; diff --git a/juniper/src/integrations/objectid.rs b/juniper/src/integrations/objectid.rs new file mode 100644 index 00000000..cea59d72 --- /dev/null +++ b/juniper/src/integrations/objectid.rs @@ -0,0 +1,45 @@ +use bson::oid::ObjectId; + +use crate::{ + parser::{ParseError, ScalarToken, Token}, + value::ParseScalarResult, + Value, +}; + +graphql_scalar!(ObjectId where Scalar = { + description: "ObjectId" + + resolve(&self) -> Value { + Value::scalar(self.to_hex()) + } + + from_input_value(v: &InputValue) -> Option { + v.as_string_value() + .and_then(|s| ObjectId::with_string(s).ok()) + } + + from_str<'a>(value: ScalarToken<'a>) -> ParseScalarResult<'a, S> { + if let ScalarToken::String(value) = value { + Ok(S::from(value.to_owned())) + } else { + Err(ParseError::UnexpectedToken(Token::Scalar(value))) + } + } +}); + +#[cfg(test)] +mod test { + use crate::{value::DefaultScalarValue, InputValue}; + use bson::oid::ObjectId; + + #[test] + fn objectid_from_input_value() { + let raw = "53e37d08776f724e42000000"; + let input: InputValue = InputValue::scalar(raw.to_string()); + + let parsed: ObjectId = crate::FromInputValue::from_input_value(&input).unwrap(); + let id = ObjectId::with_string(raw).unwrap(); + + assert_eq!(parsed, id); + } +} diff --git a/juniper/src/lib.rs b/juniper/src/lib.rs index c5d8de15..b606cf88 100644 --- a/juniper/src/lib.rs +++ b/juniper/src/lib.rs @@ -59,6 +59,7 @@ your Schemas automatically. * [uuid][uuid] * [url][url] * [chrono][chrono] +* [bson][bson] ### Web Frameworks @@ -86,6 +87,7 @@ Juniper has not reached 1.0 yet, thus some API instability should be expected. [uuid]: https://crates.io/crates/uuid [url]: https://crates.io/crates/url [chrono]: https://crates.io/crates/chrono +[bson]: https://crates.io/crates/bson */ #![doc(html_root_url = "https://docs.rs/juniper/0.14.2")] @@ -106,6 +108,9 @@ extern crate url; #[cfg(any(test, feature = "uuid"))] extern crate uuid; +#[cfg(any(test, feature = "bson"))] +extern crate bson; + // Depend on juniper_codegen and re-export everything in it. // This allows users to just depend on juniper and get the derive // functionality automatically.