use rspack_core::{
Compilation, RuntimeGlobals, RuntimeModule, RuntimeModuleGenerateContext, RuntimeTemplate,
impl_runtime_module,
};
use crate::get_chunk_runtime_requirements;
#[impl_runtime_module]
#[derive(Debug)]
pub struct EnsureChunkRuntimeModule {
has_async_chunks: bool,
}
impl EnsureChunkRuntimeModule {
pub fn new(runtime_template: &RuntimeTemplate, has_async_chunks: bool) -> Self {
Self::with_default(runtime_template, has_async_chunks)
}
}
enum TemplateId {
Raw,
WithInline,
}
impl EnsureChunkRuntimeModule {
fn template_id(&self, id: TemplateId) -> String {
match id {
TemplateId::Raw => self.id().to_string(),
TemplateId::WithInline => format!("{}_inline", self.id()),
}
}
}
#[async_trait::async_trait]
impl RuntimeModule for EnsureChunkRuntimeModule {
fn template(&self) -> Vec<(String, String)> {
vec![
(
self.template_id(TemplateId::Raw),
include_str!("runtime/ensure_chunk.ejs").to_string(),
),
(
self.template_id(TemplateId::WithInline),
include_str!("runtime/ensure_chunk_with_inline.ejs").to_string(),
),
]
}
async fn generate(
&self,
context: &RuntimeModuleGenerateContext<'_>,
) -> rspack_error::Result<String> {
let compilation = context.compilation;
let runtime_template = context.runtime_template;
let chunk_ukey = self.chunk().expect("should have chunk");
let runtime_requirements = get_chunk_runtime_requirements(compilation, &chunk_ukey);
let source = if runtime_requirements.contains(RuntimeGlobals::ENSURE_CHUNK_HANDLERS) {
let fetch_priority = if runtime_requirements.contains(RuntimeGlobals::HAS_FETCH_PRIORITY) {
", fetchPriority"
} else {
""
};
runtime_template.render(
&self.template_id(TemplateId::Raw),
Some(serde_json::json!({
"_fetch_priority": fetch_priority,
})),
)?
} else {
runtime_template.render(&self.template_id(TemplateId::WithInline), None)?
};
Ok(source)
}
fn runtime_requirements(
&self,
compilation: &Compilation,
) -> rspack_core::RuntimeModuleRuntimeRequirements {
let mut dependencies = RuntimeGlobals::default();
let mut write = RuntimeGlobals::ENSURE_CHUNK;
if let Some(chunk_ukey) = self.chunk() {
if self.has_async_chunks
|| get_chunk_runtime_requirements(compilation, &chunk_ukey)
.contains(RuntimeGlobals::ENSURE_CHUNK_HANDLERS)
{
dependencies.insert(RuntimeGlobals::ENSURE_CHUNK_HANDLERS);
write.insert(RuntimeGlobals::ENSURE_CHUNK_HANDLERS);
}
} else if self.has_async_chunks {
dependencies.insert(RuntimeGlobals::ENSURE_CHUNK_HANDLERS);
write.insert(RuntimeGlobals::ENSURE_CHUNK_HANDLERS);
}
rspack_core::RuntimeModuleRuntimeRequirements {
dependencies,
write,
..Default::default()
}
}
}