Skip to content

Commit 42c185e

Browse files
authored
Merge pull request #122 from h-michael/codegen
Enable generating graphql client code by cli
2 parents f2ea14a + da185f2 commit 42c185e

File tree

4 files changed

+94
-17
lines changed

4 files changed

+94
-17
lines changed

graphql_client_cli/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,3 +17,4 @@ structopt = "0.2"
1717
serde = "1.0"
1818
serde_derive = "1.0"
1919
serde_json = "1.0"
20+
graphql_client_codegen = { path = "../graphql_client_codegen/", version = "0.4.0" }

graphql_client_cli/src/main.rs

Lines changed: 63 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,15 @@ extern crate reqwest;
44
extern crate structopt;
55
#[macro_use]
66
extern crate graphql_client;
7+
extern crate graphql_client_codegen;
78
#[macro_use]
89
extern crate serde_derive;
910
extern crate serde;
1011
extern crate serde_json;
1112

1213
use reqwest::header::{HeaderMap, HeaderValue, CONTENT_TYPE, ACCEPT};
14+
use std::fs::File;
15+
use std::io::Write as IoWrite;
1316
use std::path::PathBuf;
1417
use structopt::StructOpt;
1518

@@ -38,9 +41,22 @@ enum Cli {
3841
#[structopt(name = "generate")]
3942
Generate {
4043
// should be a glob
41-
paths: String,
44+
/// Path to graphql query file.
4245
#[structopt(parse(from_os_str))]
43-
schema: PathBuf,
46+
query_path: PathBuf,
47+
/// Path to graphql schema file.
48+
#[structopt(parse(from_os_str))]
49+
schema_path: PathBuf,
50+
/// Name of struct that is implementation target.
51+
selected_operation: String,
52+
/// Additional derives that will be added to the generated structs and enums for the response and the variables.
53+
/// --additional-derives='Serialize,PartialEq'
54+
#[structopt(short = "a", long = "additional-derives")]
55+
additional_derives: Option<String>,
56+
/// You can choose deprecation strategy from allow, deny, or warn.
57+
/// Default value is warn.
58+
#[structopt(short = "d", long = "deprecation-strategy",)]
59+
deprecation_strategy: Option<String>,
4460
#[structopt(parse(from_os_str))]
4561
output: PathBuf,
4662
},
@@ -55,10 +71,20 @@ fn main() -> Result<(), failure::Error> {
5571
authorization,
5672
} => introspect_schema(schema_location, output, authorization),
5773
Cli::Generate {
58-
paths: _,
59-
schema: _,
60-
output: _,
61-
} => unimplemented!(),
74+
query_path,
75+
schema_path,
76+
selected_operation,
77+
additional_derives,
78+
deprecation_strategy,
79+
output,
80+
} => generate_code(
81+
query_path,
82+
schema_path,
83+
selected_operation,
84+
additional_derives,
85+
deprecation_strategy,
86+
output,
87+
),
6288
}
6389
}
6490

@@ -106,3 +132,34 @@ fn construct_headers() -> HeaderMap {
106132
headers.insert(ACCEPT, HeaderValue::from_static("application/json"));
107133
headers
108134
}
135+
136+
fn generate_code(
137+
query_path: PathBuf,
138+
schema_path: PathBuf,
139+
selected_operation: String,
140+
additional_derives: Option<String>,
141+
deprecation_strategy: Option<String>,
142+
output: PathBuf,
143+
) -> Result<(), failure::Error> {
144+
let deprecation_strategy = deprecation_strategy.as_ref().map(|s| s.as_str());
145+
let deprecation_strategy = match deprecation_strategy {
146+
Some("allow") => Some(graphql_client_codegen::deprecation::DeprecationStrategy::Allow),
147+
Some("deny") => Some(graphql_client_codegen::deprecation::DeprecationStrategy::Deny),
148+
Some("warn") => Some(graphql_client_codegen::deprecation::DeprecationStrategy::Warn),
149+
_ => None,
150+
};
151+
152+
let options = graphql_client_codegen::GraphQLClientDeriveOptions {
153+
selected_operation,
154+
additional_derives: additional_derives,
155+
deprecation_strategy,
156+
};
157+
let gen = graphql_client_codegen::generate_module_token_stream(
158+
query_path,
159+
schema_path,
160+
Some(options),
161+
)?;
162+
let mut file = File::create(output)?;
163+
write!(file, "{}", gen.to_string());
164+
Ok(())
165+
}

