mirror of
https://github.com/denoland/deno.git
synced 2025-08-04 10:59:13 +00:00
fix(npm): add support for npm packages in lock files (#15938)
This commit adds support for npm packages in the lock file.
This commit is contained in:
parent
10c3c0ee57
commit
9835b095e5
12 changed files with 513 additions and 16 deletions
|
@ -11,6 +11,7 @@ use deno_core::futures;
|
|||
use deno_core::futures::future::BoxFuture;
|
||||
use deno_core::url::Url;
|
||||
|
||||
use crate::lockfile::Lockfile;
|
||||
use crate::npm::cache::should_sync_download;
|
||||
use crate::npm::resolution::NpmResolutionSnapshot;
|
||||
use crate::npm::NpmCache;
|
||||
|
@ -50,6 +51,8 @@ pub trait InnerNpmPackageResolver: Send + Sync {
|
|||
fn ensure_read_permission(&self, path: &Path) -> Result<(), AnyError>;
|
||||
|
||||
fn snapshot(&self) -> NpmResolutionSnapshot;
|
||||
|
||||
fn lock(&self, lockfile: &mut Lockfile) -> Result<(), AnyError>;
|
||||
}
|
||||
|
||||
/// Caches all the packages in parallel.
|
||||
|
|
|
@ -15,6 +15,7 @@ use deno_core::url::Url;
|
|||
use deno_runtime::deno_node::PackageJson;
|
||||
use deno_runtime::deno_node::TYPES_CONDITIONS;
|
||||
|
||||
use crate::lockfile::Lockfile;
|
||||
use crate::npm::resolution::NpmResolution;
|
||||
use crate::npm::resolution::NpmResolutionSnapshot;
|
||||
use crate::npm::resolvers::common::cache_packages;
|
||||
|
@ -145,6 +146,11 @@ impl InnerNpmPackageResolver for GlobalNpmPackageResolver {
|
|||
fn snapshot(&self) -> NpmResolutionSnapshot {
|
||||
self.resolution.snapshot()
|
||||
}
|
||||
|
||||
fn lock(&self, lockfile: &mut Lockfile) -> Result<(), AnyError> {
|
||||
let snapshot = self.resolution.snapshot();
|
||||
self.resolution.lock(lockfile, &snapshot)
|
||||
}
|
||||
}
|
||||
|
||||
async fn cache_packages_in_resolver(
|
||||
|
|
|
@ -22,6 +22,7 @@ use deno_runtime::deno_node::TYPES_CONDITIONS;
|
|||
use tokio::task::JoinHandle;
|
||||
|
||||
use crate::fs_util;
|
||||
use crate::lockfile::Lockfile;
|
||||
use crate::npm::cache::should_sync_download;
|
||||
use crate::npm::resolution::NpmResolution;
|
||||
use crate::npm::resolution::NpmResolutionSnapshot;
|
||||
|
@ -213,6 +214,10 @@ impl InnerNpmPackageResolver for LocalNpmPackageResolver {
|
|||
fn snapshot(&self) -> NpmResolutionSnapshot {
|
||||
self.resolution.snapshot()
|
||||
}
|
||||
|
||||
fn lock(&self, lockfile: &mut Lockfile) -> Result<(), AnyError> {
|
||||
self.resolution.lock(lockfile, &self.snapshot())
|
||||
}
|
||||
}
|
||||
|
||||
async fn sync_resolver_with_fs(
|
||||
|
|
|
@ -8,6 +8,7 @@ use deno_ast::ModuleSpecifier;
|
|||
use deno_core::anyhow::bail;
|
||||
use deno_core::error::custom_error;
|
||||
use deno_core::error::AnyError;
|
||||
use deno_core::parking_lot::Mutex;
|
||||
use deno_core::serde_json;
|
||||
use deno_runtime::deno_node::PathClean;
|
||||
use deno_runtime::deno_node::RequireNpmResolver;
|
||||
|
@ -21,6 +22,7 @@ use std::path::PathBuf;
|
|||
use std::sync::Arc;
|
||||
|
||||
use crate::fs_util;
|
||||
use crate::lockfile::Lockfile;
|
||||
|
||||
use self::common::InnerNpmPackageResolver;
|
||||
use self::local::LocalNpmPackageResolver;
|
||||
|
@ -70,6 +72,7 @@ pub struct NpmPackageResolver {
|
|||
local_node_modules_path: Option<PathBuf>,
|
||||
api: NpmRegistryApi,
|
||||
cache: NpmCache,
|
||||
maybe_lockfile: Option<Arc<Mutex<Lockfile>>>,
|
||||
}
|
||||
|
||||
impl std::fmt::Debug for NpmPackageResolver {
|
||||
|
@ -101,6 +104,32 @@ impl NpmPackageResolver {
|
|||
)
|
||||
}
|
||||
|
||||
/// This function will replace current resolver with a new one built from a
|
||||
/// snapshot created out of the lockfile.
|
||||
pub async fn add_lockfile(
|
||||
&mut self,
|
||||
lockfile: Arc<Mutex<Lockfile>>,
|
||||
) -> Result<(), AnyError> {
|
||||
let snapshot =
|
||||
NpmResolutionSnapshot::from_lockfile(lockfile.clone(), &self.api).await?;
|
||||
self.maybe_lockfile = Some(lockfile);
|
||||
if let Some(node_modules_folder) = &self.local_node_modules_path {
|
||||
self.inner = Arc::new(LocalNpmPackageResolver::new(
|
||||
self.cache.clone(),
|
||||
self.api.clone(),
|
||||
node_modules_folder.clone(),
|
||||
Some(snapshot),
|
||||
));
|
||||
} else {
|
||||
self.inner = Arc::new(GlobalNpmPackageResolver::new(
|
||||
self.cache.clone(),
|
||||
self.api.clone(),
|
||||
Some(snapshot),
|
||||
));
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn new_with_maybe_snapshot(
|
||||
cache: NpmCache,
|
||||
api: NpmRegistryApi,
|
||||
|
@ -138,6 +167,7 @@ impl NpmPackageResolver {
|
|||
local_node_modules_path,
|
||||
api,
|
||||
cache,
|
||||
maybe_lockfile: None,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -224,7 +254,15 @@ impl NpmPackageResolver {
|
|||
));
|
||||
}
|
||||
|
||||
self.inner.add_package_reqs(packages).await
|
||||
self.inner.add_package_reqs(packages).await?;
|
||||
|
||||
// If there's a lock file, update it with all discovered npm packages
|
||||
if let Some(lockfile_mutex) = &self.maybe_lockfile {
|
||||
let mut lockfile = lockfile_mutex.lock();
|
||||
self.lock(&mut lockfile)?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Sets package requirements to the resolver, removing old requirements and adding new ones.
|
||||
|
@ -266,6 +304,10 @@ impl NpmPackageResolver {
|
|||
Some(self.inner.snapshot()),
|
||||
)
|
||||
}
|
||||
|
||||
pub fn lock(&self, lockfile: &mut Lockfile) -> Result<(), AnyError> {
|
||||
self.inner.lock(lockfile)
|
||||
}
|
||||
}
|
||||
|
||||
impl RequireNpmResolver for NpmPackageResolver {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue