initial commit
This commit is contained in:
commit
331f67f130
5 changed files with 120 additions and 0 deletions
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
/target
|
||||
Cargo.lock
|
7
.vscode/settings.json
vendored
Normal file
7
.vscode/settings.json
vendored
Normal file
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"[rust]": {
|
||||
"editor.formatOnSave": true,
|
||||
"editor.formatOnSaveMode": "file",
|
||||
"editor.defaultFormatter": "rust-lang.rust-analyzer"
|
||||
}
|
||||
}
|
21
Cargo.toml
Normal file
21
Cargo.toml
Normal file
|
@ -0,0 +1,21 @@
|
|||
[package]
|
||||
name = "graphql_query_builder"
|
||||
authors = ["DrakeTDL"]
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
description = "A GraphQL query builder."
|
||||
repository = "https://git.disroot.org/everyone/graphql_query_builder"
|
||||
license-file = "LICENSE"
|
||||
keywords= ["graphql", "gql", "builder"]
|
||||
# categories = []
|
||||
exclude = [".vscode", ".gitignore"]
|
||||
|
||||
[lib]
|
||||
name = "graphql_query_builder"
|
||||
path = "src/lib.rs"
|
||||
crate-type = ["cdylib", "rlib"]
|
||||
|
||||
[dependencies]
|
||||
either = "1.9.0"
|
||||
strum = { version = "0.25", features = ["derive"] }
|
||||
strum_macros = "0.25"
|
21
LICENSE
Normal file
21
LICENSE
Normal file
|
@ -0,0 +1,21 @@
|
|||
MIT License
|
||||
|
||||
Copyright (c) 2023 [fullname]
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
69
src/lib.rs
Normal file
69
src/lib.rs
Normal file
|
@ -0,0 +1,69 @@
|
|||
use std::collections::HashMap;
|
||||
use strum_macros::Display;
|
||||
|
||||
#[derive(Clone)]
|
||||
pub enum VariableValues {
|
||||
Int(i32),
|
||||
Str(&'static str),
|
||||
Enum(&'static str),
|
||||
VecInt(Vec<i32>),
|
||||
VecStr(Vec<&'static str>),
|
||||
VecEnum(Vec<&'static str>),
|
||||
}
|
||||
type Fields = Vec<either::Either<&'static str, Args>>;
|
||||
#[derive(Clone)]
|
||||
pub struct Args {
|
||||
pub operation: String,
|
||||
pub fields: Fields,
|
||||
pub variables: Option<HashMap<&'static str, VariableValues>>,
|
||||
}
|
||||
|
||||
pub fn tabs(level: usize) -> String {
|
||||
"\t".repeat(level)
|
||||
}
|
||||
|
||||
// pub struct OperationArgs {
|
||||
// pub level: usize,
|
||||
// pub field: &'static str,
|
||||
// pub variables: Option<HashMap<&'static str, VariableValues>>,
|
||||
// pub sub_field: Option<bool>,
|
||||
// pub union: Option<bool>,
|
||||
// }
|
||||
|
||||
#[derive(Display)]
|
||||
#[strum(serialize_all = "snake_case")]
|
||||
pub enum Operation {
|
||||
Query,
|
||||
Mutation,
|
||||
Subscription,
|
||||
}
|
||||
|
||||
pub struct Builder {
|
||||
pub raw: String,
|
||||
}
|
||||
|
||||
impl Builder {
|
||||
pub fn new(operation: Operation, opts: &Args) -> String {
|
||||
let subfields = Self::parse_sub_fields(&opts, 1).join("\n");
|
||||
let field = &opts.operation;
|
||||
format!("{operation} {{\n\t{field} {{\n{subfields}\n\t}}\n}}",)
|
||||
}
|
||||
fn parse_sub_fields(args: &Args, level: usize) -> Vec<String> {
|
||||
let level = level + 1;
|
||||
let tabs = tabs(level);
|
||||
args.fields
|
||||
.clone()
|
||||
.into_iter()
|
||||
.map(|arg| match arg {
|
||||
either::Either::Left(field) => {
|
||||
format!("{tabs}{field}", field = field)
|
||||
}
|
||||
either::Either::Right(args) => {
|
||||
let field = &args.operation;
|
||||
let sub_field = Self::parse_sub_fields(&args, level).join("\n");
|
||||
format!("{tabs}{field} {{\n{sub_field}\n{tabs}}}")
|
||||
}
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
}
|
Reference in a new issue