diff --git a/packages/next-swc/crates/next-core/src/next_server/transforms.rs b/packages/next-swc/crates/next-core/src/next_server/transforms.rs index 1398f81f69..12226a0870 100644 --- a/packages/next-swc/crates/next-core/src/next_server/transforms.rs +++ b/packages/next-swc/crates/next-core/src/next_server/transforms.rs @@ -15,6 +15,7 @@ use crate::{ next_cjs_optimizer::get_next_cjs_optimizer_rule, next_disallow_re_export_all_in_page::get_next_disallow_export_all_in_page_rule, next_middleware_dynamic_assert::get_middleware_dynamic_assert_rule, + next_page_static_info::get_next_page_static_info_assert_rule, next_pure::get_next_pure_rule, server_actions::ActionsTransform, }, util::NextRuntime, @@ -41,6 +42,14 @@ pub async fn get_next_server_transforms_rules( } rules.push(get_next_font_transform_rule(mdx_rs)); + if !foreign_code { + rules.push(get_next_page_static_info_assert_rule( + mdx_rs, + Some(context_ty), + None, + )); + } + let (is_server_components, pages_dir) = match context_ty { ServerContextType::Pages { pages_dir } | ServerContextType::PagesApi { pages_dir } => { if !foreign_code { @@ -75,6 +84,7 @@ pub async fn get_next_server_transforms_rules( ActionsTransform::Client, mdx_rs, )); + (false, None) } ServerContextType::AppRSC { diff --git a/packages/next-swc/crates/next-core/src/next_shared/transforms/next_page_static_info.rs b/packages/next-swc/crates/next-core/src/next_shared/transforms/next_page_static_info.rs index 329e2eb4c8..48b9e70c48 100644 --- a/packages/next-swc/crates/next-core/src/next_shared/transforms/next_page_static_info.rs +++ b/packages/next-swc/crates/next-core/src/next_shared/transforms/next_page_static_info.rs @@ -1,6 +1,9 @@ use anyhow::Result; use async_trait::async_trait; -use next_custom_transforms::transforms::page_static_info::collect_exports; +use next_custom_transforms::transforms::page_static_info::{ + collect_exports, extract_exported_const_values, Const, +}; +use serde_json::Value; use turbo_tasks::Vc; use turbo_tasks_fs::FileSystemPath; use turbopack_binding::{ @@ -52,11 +55,60 @@ impl CustomTransformer for NextPageStaticInfo { let mut properties_to_extract = collected_exports.extra_properties.clone(); properties_to_extract.insert("config".to_string()); - let is_app_page = - matches!( - self.server_context, - Some(ServerContextType::AppRSC { .. }) | Some(ServerContextType::AppSSR { .. }) - ) || matches!(self.client_context, Some(ClientContextType::App { .. })); + let extracted = extract_exported_const_values(program, properties_to_extract); + + let is_server_layer_page = matches!( + self.server_context, + Some(ServerContextType::AppRSC { .. }) | Some(ServerContextType::AppSSR { .. }) + ); + + let is_app_page = is_server_layer_page + || matches!(self.client_context, Some(ClientContextType::App { .. })); + + if is_server_layer_page { + for warning in collected_exports.warnings.iter() { + PageStaticInfoIssue { + file_path: ctx.file_path, + messages: vec![ + format!( + "Next.js can't recognize the exported `{}` field in \"{}\" as {}.", + warning.key, ctx.file_path_str, warning.message + ), + "The default runtime will be used instead.".to_string(), + ], + severity: IssueSeverity::Warning, + } + .cell() + .emit(); + } + } + + if is_app_page { + if let Some(Some(Const::Value(Value::Object(config_obj)))) = extracted.get("config") + { + let mut messages = vec![format!( + "Page config in {} is deprecated. Replace `export const config=…` with \ + the following:", + ctx.file_path_str + )]; + + if let Some(runtime) = config_obj.get("runtime") { + messages.push(format!("- `export const runtime = {}`", runtime)); + } + + if let Some(regions) = config_obj.get("regions") { + messages.push(format!("- `export const preferredRegion = {}`", regions)); + } + + PageStaticInfoIssue { + file_path: ctx.file_path, + messages, + severity: IssueSeverity::Warning, + } + .cell() + .emit(); + } + } if collected_exports.directives.contains("client") && collected_exports.generate_static_params @@ -65,6 +117,7 @@ impl CustomTransformer for NextPageStaticInfo { PageStaticInfoIssue { file_path: ctx.file_path, messages: vec![format!(r#"Page "{}" cannot use both "use client" and export function "generateStaticParams()"."#, ctx.file_path_str)], + severity: IssueSeverity::Error, } .cell() .emit(); @@ -79,13 +132,14 @@ impl CustomTransformer for NextPageStaticInfo { pub struct PageStaticInfoIssue { pub file_path: Vc, pub messages: Vec, + pub severity: IssueSeverity, } #[turbo_tasks::value_impl] impl Issue for PageStaticInfoIssue { #[turbo_tasks::function] fn severity(&self) -> Vc { - IssueSeverity::Error.into() + self.severity.into() } #[turbo_tasks::function] diff --git a/packages/next-swc/crates/next-custom-transforms/src/transforms/page_static_info/mod.rs b/packages/next-swc/crates/next-custom-transforms/src/transforms/page_static_info/mod.rs index 0ef34a3c8a..8eae568fb9 100644 --- a/packages/next-swc/crates/next-custom-transforms/src/transforms/page_static_info/mod.rs +++ b/packages/next-swc/crates/next-custom-transforms/src/transforms/page_static_info/mod.rs @@ -207,7 +207,7 @@ pub fn collect_rsc_module_info( /// /// Returns a map of the extracted values, or either contains corresponding /// error. -pub fn extract_expored_const_values( +pub fn extract_exported_const_values( source_ast: &Program, properties_to_extract: HashSet, ) -> HashMap> { diff --git a/test/turbopack-dev-tests-manifest.json b/test/turbopack-dev-tests-manifest.json index d8f0bcb8d5..afd022e1ae 100644 --- a/test/turbopack-dev-tests-manifest.json +++ b/test/turbopack-dev-tests-manifest.json @@ -2225,10 +2225,10 @@ "runtimeError": false }, "test/e2e/app-dir-legacy-edge-runtime-config/index.test.ts": { - "passed": [], - "failed": [ + "passed": [ "app-dir edge runtime config should warn the legacy object config export" ], + "failed": [], "pending": [], "flakey": [], "runtimeError": false @@ -2537,11 +2537,10 @@ "app-dir edge SSR should handle edge rsc hmr", "app-dir edge SSR should resolve client component without error", "app-dir edge SSR should resolve module without error in edge runtime", - "app-dir edge SSR should retrieve cookies in a server component in the edge runtime" - ], - "failed": [ + "app-dir edge SSR should retrieve cookies in a server component in the edge runtime", "app-dir edge SSR should warn about the re-export of a pages runtime/preferredRegion config" ], + "failed": [], "pending": [], "flakey": [], "runtimeError": false