mirror of
https://github.com/pesde-pkg/pesde.git
synced 2024-12-12 11:00:36 +00:00
perf: asyncify linking
This commit is contained in:
parent
a9243b0214
commit
60dafa0114
2 changed files with 229 additions and 209 deletions
|
@ -15,6 +15,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|||
### Fixed
|
||||
- Install dependencies of packages in `x` command
|
||||
|
||||
### Performance
|
||||
- Asyncify dependency linking by @daimond113
|
||||
|
||||
## [0.5.0-rc.12] - 2024-11-22
|
||||
### Added
|
||||
- Support fallback Wally registries by @daimond113
|
||||
|
|
|
@ -1,21 +1,22 @@
|
|||
use crate::{
|
||||
linking::generator::get_file_types,
|
||||
lockfile::DownloadedGraph,
|
||||
names::PackageNames,
|
||||
scripts::{execute_script, ScriptName},
|
||||
source::{
|
||||
fs::{cas_path, store_in_cas},
|
||||
traits::PackageRef,
|
||||
version_id::VersionId,
|
||||
},
|
||||
Project, LINK_LIB_NO_FILE_FOUND, PACKAGES_CONTAINER_NAME,
|
||||
};
|
||||
use fs_err::tokio as fs;
|
||||
use futures::future::try_join_all;
|
||||
use std::{
|
||||
collections::BTreeMap,
|
||||
collections::HashMap,
|
||||
ffi::OsStr,
|
||||
path::{Path, PathBuf},
|
||||
sync::Arc,
|
||||
};
|
||||
use tokio::task::spawn_blocking;
|
||||
|
||||
/// Generates linking modules for a project
|
||||
pub mod generator;
|
||||
|
@ -39,19 +40,24 @@ impl Project {
|
|||
graph: &DownloadedGraph,
|
||||
) -> Result<(), errors::LinkingError> {
|
||||
let manifest = self.deser_manifest().await?;
|
||||
let manifest_target_kind = manifest.target.kind();
|
||||
let roblox_sync_config_gen_script = manifest
|
||||
.scripts
|
||||
.get(&ScriptName::RobloxSyncConfigGenerator.to_string());
|
||||
|
||||
let mut package_types = BTreeMap::<&PackageNames, BTreeMap<&VersionId, Vec<String>>>::new();
|
||||
|
||||
for (name, versions) in graph {
|
||||
for (version_id, node) in versions {
|
||||
let package_types = try_join_all(
|
||||
graph
|
||||
.iter()
|
||||
.map(|(name, versions)| async move {
|
||||
Ok::<_, errors::LinkingError>((name, try_join_all(versions.iter().map(|(version_id, node)| async move {
|
||||
let Some(lib_file) = node.target.lib_path() else {
|
||||
continue;
|
||||
return Ok((version_id, vec![]));
|
||||
};
|
||||
|
||||
let container_folder = node.node.container_folder(
|
||||
&self
|
||||
.package_dir()
|
||||
.join(manifest.target.kind().packages_folder(version_id.target()))
|
||||
.join(manifest_target_kind.packages_folder(version_id.target()))
|
||||
.join(PACKAGES_CONTAINER_NAME),
|
||||
name,
|
||||
version_id.version(),
|
||||
|
@ -70,7 +76,7 @@ impl Project {
|
|||
Err(e) => return Err(e.into()),
|
||||
};
|
||||
|
||||
let types = match get_file_types(&contents) {
|
||||
let types = match spawn_blocking(move || get_file_types(&contents)).await.unwrap() {
|
||||
Ok(types) => types,
|
||||
Err(e) => {
|
||||
return Err(errors::LinkingError::FullMoon(
|
||||
|
@ -87,20 +93,13 @@ impl Project {
|
|||
vec![]
|
||||
};
|
||||
|
||||
package_types
|
||||
.entry(name)
|
||||
.or_default()
|
||||
.insert(version_id, types);
|
||||
|
||||
if let Some(build_files) = Some(&node.target)
|
||||
.filter(|_| !node.node.pkg_ref.like_wally())
|
||||
.and_then(|t| t.build_files())
|
||||
{
|
||||
let script_name = ScriptName::RobloxSyncConfigGenerator.to_string();
|
||||
|
||||
let Some(script_path) = manifest.scripts.get(&script_name) else {
|
||||
log::warn!("not having a `{script_name}` script in the manifest might cause issues with Roblox linking");
|
||||
continue;
|
||||
let Some(script_path) = roblox_sync_config_gen_script else {
|
||||
log::warn!("not having a `{}` script in the manifest might cause issues with Roblox linking", ScriptName::RobloxSyncConfigGenerator);
|
||||
return Ok((version_id, vec![]));
|
||||
};
|
||||
|
||||
execute_script(
|
||||
|
@ -118,22 +117,37 @@ impl Project {
|
|||
)
|
||||
})?;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (name, versions) in graph {
|
||||
for (version_id, node) in versions {
|
||||
Ok((version_id, types))
|
||||
})).await?.into_iter().collect::<HashMap<_, _>>()))
|
||||
}
|
||||
)
|
||||
)
|
||||
.await?
|
||||
.into_iter()
|
||||
.collect::<HashMap<_, _>>();
|
||||
|
||||
let manifest = Arc::new(manifest);
|
||||
let package_types = Arc::new(package_types);
|
||||
|
||||
try_join_all(graph.iter().flat_map(|(name, versions)| {
|
||||
versions.iter().map(|(version_id, node)| {
|
||||
let name = name.clone();
|
||||
let manifest = manifest.clone();
|
||||
let package_types = package_types.clone();
|
||||
|
||||
async move {
|
||||
let (node_container_folder, node_packages_folder) = {
|
||||
let base_folder = create_and_canonicalize(
|
||||
self.package_dir()
|
||||
.join(manifest.target.kind().packages_folder(version_id.target())),
|
||||
.join(manifest_target_kind.packages_folder(version_id.target())),
|
||||
)
|
||||
.await?;
|
||||
let packages_container_folder = base_folder.join(PACKAGES_CONTAINER_NAME);
|
||||
|
||||
let container_folder = node.node.container_folder(
|
||||
&packages_container_folder,
|
||||
name,
|
||||
&name,
|
||||
version_id.version(),
|
||||
);
|
||||
|
||||
|
@ -141,7 +155,7 @@ impl Project {
|
|||
if let Some((lib_file, types)) =
|
||||
node.target.lib_path().and_then(|lib_file| {
|
||||
package_types
|
||||
.get(name)
|
||||
.get(&name)
|
||||
.and_then(|v| v.get(version_id))
|
||||
.map(|types| (lib_file, types))
|
||||
})
|
||||
|
@ -249,11 +263,14 @@ impl Project {
|
|||
)
|
||||
.await?;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
})
|
||||
}))
|
||||
.await
|
||||
.map(|_| ())
|
||||
}
|
||||
}
|
||||
|
||||
/// Errors that can occur while linking dependencies
|
||||
|
|
Loading…
Reference in a new issue