Skip to content

Commit

Permalink
Merge pull request #56 from Shopify/jb/extern-enums
Browse files Browse the repository at this point in the history
Add `extern_enums` and skip codegen for large enums
  • Loading branch information
jbourassa authored Mar 8, 2024
2 parents 8b4860f + 3bf99bb commit 74f49f6
Show file tree
Hide file tree
Showing 9 changed files with 208 additions and 43 deletions.
25 changes: 16 additions & 9 deletions example_with_targets/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -76,20 +76,27 @@ input_query = "b.graphql"
export = "function_b"
```

- `target`: the API-specific handle for the target implemented by the Wasm function
- `input_query`: the path to the target-specific input query file
- `export` (optional): the name of the Wasm function export to run
- default: the target handle as `snake_case`
- `target`: The API-specific handle for the target implemented by the Wasm function.
- `input_query`: The path to the target-specific input query file.
- `export` (optional): The name of the Wasm function export to run.
- default: The target handle as `snake_case`.

## `shopify_function_target` usage

### Arguments

- `query_path`: the path to the input query file for the target
- `schema_path`: the path to the API schema file for the target
- `target` (optional): the API-specific handle for the target if the function name does not match the target handle as `snake_case`
- `module_name` (optional): the name of the generated module
- default: the target handle as `snake_case`
- `query_path`: A path to a GraphQL query, whose result will be used
as the input for the function invocation. The query MUST be named "Input".
- `schema_path`: A path to Shopify's GraphQL schema definition. Use the CLI
to download a fresh copy.
- `target` (optional): The API-specific handle for the target if the function name does not match the target handle as `snake_case`.
- `module_name` (optional): The name of the generated module.
- default: The target handle as `snake_case`
- `extern_enums` (optional): A list of Enums for which an external type should be used.
For those, code generation will be skipped. This is useful for large enums
which can increase binary size, or for enums shared between multiple targets.
Example: `extern_enums = ["LanguageCode"]`
- default: `["LanguageCode", "CountryCode", "CurrencyCode"]`

### `src/lib.rs`

Expand Down
3 changes: 3 additions & 0 deletions shopify_function/src/enums.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
pub type CountryCode = String;
pub type CurrencyCode = String;
pub type LanguageCode = String;
3 changes: 3 additions & 0 deletions shopify_function/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,14 @@
pub use shopify_function_macro::{generate_types, shopify_function, shopify_function_target};

#[doc(hidden)]
pub mod enums;
/// Only used for struct generation.
#[doc(hidden)]
pub mod scalars;

pub mod prelude {
pub use crate::enums::*;
pub use crate::scalars::*;
pub use shopify_function_macro::{generate_types, shopify_function, shopify_function_target};
}
Expand Down
1 change: 1 addition & 0 deletions shopify_function/tests/fixtures/input.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@ query Input {
id
num
name
country
}
6 changes: 6 additions & 0 deletions shopify_function/tests/fixtures/schema.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ type Input {
id: ID!
num: Int
name: String
country: CountryCode
}

"""
Expand All @@ -51,3 +52,8 @@ The result of the function.
input FunctionResult {
name: String
}

enum CountryCode {
AC
CA
}
6 changes: 6 additions & 0 deletions shopify_function/tests/fixtures/schema_with_targets.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ type Input {
id: ID!
num: Int
name: String
country: CountryCode,
targetAResult: Int @restrictTarget(only: ["test.target-b"])
}

Expand Down Expand Up @@ -69,3 +70,8 @@ The result of API target B.
input FunctionTargetBResult {
name: String
}

enum CountryCode {
AC
CA
}
3 changes: 2 additions & 1 deletion shopify_function/tests/shopify_function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@ use shopify_function::Result;
const FUNCTION_INPUT: &str = r#"{
"id": "gid://shopify/Order/1234567890",
"num": 123,
"name": "test"
"name": "test",
"country": "CA"
}"#;
static mut FUNCTION_OUTPUT: Vec<u8> = vec![];

Expand Down
33 changes: 30 additions & 3 deletions shopify_function/tests/shopify_function_target.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@ use shopify_function::Result;
const TARGET_A_INPUT: &str = r#"{
"id": "gid://shopify/Order/1234567890",
"num": 123,
"name": "test"
"name": "test",
"country": "CA"
}"#;
static mut TARGET_A_OUTPUT: Vec<u8> = vec![];

Expand All @@ -24,8 +25,11 @@ fn test_target_a_export() {
output_stream = unsafe { &mut TARGET_A_OUTPUT }
)]
fn target_a(
_input: target_a::input::ResponseData,
input: target_a::input::ResponseData,
) -> Result<target_a::output::FunctionTargetAResult> {
if input.country != Some("CA".to_string()) {
panic!("Expected CountryCode to be the CA String")
}
Ok(target_a::output::FunctionTargetAResult { status: Some(200) })
}

Expand All @@ -49,7 +53,7 @@ fn test_mod_b_export() {
query_path = "./tests/fixtures/b.graphql",
schema_path = "./tests/fixtures/schema_with_targets.graphql",
input_stream = std::io::Cursor::new(TARGET_B_INPUT.as_bytes().to_vec()),
output_stream = unsafe { &mut TARGET_B_OUTPUT }
output_stream = unsafe { &mut TARGET_B_OUTPUT },
)]
fn some_function(
input: mod_b::input::ResponseData,
Expand All @@ -58,3 +62,26 @@ fn some_function(
name: Some(format!("new name: {}", input.id)),
})
}

// Verify that the CountryCode enum is generated when `extern_enums = []`
#[shopify_function_target(
target = "test.target-a",
module_name = "country_enum",
query_path = "./tests/fixtures/input.graphql",
schema_path = "./tests/fixtures/schema_with_targets.graphql",
extern_enums = []
)]
fn _with_generated_country_code(
input: country_enum::input::ResponseData,
) -> Result<country_enum::output::FunctionTargetAResult> {
use country_enum::*;

let status = match input.country {
Some(input::CountryCode::CA) => 200,
_ => 201,
};

Ok(output::FunctionTargetAResult {
status: Some(status),
})
}
Loading

0 comments on commit 74f49f6

Please sign in to comment.