Add async-graphql-lambda

Update async-graphql-tide api
This commit is contained in:
Sunli 2020-05-14 14:50:08 +08:00
parent 3870937623
commit 191758f9b0
11 changed files with 100 additions and 100 deletions

View File

@ -33,6 +33,9 @@ jobs:
- name: async-graphql-tide
registryName: async-graphql-tide
path: async-graphql-tide
- name: async-graphql-lambda
registryName: async-graphql-lambda
path: async-graphql-lambda
steps:
- name: Checkout
uses: actions/checkout@v2

View File

@ -1,6 +1,6 @@
[package]
name = "async-graphql"
version = "1.12.3"
version = "1.12.4"
authors = ["sunli <scott_s829@163.com>"]
edition = "2018"
description = "The GraphQL server library implemented by rust"
@ -18,7 +18,7 @@ default = ["bson", "uuid", "url", "chrono-tz"]
[dependencies]
async-graphql-parser = { path = "async-graphql-parser", version = "0.3.1" }
async-graphql-derive = { path = "async-graphql-derive", version = "1.12.3" }
async-graphql-derive = { path = "async-graphql-derive", version = "1.12.4" }
anyhow = "1.0.26"
thiserror = "1.0.11"
async-trait = "0.1.30"
@ -59,4 +59,5 @@ members = [
"async-graphql-actix-web",
"async-graphql-warp",
"async-graphql-tide",
"async-graphql-lambda",
]

View File

@ -1,6 +1,6 @@
[package]
name = "async-graphql-actix-web"
version = "1.4.3"
version = "1.4.4"
authors = ["sunli <scott_s829@163.com>"]
edition = "2018"
description = "async-graphql for actix-web"
@ -13,7 +13,7 @@ keywords = ["futures", "async", "graphql"]
categories = ["network-programming", "asynchronous"]
[dependencies]
async-graphql = { path = "..", version = "1.12.3" }
async-graphql = { path = "..", version = "1.12.4" }
actix-web = "2.0.0"
actix-web-actors = "2.0.0"
actix = "0.9.0"

View File

@ -1,6 +1,6 @@
[package]
name = "async-graphql-derive"
version = "1.12.3"
version = "1.12.4"
authors = ["sunli <scott_s829@163.com>"]
edition = "2018"
description = "Macros for async-graphql"

View File

@ -0,0 +1,20 @@
[package]
name = "async-graphql-lambda"
version = "0.1.0"
authors = ["Sunli <scott_s829@163.com>"]
edition = "2018"
description = "async-graphql for AWS Lambda"
publish = true
license = "MIT/Apache-2.0"
documentation = "https://docs.rs/async-graphql/"
homepage = "https://github.com/async-graphql/async-graphql"
repository = "https://github.com/async-graphql/async-graphql"
keywords = ["futures", "async", "graphql"]
categories = ["network-programming", "asynchronous"]
[dependencies]
async-graphql = { path = "..", version = "1.12.4" }
lambda_http = { git = "https://github.com/awslabs/aws-lambda-rust-runtime" }
futures = "0.3.0"
http = "0.2"
async-trait = "0.1.30"

View File

@ -0,0 +1,37 @@
use async_graphql::{IntoQueryBuilder, IntoQueryBuilderOpts, ParseRequestError, QueryBuilder};
use futures::io::AllowStdIo;
use lambda_http::Request;
use std::io::Cursor;
/// Lambda request extension
///
#[async_trait::async_trait]
pub trait GQLRequestExt {
/// Convert a query to `async_graphql::QueryBuilder`.
async fn graphql(&self) -> Result<QueryBuilder, ParseRequestError> {
self.graphql_opts(Default::default()).await
}
/// Similar to graphql, but you can set the options `IntoQueryBuilderOpts`.
async fn graphql_opts(
&self,
opts: IntoQueryBuilderOpts,
) -> Result<QueryBuilder, ParseRequestError>;
}
#[async_trait::async_trait]
impl GQLRequestExt for Request {
async fn graphql_opts(
&self,
opts: IntoQueryBuilderOpts,
) -> Result<QueryBuilder, ParseRequestError> {
let body = self.body().as_ref();
let ct = self
.headers()
.get(http::header::CONTENT_TYPE)
.and_then(|value| value.to_str().ok());
(ct, AllowStdIo::new(Cursor::new(body)))
.into_query_builder_opts(&opts)
.await
}
}