graphql_client_codegen/src/lib.rs

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -55,8 +55,10 @@ lazy_static! {
5555
CacheMap::default();
5656
}
5757

58-
pub struct GraphQLClientDeriveOptions<'a> {
59-
pub input: &'a syn::DeriveInput,
58+
pub struct GraphQLClientDeriveOptions {
59+
pub selected_operation: String,
60+
pub additional_derives: Option<String>,
61+
pub deprecation_strategy: Option<deprecation::DeprecationStrategy>,
6062
}
6163

6264
#[derive(Serialize, Deserialize, Debug)]
@@ -69,12 +71,13 @@ pub fn generate_module_token_stream(
6971
schema_path: std::path::PathBuf,
7072
options: Option<GraphQLClientDeriveOptions>,
7173
) -> Result<TokenStream, failure::Error> {
72-
let input = options.unwrap().input;
74+
let options = options.unwrap();
7375

74-
let response_derives = attributes::extract_attr(input, "response_derives").ok();
76+
let response_derives = options.additional_derives;
7577

7678
// The user can determine what to do about deprecations.
77-
let deprecation_strategy = deprecation::extract_deprecation_strategy(input)
79+
let deprecation_strategy = options
80+
.deprecation_strategy
7881
.unwrap_or(deprecation::DeprecationStrategy::Warn);
7982

8083
// We need to qualify the query with the path to the crate it is part of
@@ -122,13 +125,16 @@ pub fn generate_module_token_stream(
122125
}
123126
};
124127

125-
let operation_string = input.ident.to_string();
126-
let module_name = Ident::new(&operation_string.to_snake_case(), Span::call_site());
127-
let struct_name = &input.ident;
128+
let operation_string = options.selected_operation.clone();
129+
let module_name = Ident::new(
130+
options.selected_operation.to_snake_case().as_str(),
131+
Span::call_site(),
132+
);
133+
let struct_name = Ident::new(options.selected_operation.as_str(), Span::call_site());
128134
let schema_output = codegen::response_for_query(
129135
schema,
130136
query,
131-
input.ident.to_string(),
137+
options.selected_operation.clone(),
132138
response_derives,
133139
deprecation_strategy,
134140
)?;

graphql_query_derive/src/lib.rs

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ pub fn graphql_query_derive(input: proc_macro::TokenStream) -> proc_macro::Token
1111
let input = TokenStream::from(input);
1212
let ast = syn::parse2(input).expect("Derive input is well formed");
1313
let (query_path, schema_path) = build_query_and_schema_path(&ast);
14-
let option = GraphQLClientDeriveOptions { input: &ast };
15-
let gen = generate_module_token_stream(query_path, schema_path, Some(option)).unwrap();
14+
let options = build_graphql_client_derive_options(&ast);
15+
let gen = generate_module_token_stream(query_path, schema_path, Some(options)).unwrap();
1616
gen.into()
1717
}
1818

@@ -29,3 +29,16 @@ fn build_query_and_schema_path(
2929
let schema_path = ::std::path::Path::new(&cargo_manifest_dir).join(schema_path);
3030
(query_path, schema_path)
3131
}
32+
33+
fn build_graphql_client_derive_options(input: &syn::DeriveInput) -> GraphQLClientDeriveOptions {
34+
let response_derives = attributes::extract_attr(input, "response_derives").ok();
35+
// The user can determine what to do about deprecations.
36+
let deprecation_strategy = deprecation::extract_deprecation_strategy(input)
37+
.unwrap_or(deprecation::DeprecationStrategy::Warn);
38+
39+
GraphQLClientDeriveOptions {
40+
selected_operation: input.ident.to_string(),
41+
additional_derives: response_derives,
42+
deprecation_strategy: Some(deprecation_strategy),
43+
}
44+
}

0 commit comments

Comments
 (0)