turbopack_core/chunk/
evaluate.rs1use anyhow::{Result, bail};
2use turbo_tasks::{ResolvedVc, Upcast, Value, ValueToString, Vc};
3
4use super::ChunkableModule;
5use crate::{
6 asset::Asset,
7 context::AssetContext,
8 module::Module,
9 reference_type::{EntryReferenceSubType, ReferenceType},
10 source::Source,
11};
12
13#[turbo_tasks::value_trait]
18pub trait EvaluatableAsset: Asset + Module + ChunkableModule {}
19
20pub trait EvaluatableAssetExt {
21 fn to_evaluatable(
22 self: Vc<Self>,
23 asset_context: Vc<Box<dyn AssetContext>>,
24 ) -> Vc<Box<dyn EvaluatableAsset>>;
25}
26
27impl<T> EvaluatableAssetExt for T
28where
29 T: Upcast<Box<dyn Source>>,
30{
31 fn to_evaluatable(
32 self: Vc<Self>,
33 asset_context: Vc<Box<dyn AssetContext>>,
34 ) -> Vc<Box<dyn EvaluatableAsset>> {
35 to_evaluatable(Vc::upcast(self), asset_context)
36 }
37}
38
39#[turbo_tasks::function]
40async fn to_evaluatable(
41 asset: Vc<Box<dyn Source>>,
42 asset_context: Vc<Box<dyn AssetContext>>,
43) -> Result<Vc<Box<dyn EvaluatableAsset>>> {
44 let module = asset_context
45 .process(
46 asset,
47 Value::new(ReferenceType::Entry(EntryReferenceSubType::Runtime)),
48 )
49 .module();
50 let Some(entry) = Vc::try_resolve_downcast::<Box<dyn EvaluatableAsset>>(module).await? else {
51 bail!(
52 "{} is not a valid evaluated entry",
53 module.ident().to_string().await?
54 )
55 };
56 Ok(entry)
57}
58
59#[turbo_tasks::value(transparent)]
60pub struct EvaluatableAssets(Vec<ResolvedVc<Box<dyn EvaluatableAsset>>>);
61
62#[turbo_tasks::value_impl]
63impl EvaluatableAssets {
64 #[turbo_tasks::function]
65 pub fn empty() -> Vc<EvaluatableAssets> {
66 EvaluatableAssets(vec![]).cell()
67 }
68
69 #[turbo_tasks::function]
70 pub fn one(entry: ResolvedVc<Box<dyn EvaluatableAsset>>) -> Vc<EvaluatableAssets> {
71 EvaluatableAssets(vec![entry]).cell()
72 }
73
74 #[turbo_tasks::function]
75 pub fn many(assets: Vec<ResolvedVc<Box<dyn EvaluatableAsset>>>) -> Vc<EvaluatableAssets> {
76 EvaluatableAssets(assets).cell()
77 }
78
79 #[turbo_tasks::function]
80 pub async fn with_entry(
81 self: Vc<Self>,
82 entry: ResolvedVc<Box<dyn EvaluatableAsset>>,
83 ) -> Result<Vc<EvaluatableAssets>> {
84 let mut entries = self.owned().await?;
85 entries.push(entry);
86 Ok(EvaluatableAssets(entries).cell())
87 }
88}