View File

@ -1,6 +1,6 @@
[package]
name = "async-graphql-tide"
version = "1.4.3"
version = "1.4.4"
authors = ["vkill <vkill.net@gmail.com>"]
edition = "2018"
description = "async-graphql for tide"
@ -13,7 +13,7 @@ keywords = ["futures", "async", "graphql"]
categories = ["network-programming", "asynchronous"]
[dependencies]
async-graphql = { path = "..", version = "1.12.3" }
async-graphql = { path = "..", version = "1.12.4" }
tide = "0.8"
async-trait = "0.1.30"

View File

@ -6,7 +6,8 @@
use async_graphql::http::GQLResponse;
use async_graphql::{
IntoQueryBuilder, IntoQueryBuilderOpts, ObjectType, QueryBuilder, Schema, SubscriptionType,
IntoQueryBuilder, IntoQueryBuilderOpts, ObjectType, ParseRequestError, QueryBuilder, Schema,
SubscriptionType,
};
use async_trait::async_trait;
use tide::{http::headers, Request, Response, Status, StatusCode};
@ -56,7 +57,13 @@ where
TideState: Send + Sync + 'static,
F: Fn(QueryBuilder) -> QueryBuilder + Send,
{
graphql_opts(req, schema, query_builder_configuration, Default::default()).await
let query_builder = req.graphql().await.status(StatusCode::BadRequest)?;
let resp = GQLResponse(
query_builder_configuration(query_builder)
.execute(&schema)
.await,
);
Ok(Response::new(StatusCode::Ok).body_json(&resp)?)
}
/// Similar to graphql, but you can set the options `IntoQueryBuilderOpts`.
@ -73,105 +80,43 @@ where
TideState: Send + Sync + 'static,
F: Fn(QueryBuilder) -> QueryBuilder + Send,
{
req.graphql_opts(schema, query_builder_configuration, opts)
let query_builder = req
.graphql_opts(opts)
.await
.status(StatusCode::BadRequest)?;
let resp = GQLResponse(
query_builder_configuration(query_builder)
.execute(&schema)
.await,
);
Ok(Response::new(StatusCode::Ok).body_json(&resp)?)
}
/// Tide request extension
///
#[async_trait]
pub trait RequestExt<State>: Sized {
/// ```no_run
/// use async_graphql::*;
/// use async_std::task;
/// use tide::Request;
/// use async_graphql_tide::RequestExt as _;
///
/// struct QueryRoot;
/// #[Object]
/// impl QueryRoot {
/// #[field(desc = "Returns the sum of a and b")]
/// async fn add(&self, a: i32, b: i32) -> i32 {
/// a + b
/// }
/// }
///
/// fn main() -> std::result::Result<(), Box<dyn std::error::Error + Send + Sync>> {
/// task::block_on(async {
/// let mut app = tide::new();
/// app.at("/").post(|req: Request<()>| async move {
/// let schema = Schema::build(QueryRoot, EmptyMutation, EmptySubscription).finish();
/// req.graphql(schema, |query_builder| query_builder).await
/// });
/// app.listen("0.0.0.0:8000").await?;
///
/// Ok(())
/// })
/// }
/// ```
async fn graphql<Query, Mutation, Subscription, F>(
self,
schema: Schema<Query, Mutation, Subscription>,
query_builder_configuration: F,
) -> tide::Result<Response>
where
Query: ObjectType + Send + Sync + 'static,
Mutation: ObjectType + Send + Sync + 'static,
Subscription: SubscriptionType + Send + Sync + 'static,
State: Send + Sync + 'static,
F: Fn(QueryBuilder) -> QueryBuilder + Send,
{
self.graphql_opts(schema, query_builder_configuration, Default::default())
.await
pub trait RequestExt<State: Send + Sync + 'static>: Sized {
/// Convert a query to `async_graphql::QueryBuilder`.
async fn graphql(self) -> Result<QueryBuilder, ParseRequestError> {
self.graphql_opts(Default::default()).await
}
/// Similar to graphql, but you can set the options `IntoQueryBuilderOpts`.
async fn graphql_opts<Query, Mutation, Subscription, F>(
async fn graphql_opts(
self,
schema: Schema<Query, Mutation, Subscription>,
query_builder_configuration: F,
opts: IntoQueryBuilderOpts,
) -> tide::Result<Response>
where
Query: ObjectType + Send + Sync + 'static,
Mutation: ObjectType + Send + Sync + 'static,
Subscription: SubscriptionType + Send + Sync + 'static,
State: Send + Sync + 'static,
F: Fn(QueryBuilder) -> QueryBuilder + Send;
) -> Result<QueryBuilder, ParseRequestError>;
}
#[async_trait]
impl<State> RequestExt<State> for Request<State> {
async fn graphql_opts<Query, Mutation, Subscription, F>(
impl<State: Send + Sync + 'static> RequestExt<State> for Request<State> {
async fn graphql_opts(
self,
schema: Schema<Query, Mutation, Subscription>,
query_builder_configuration: F,
opts: IntoQueryBuilderOpts,
) -> tide::Result<Response>
where
Query: ObjectType + Send + Sync + 'static,
Mutation: ObjectType + Send + Sync + 'static,
Subscription: SubscriptionType + Send + Sync + 'static,
State: Send + Sync + 'static,
F: Fn(QueryBuilder) -> QueryBuilder + Send,
{
) -> Result<QueryBuilder, ParseRequestError> {
let content_type = self
.header(&headers::CONTENT_TYPE)
.and_then(|values| values.first().map(|value| value.to_string()));
let mut query_builder = (content_type, self)
.into_query_builder_opts(&opts)
.await
.status(StatusCode::BadRequest)?;
query_builder = query_builder_configuration(query_builder);
let query_response = query_builder.execute(&schema).await;
let gql_response = GQLResponse(query_response);
let resp = Response::new(StatusCode::Ok).body_json(&gql_response)?;
Ok(resp)
(content_type, self).into_query_builder_opts(&opts).await
}
}

View File

@ -6,7 +6,7 @@ use std::time::Duration;
use tide::Request;
use async_graphql::*;
use async_graphql_tide::RequestExt as _;
use async_graphql_tide::graphql;
type Result<T> = std::result::Result<T, Box<dyn std::error::Error + Send + Sync>>;
@ -28,7 +28,7 @@ fn quickstart() -> Result<()> {
let mut app = tide::new();
app.at("/").post(|req: Request<()>| async move {
let schema = Schema::build(QueryRoot, EmptyMutation, EmptySubscription).finish();
req.graphql(schema, |query_builder| query_builder).await
graphql(req, schema, |query_builder| query_builder).await
});
app.listen(&listen_addr).await?;

View File

@ -1,6 +1,6 @@
[package]
name = "async-graphql-warp"
version = "1.4.3"
version = "1.4.4"
authors = ["sunli <scott_s829@163.com>"]
edition = "2018"
description = "async-graphql for warp"
@ -13,7 +13,7 @@ keywords = ["futures", "async", "graphql"]
categories = ["network-programming", "asynchronous"]
[dependencies]
async-graphql = { path = "..", version = "1.12.3" }
async-graphql = { path = "..", version = "1.12.4" }
warp = "0.2.2"
futures = "0.3.0"
bytes = "0.5.4"

View File

@ -11,17 +11,11 @@ use async_graphql_parser::ast::OperationType;
use itertools::Itertools;
use std::any::Any;
use std::fs::File;
use std::path::PathBuf;
use std::sync::atomic::AtomicUsize;
/// IntoQueryBuilder options
#[derive(Default, Clone)]
pub struct IntoQueryBuilderOpts {
/// A temporary path to store the contents of all files.
///
/// If None, the system temporary path is used.
pub temp_dir: Option<PathBuf>,
/// Maximum file size.
pub max_file_size: Option<usize>,