-
Notifications
You must be signed in to change notification settings - Fork 29.9k
Relay Support in Rust Compiler #33702
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from all commits
Commits
Show all changes
21 commits
Select commit
Hold shift + click to select a range
7b337f3
Revert "Revert "Relay Support in Rust Compiler" (#33699)"
ijjk b950d7e
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
ijjk 6b1beab
enable release builds for debugging
ijjk c335297
Revert 33699 revert 33240 relay plugin (#33704)
alunyov fb62da6
update cargo
ijjk e4c58ce
move dep
ijjk a61229c
disable fail-fast
ijjk 9462285
fix config
ijjk 81a3200
install musl-tools (#33748)
alunyov b3b9a6e
Remove relay-compiler as a dependency, to unblock the build. (#33780)
alunyov 247bac5
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
ijjk 5da944c
fix wasm build
ijjk e6eb776
Few more fixes for Relay Support in Rust Compiler PR (#33795)
alunyov 9747ddd
#[cfg(target_arch = "wasm32")] (#33839)
alunyov acfc3db
revert dependency bumps
ijjk 4ebc990
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
ijjk 02ce6da
ensure release builds without dep bumps
ijjk 0fcd22d
undo release builds change
ijjk d082fc7
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
ijjk 117fed5
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
ijjk cd6783a
Merge branch 'canary' into revert-33699-revert-33240-relay-plugin
kodiakhq[bot] File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,170 @@ | ||
| use once_cell::sync::Lazy; | ||
| use regex::Regex; | ||
| use serde::Deserialize; | ||
| use std::path::{Path, PathBuf}; | ||
| use swc_atoms::JsWord; | ||
| use swc_common::errors::HANDLER; | ||
| use swc_common::FileName; | ||
| use swc_ecmascript::ast::*; | ||
| use swc_ecmascript::utils::{quote_ident, ExprFactory}; | ||
| use swc_ecmascript::visit::{Fold, FoldWith}; | ||
|
|
||
| #[derive(Copy, Clone, Debug, Deserialize)] | ||
| #[serde(rename_all = "lowercase")] | ||
| pub enum RelayLanguageConfig { | ||
| TypeScript, | ||
| Flow, | ||
| } | ||
|
|
||
| impl Default for RelayLanguageConfig { | ||
| fn default() -> Self { | ||
| Self::Flow | ||
| } | ||
| } | ||
|
|
||
| struct Relay<'a> { | ||
| root_dir: PathBuf, | ||
| file_name: FileName, | ||
| config: &'a Config, | ||
| } | ||
|
|
||
| #[derive(Deserialize, Debug, Default, Clone)] | ||
| #[serde(rename_all = "camelCase")] | ||
| pub struct Config { | ||
| pub src: PathBuf, | ||
| pub artifact_directory: Option<PathBuf>, | ||
| #[serde(default)] | ||
| pub language: RelayLanguageConfig, | ||
| } | ||
|
|
||
| fn pull_first_operation_name_from_tpl(tpl: &TaggedTpl) -> Option<String> { | ||
| tpl.tpl.quasis.iter().find_map(|quasis| { | ||
| static OPERATION_REGEX: Lazy<Regex> = | ||
| Lazy::new(|| Regex::new(r"(fragment|mutation|query|subscription) (\w+)").unwrap()); | ||
|
|
||
| let capture_group = OPERATION_REGEX.captures_iter(&quasis.raw.value).next(); | ||
|
|
||
| capture_group.map(|capture_group| capture_group[2].to_string()) | ||
| }) | ||
| } | ||
|
|
||
| fn build_require_expr_from_path(path: &str) -> Expr { | ||
| Expr::Call(CallExpr { | ||
| span: Default::default(), | ||
| callee: quote_ident!("require").as_callee(), | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The compiler supports eager esm as well, probably worth also exposing this. |
||
| args: vec![ | ||
| Lit::Str(Str { | ||
| span: Default::default(), | ||
| value: JsWord::from(path), | ||
| has_escape: false, | ||
| kind: Default::default(), | ||
| }) | ||
| .as_arg(), | ||
| ], | ||
| type_args: None, | ||
| }) | ||
| } | ||
|
|
||
| impl<'a> Fold for Relay<'a> { | ||
| fn fold_expr(&mut self, expr: Expr) -> Expr { | ||
| let expr = expr.fold_children_with(self); | ||
|
|
||
| match &expr { | ||
| Expr::TaggedTpl(tpl) => { | ||
| if let Some(built_expr) = self.build_call_expr_from_tpl(tpl) { | ||
| built_expr | ||
| } else { | ||
| expr | ||
| } | ||
| } | ||
| _ => expr, | ||
| } | ||
| } | ||
| } | ||
|
|
||
| #[derive(Debug)] | ||
| enum BuildRequirePathError { | ||
| FileNameNotReal, | ||
| ArtifactDirectoryExpected, | ||
| } | ||
|
|
||
| fn path_for_artifact( | ||
| root_dir: &Path, | ||
| config: &Config, | ||
| definition_name: &str, | ||
| ) -> Result<PathBuf, BuildRequirePathError> { | ||
| let filename = match &config.language { | ||
| RelayLanguageConfig::Flow => format!("{}.graphql.js", definition_name), | ||
| RelayLanguageConfig::TypeScript => { | ||
| format!("{}.graphql.ts", definition_name) | ||
| } | ||
| }; | ||
|
|
||
| if let Some(artifact_directory) = &config.artifact_directory { | ||
| Ok(root_dir.join(artifact_directory).join(filename)) | ||
| } else { | ||
| Err(BuildRequirePathError::ArtifactDirectoryExpected) | ||
| } | ||
| } | ||
|
|
||
| impl<'a> Relay<'a> { | ||
| fn build_require_path( | ||
| &mut self, | ||
| operation_name: &str, | ||
| ) -> Result<PathBuf, BuildRequirePathError> { | ||
| match &self.file_name { | ||
| FileName::Real(_real_file_name) => { | ||
| path_for_artifact(&self.root_dir, self.config, operation_name) | ||
| } | ||
| _ => Err(BuildRequirePathError::FileNameNotReal), | ||
| } | ||
| } | ||
|
|
||
| fn build_call_expr_from_tpl(&mut self, tpl: &TaggedTpl) -> Option<Expr> { | ||
| if let Expr::Ident(ident) = &*tpl.tag { | ||
| if &*ident.sym != "graphql" { | ||
| return None; | ||
| } | ||
| } | ||
|
|
||
| let operation_name = pull_first_operation_name_from_tpl(tpl); | ||
|
|
||
| match operation_name { | ||
| None => None, | ||
| Some(operation_name) => match self.build_require_path(operation_name.as_str()) { | ||
| Ok(final_path) => Some(build_require_expr_from_path(final_path.to_str().unwrap())), | ||
| Err(err) => { | ||
| let base_error = "Could not transform GraphQL template to a Relay import."; | ||
| let error_message = match err { | ||
| BuildRequirePathError::FileNameNotReal => "Source file was not a real \ | ||
| file. This is likely a bug and \ | ||
| should be reported to Next.js" | ||
| .to_string(), | ||
| BuildRequirePathError::ArtifactDirectoryExpected => { | ||
| "The `artifactDirectory` is expected to be set in the Relay config \ | ||
| file to work correctly with Next.js." | ||
| .to_string() | ||
| } | ||
| }; | ||
|
|
||
| HANDLER.with(|handler| { | ||
| handler.span_err( | ||
| tpl.span, | ||
| format!("{} {}", base_error, error_message).as_str(), | ||
| ); | ||
| }); | ||
|
|
||
| None | ||
| } | ||
| }, | ||
| } | ||
| } | ||
| } | ||
|
|
||
| pub fn relay<'a>(config: &'a Config, file_name: FileName) -> impl Fold + '_ { | ||
| Relay { | ||
| root_dir: std::env::current_dir().unwrap(), | ||
| file_name, | ||
| config, | ||
| } | ||
| } | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
42 changes: 42 additions & 0 deletions
42
packages/next-swc/crates/core/tests/fixture/relay/input.tsx
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| const variableQuery = graphql` | ||
| query InputVariableQuery { | ||
| hello | ||
| } | ||
| ` | ||
|
|
||
| fetchQuery(graphql` | ||
| query InputUsedInFunctionCallQuery { | ||
| hello | ||
| } | ||
| `) | ||
|
|
||
| function SomeQueryComponent() { | ||
| useLazyLoadQuery(graphql` | ||
| query InputInHookQuery { | ||
| hello | ||
| } | ||
| `) | ||
| } | ||
|
|
||
| const variableMutation = graphql` | ||
| query InputVariableMutation { | ||
| someMutation | ||
| } | ||
| ` | ||
|
|
||
| commitMutation( | ||
| environment, | ||
| graphql` | ||
| query InputUsedInFunctionCallMutation { | ||
| someMutation | ||
| } | ||
| ` | ||
| ) | ||
|
|
||
| function SomeMutationComponent() { | ||
| useMutation(graphql` | ||
| query InputInHookMutation { | ||
| someMutation | ||
| } | ||
| `) | ||
| } |
10 changes: 10 additions & 0 deletions
10
packages/next-swc/crates/core/tests/fixture/relay/output.js
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,10 @@ | ||
| const variableQuery = require("$DIR/__generated__/InputVariableQuery.graphql.ts"); | ||
| fetchQuery(require("$DIR/__generated__/InputUsedInFunctionCallQuery.graphql.ts")); | ||
| function SomeQueryComponent() { | ||
| useLazyLoadQuery(require("$DIR/__generated__/InputInHookQuery.graphql.ts")); | ||
| } | ||
| const variableMutation = require("$DIR/__generated__/InputVariableMutation.graphql.ts"); | ||
| commitMutation(environment, require("$DIR/__generated__/InputUsedInFunctionCallMutation.graphql.ts")); | ||
| function SomeMutationComponent() { | ||
| useMutation(require("$DIR/__generated__/InputInHookMutation.graphql.ts")); | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.