mirror of
https://github.com/denoland/deno.git
synced 2025-01-21 04:52:26 -05:00
remove need for outer factory
This commit is contained in:
parent
9a6263c1ce
commit
5d76fc9d3e
4 changed files with 258 additions and 282 deletions
197
cli/factory.rs
197
cli/factory.rs
|
@ -93,6 +93,7 @@ use deno_runtime::deno_node::NodeResolver;
|
|||
use deno_runtime::deno_node::PackageJsonResolver;
|
||||
use deno_runtime::deno_permissions::Permissions;
|
||||
use deno_runtime::deno_permissions::PermissionsContainer;
|
||||
use deno_runtime::deno_permissions::PermissionsOptions;
|
||||
use deno_runtime::deno_tls::rustls::RootCertStore;
|
||||
use deno_runtime::deno_tls::RootCertStoreProvider;
|
||||
use deno_runtime::deno_web::BlobStore;
|
||||
|
@ -1075,33 +1076,99 @@ pub struct SpecifierInfo {
|
|||
pub check_doc: bool,
|
||||
}
|
||||
|
||||
struct WorkspaceFileContainerEntry {
|
||||
pub struct WorkspaceDirFilesFactory {
|
||||
specifiers: Vec<(ModuleSpecifier, SpecifierInfo)>,
|
||||
doc_snippet_specifiers: Vec<ModuleSpecifier>,
|
||||
factory: CliFactory,
|
||||
worker_factory: Arc<CliMainWorkerFactory>,
|
||||
cli_options: Arc<CliOptions>,
|
||||
cli_factory: CliFactory,
|
||||
permissions_options: Deferred<PermissionsOptions>,
|
||||
}
|
||||
|
||||
impl WorkspaceFileContainerEntry {
|
||||
fn checked_specifiers(&self) -> impl Iterator<Item = &ModuleSpecifier> {
|
||||
impl WorkspaceDirFilesFactory {
|
||||
pub fn checked_specifiers(&self) -> impl Iterator<Item = &ModuleSpecifier> {
|
||||
self
|
||||
.specifiers
|
||||
.iter()
|
||||
.filter_map(|(s, i)| i.check.then_some(s))
|
||||
.chain(self.doc_snippet_specifiers.iter())
|
||||
}
|
||||
|
||||
pub async fn dependent_checked_specifiers(
|
||||
&self,
|
||||
canonicalized_dep_paths: &HashSet<PathBuf>,
|
||||
) -> Result<Vec<&ModuleSpecifier>, AnyError> {
|
||||
let graph_kind = self
|
||||
.cli_factory
|
||||
.cli_options()?
|
||||
.type_check_mode()
|
||||
.as_graph_kind();
|
||||
let module_graph_creator = self.cli_factory.module_graph_creator().await?;
|
||||
let specifiers = self.checked_specifiers().cloned().collect::<Vec<_>>();
|
||||
let graph = module_graph_creator
|
||||
.create_graph(
|
||||
graph_kind,
|
||||
specifiers.clone(),
|
||||
crate::graph_util::NpmCachingStrategy::Eager,
|
||||
)
|
||||
.await?;
|
||||
module_graph_creator.graph_valid(&graph)?;
|
||||
let dependent_specifiers = self
|
||||
.checked_specifiers()
|
||||
.filter(|s| {
|
||||
let mut dependency_specifiers = graph.walk(
|
||||
std::iter::once(*s),
|
||||
deno_graph::WalkOptions {
|
||||
follow_dynamic: true,
|
||||
kind: deno_graph::GraphKind::All,
|
||||
prefer_fast_check_graph: true,
|
||||
check_js: true,
|
||||
},
|
||||
);
|
||||
while let Some((s, _)) = dependency_specifiers.next() {
|
||||
if let Ok(path) = url_to_file_path(s) {
|
||||
if let Ok(path) = canonicalize_path(&path) {
|
||||
if canonicalized_dep_paths.contains(&path) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// skip walking this remote module's dependencies
|
||||
dependency_specifiers.skip_previous_dependencies();
|
||||
}
|
||||
}
|
||||
false
|
||||
})
|
||||
.collect();
|
||||
Ok(dependent_specifiers)
|
||||
}
|
||||
|
||||
pub fn permissions_options(&self) -> &PermissionsOptions {
|
||||
self
|
||||
.permissions_options
|
||||
.get_or_init(|| self.cli_options.permissions_options())
|
||||
}
|
||||
|
||||
pub fn permission_desc_parser(
|
||||
&self,
|
||||
) -> Result<&Arc<RuntimePermissionDescriptorParser>, AnyError> {
|
||||
self.cli_factory.permission_desc_parser()
|
||||
}
|
||||
|
||||
pub async fn create_cli_main_worker_factory(
|
||||
&self,
|
||||
) -> Result<CliMainWorkerFactory, AnyError> {
|
||||
self.cli_factory.create_cli_main_worker_factory().await
|
||||
}
|
||||
}
|
||||
|
||||
pub struct WorkspaceFileContainer {
|
||||
entries: Vec<WorkspaceFileContainerEntry>,
|
||||
pub struct WorkspaceFilesFactory {
|
||||
dirs: Vec<WorkspaceDirFilesFactory>,
|
||||
}
|
||||
|
||||
impl WorkspaceFileContainer {
|
||||
impl WorkspaceFilesFactory {
|
||||
#[allow(clippy::type_complexity)]
|
||||
pub async fn from_workspace_dirs_with_files<T: Clone>(
|
||||
mut workspace_dirs_with_files: Vec<(Arc<WorkspaceDirectory>, FilePatterns)>,
|
||||
factory: &CliFactory,
|
||||
extract_doc_files: Option<fn(File) -> Result<Vec<File>, AnyError>>,
|
||||
collect_specifiers: fn(
|
||||
FilePatterns,
|
||||
Arc<CliOptions>,
|
||||
|
@ -1115,10 +1182,11 @@ impl WorkspaceFileContainer {
|
|||
>,
|
||||
>,
|
||||
args: T,
|
||||
extract_doc_files: Option<fn(File) -> Result<Vec<File>, AnyError>>,
|
||||
cli_options: &CliOptions,
|
||||
watcher_communicator: Option<&Arc<WatcherCommunicator>>,
|
||||
) -> Result<Self, AnyError> {
|
||||
workspace_dirs_with_files.sort_by_cached_key(|(d, _)| d.dir_url().clone());
|
||||
let cli_options = factory.cli_options()?;
|
||||
let watcher_communicator = &factory.watcher_communicator;
|
||||
let all_scopes = Arc::new(
|
||||
workspace_dirs_with_files
|
||||
.iter()
|
||||
|
@ -1127,7 +1195,7 @@ impl WorkspaceFileContainer {
|
|||
.collect::<BTreeSet<_>>(),
|
||||
);
|
||||
let dir_count = workspace_dirs_with_files.len();
|
||||
let mut entries = Vec::with_capacity(dir_count);
|
||||
let mut dirs = Vec::with_capacity(dir_count);
|
||||
for (workspace_dir, files) in workspace_dirs_with_files {
|
||||
let scope_options = (dir_count > 1).then(|| ScopeOptions {
|
||||
scope: workspace_dir
|
||||
|
@ -1140,11 +1208,11 @@ impl WorkspaceFileContainer {
|
|||
.with_new_start_dir_and_scope_options(workspace_dir, scope_options)?,
|
||||
);
|
||||
let mut factory = CliFactory::from_cli_options(cli_options.clone());
|
||||
factory.watcher_communicator = watcher_communicator.clone();
|
||||
factory.watcher_communicator = watcher_communicator.cloned();
|
||||
let file_fetcher = factory.file_fetcher()?;
|
||||
let specifiers = collect_specifiers(
|
||||
files,
|
||||
cli_options,
|
||||
cli_options.clone(),
|
||||
file_fetcher.clone(),
|
||||
args.clone(),
|
||||
)
|
||||
|
@ -1161,30 +1229,32 @@ impl WorkspaceFileContainer {
|
|||
}
|
||||
}
|
||||
}
|
||||
let worker_factory =
|
||||
Arc::new(factory.create_cli_main_worker_factory().await?);
|
||||
entries.push(WorkspaceFileContainerEntry {
|
||||
dirs.push(WorkspaceDirFilesFactory {
|
||||
specifiers,
|
||||
doc_snippet_specifiers,
|
||||
factory,
|
||||
worker_factory,
|
||||
cli_options,
|
||||
cli_factory: factory,
|
||||
permissions_options: Default::default(),
|
||||
});
|
||||
}
|
||||
Ok(Self { entries })
|
||||
Ok(Self { dirs })
|
||||
}
|
||||
|
||||
pub async fn check(&self) -> Result<(), AnyError> {
|
||||
let mut diagnostics = vec![];
|
||||
let mut all_errors = vec![];
|
||||
for entry in &self.entries {
|
||||
let main_graph_container =
|
||||
entry.factory.main_module_graph_container().await?.clone();
|
||||
for entry in &self.dirs {
|
||||
let main_graph_container = entry
|
||||
.cli_factory
|
||||
.main_module_graph_container()
|
||||
.await?
|
||||
.clone();
|
||||
let specifiers_for_typecheck =
|
||||
entry.checked_specifiers().cloned().collect::<Vec<_>>();
|
||||
if specifiers_for_typecheck.is_empty() {
|
||||
continue;
|
||||
}
|
||||
let ext_flag = entry.factory.cli_options()?.ext_flag().as_ref();
|
||||
let ext_flag = entry.cli_factory.cli_options()?.ext_flag().as_ref();
|
||||
if let Err(err) = main_graph_container
|
||||
.check_specifiers(&specifiers_for_typecheck, ext_flag)
|
||||
.await
|
||||
|
@ -1213,78 +1283,11 @@ impl WorkspaceFileContainer {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
pub fn dirs(&self) -> &Vec<WorkspaceDirFilesFactory> {
|
||||
&self.dirs
|
||||
}
|
||||
|
||||
pub fn found_specifiers(&self) -> bool {
|
||||
self.entries.iter().any(|e| !e.specifiers.is_empty())
|
||||
}
|
||||
|
||||
pub fn worker_factories_with_checked_specifiers(
|
||||
&self,
|
||||
) -> Vec<(Arc<CliMainWorkerFactory>, Vec<ModuleSpecifier>)> {
|
||||
self
|
||||
.entries
|
||||
.iter()
|
||||
.map(|e| {
|
||||
(
|
||||
e.worker_factory.clone(),
|
||||
e.checked_specifiers().cloned().collect(),
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
|
||||
/// Per workspace directory, return a list of included checked specifiers
|
||||
/// which depend on the modules at the passed paths.
|
||||
pub async fn worker_factories_with_dependent_checked_specifiers(
|
||||
&self,
|
||||
canonicalized_dep_paths: &HashSet<PathBuf>,
|
||||
) -> Result<Vec<(Arc<CliMainWorkerFactory>, Vec<ModuleSpecifier>)>, AnyError>
|
||||
{
|
||||
let mut result = Vec::with_capacity(self.entries.len());
|
||||
for entry in &self.entries {
|
||||
let graph_kind = entry
|
||||
.factory
|
||||
.cli_options()?
|
||||
.type_check_mode()
|
||||
.as_graph_kind();
|
||||
let module_graph_creator = entry.factory.module_graph_creator().await?;
|
||||
let specifiers = entry.checked_specifiers().cloned().collect::<Vec<_>>();
|
||||
let graph = module_graph_creator
|
||||
.create_graph(
|
||||
graph_kind,
|
||||
specifiers.clone(),
|
||||
crate::graph_util::NpmCachingStrategy::Eager,
|
||||
)
|
||||
.await?;
|
||||
module_graph_creator.graph_valid(&graph)?;
|
||||
let dependent_specifiers = specifiers
|
||||
.into_iter()
|
||||
.filter(|s| {
|
||||
let mut dependency_specifiers = graph.walk(
|
||||
std::iter::once(s),
|
||||
deno_graph::WalkOptions {
|
||||
follow_dynamic: true,
|
||||
kind: deno_graph::GraphKind::All,
|
||||
prefer_fast_check_graph: true,
|
||||
check_js: true,
|
||||
},
|
||||
);
|
||||
while let Some((s, _)) = dependency_specifiers.next() {
|
||||
if let Ok(path) = url_to_file_path(s) {
|
||||
if let Ok(path) = canonicalize_path(&path) {
|
||||
if canonicalized_dep_paths.contains(&path) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// skip walking this remote module's dependencies
|
||||
dependency_specifiers.skip_previous_dependencies();
|
||||
}
|
||||
}
|
||||
false
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
result.push((entry.worker_factory.clone(), dependent_specifiers));
|
||||
}
|
||||
Ok(result)
|
||||
self.dirs.iter().any(|e| !e.specifiers.is_empty())
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
// Copyright 2018-2024 the Deno authors. All rights reserved. MIT license.
|
||||
|
||||
use crate::args::BenchFlags;
|
||||
use crate::args::CliOptions;
|
||||
use crate::args::Flags;
|
||||
use crate::colors;
|
||||
use crate::display::write_json_to_stdout;
|
||||
use crate::factory::CliFactory;
|
||||
use crate::factory::SpecifierInfo;
|
||||
use crate::factory::WorkspaceFileContainer;
|
||||
use crate::factory::WorkspaceFilesFactory;
|
||||
use crate::ops;
|
||||
use crate::tools::test::format_test_error;
|
||||
use crate::tools::test::TestFilter;
|
||||
|
@ -32,7 +32,6 @@ use deno_core::ModuleSpecifier;
|
|||
use deno_core::PollEventLoopOptions;
|
||||
use deno_runtime::deno_permissions::Permissions;
|
||||
use deno_runtime::deno_permissions::PermissionsContainer;
|
||||
use deno_runtime::permissions::RuntimePermissionDescriptorParser;
|
||||
use deno_runtime::tokio_util::create_and_run_current_thread;
|
||||
use deno_runtime::WorkerExecutionMode;
|
||||
use indexmap::IndexMap;
|
||||
|
@ -40,7 +39,9 @@ use indexmap::IndexSet;
|
|||
use log::Level;
|
||||
use serde::Deserialize;
|
||||
use serde::Serialize;
|
||||
use std::collections::HashSet;
|
||||
use std::path::Path;
|
||||
use std::path::PathBuf;
|
||||
use std::sync::Arc;
|
||||
use std::time::Duration;
|
||||
use tokio::sync::mpsc::unbounded_channel;
|
||||
|
@ -264,29 +265,42 @@ async fn bench_specifier_inner(
|
|||
|
||||
/// Test a collection of specifiers with test modes concurrently.
|
||||
async fn bench_specifiers(
|
||||
factories_with_specifiers: Vec<(
|
||||
Arc<CliMainWorkerFactory>,
|
||||
Vec<ModuleSpecifier>,
|
||||
)>,
|
||||
permissions: &Permissions,
|
||||
permissions_desc_parser: &Arc<RuntimePermissionDescriptorParser>,
|
||||
workspace_files_factory: &WorkspaceFilesFactory,
|
||||
changed_paths: Option<&HashSet<PathBuf>>,
|
||||
options: BenchSpecifierOptions,
|
||||
) -> Result<(), AnyError> {
|
||||
let specifiers_with_factory = factories_with_specifiers
|
||||
.into_iter()
|
||||
.flat_map(|(f, s)| {
|
||||
s.into_iter().map(|s| (s, f.clone())).collect::<Vec<_>>()
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
let mut specifiers_with_services = vec![];
|
||||
for factory in workspace_files_factory.dirs() {
|
||||
let worker_factory =
|
||||
Arc::new(factory.create_cli_main_worker_factory().await?);
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Arc::new(Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
factory.permissions_options(),
|
||||
)?);
|
||||
let specifiers = if let Some(changed_paths) = changed_paths {
|
||||
factory.dependent_checked_specifiers(changed_paths).await?
|
||||
} else {
|
||||
factory.checked_specifiers().collect()
|
||||
};
|
||||
specifiers_with_services.extend(specifiers.into_iter().map(|s| {
|
||||
(
|
||||
s.clone(),
|
||||
worker_factory.clone(),
|
||||
permission_desc_parser.clone(),
|
||||
permissions.clone(),
|
||||
)
|
||||
}));
|
||||
}
|
||||
let (sender, mut receiver) = unbounded_channel::<BenchEvent>();
|
||||
let log_level = options.log_level;
|
||||
let option_for_handles = options.clone();
|
||||
|
||||
let join_handles = specifiers_with_factory.into_iter().map(
|
||||
move |(specifier, worker_factory)| {
|
||||
let join_handles = specifiers_with_services.into_iter().map(
|
||||
move |(specifier, worker_factory, permissions_desc_parser, permissions)| {
|
||||
let permissions_container = PermissionsContainer::new(
|
||||
permissions_desc_parser.clone(),
|
||||
permissions.clone(),
|
||||
permissions.as_ref().clone(),
|
||||
);
|
||||
let sender = sender.clone();
|
||||
let options = option_for_handles.clone();
|
||||
|
@ -418,18 +432,9 @@ pub async fn run_benchmarks(
|
|||
flags: Arc<Flags>,
|
||||
bench_flags: BenchFlags,
|
||||
) -> Result<(), AnyError> {
|
||||
let factory = CliFactory::from_flags(flags);
|
||||
let cli_options = factory.cli_options()?;
|
||||
let cli_options = CliOptions::from_flags(flags)?;
|
||||
let workspace_bench_options =
|
||||
cli_options.resolve_workspace_bench_options(&bench_flags);
|
||||
// Various bench files should not share the same permissions in terms of
|
||||
// `PermissionsContainer` - otherwise granting/revoking permissions in one
|
||||
// file would have impact on other files, which is undesirable.
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
&cli_options.permissions_options(),
|
||||
)?;
|
||||
let log_level = cli_options.log_level();
|
||||
|
||||
let workspace_dirs_with_files = cli_options
|
||||
|
@ -437,42 +442,43 @@ pub async fn run_benchmarks(
|
|||
.into_iter()
|
||||
.map(|(d, o)| (d, o.files))
|
||||
.collect();
|
||||
let file_container = WorkspaceFileContainer::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
&factory,
|
||||
None,
|
||||
|patterns, cli_options, _, _| {
|
||||
async move {
|
||||
let info = SpecifierInfo {
|
||||
check: true,
|
||||
check_doc: false,
|
||||
};
|
||||
collect_specifiers(
|
||||
patterns,
|
||||
cli_options.vendor_dir_path().map(ToOwned::to_owned),
|
||||
is_supported_bench_path,
|
||||
)
|
||||
.map(|s| s.into_iter().map(|s| (s, info)).collect())
|
||||
}
|
||||
.boxed_local()
|
||||
},
|
||||
(),
|
||||
)
|
||||
.await?;
|
||||
if !file_container.found_specifiers() {
|
||||
let workspace_files_factory =
|
||||
WorkspaceFilesFactory::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
|patterns, cli_options, _, _| {
|
||||
async move {
|
||||
let info = SpecifierInfo {
|
||||
check: true,
|
||||
check_doc: false,
|
||||
};
|
||||
collect_specifiers(
|
||||
patterns,
|
||||
cli_options.vendor_dir_path().map(ToOwned::to_owned),
|
||||
is_supported_bench_path,
|
||||
)
|
||||
.map(|s| s.into_iter().map(|s| (s, info)).collect())
|
||||
}
|
||||
.boxed_local()
|
||||
},
|
||||
(),
|
||||
None,
|
||||
&cli_options,
|
||||
None,
|
||||
)
|
||||
.await?;
|
||||
if !workspace_files_factory.found_specifiers() {
|
||||
return Err(generic_error("No test modules found"));
|
||||
}
|
||||
|
||||
file_container.check().await?;
|
||||
workspace_files_factory.check().await?;
|
||||
|
||||
if workspace_bench_options.no_run {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
bench_specifiers(
|
||||
file_container.worker_factories_with_checked_specifiers(),
|
||||
&permissions,
|
||||
permission_desc_parser,
|
||||
&workspace_files_factory,
|
||||
None,
|
||||
BenchSpecifierOptions {
|
||||
filter: TestFilter::from_flag(&workspace_bench_options.filter),
|
||||
json: workspace_bench_options.json,
|
||||
|
@ -502,18 +508,9 @@ pub async fn run_benchmarks_with_watch(
|
|||
let bench_flags = bench_flags.clone();
|
||||
watcher_communicator.show_path_changed(changed_paths.clone());
|
||||
Ok(async move {
|
||||
let factory = CliFactory::from_flags_for_watcher(
|
||||
flags,
|
||||
watcher_communicator.clone(),
|
||||
);
|
||||
let cli_options = factory.cli_options()?;
|
||||
let cli_options = CliOptions::from_flags(flags)?;
|
||||
let workspace_bench_options =
|
||||
cli_options.resolve_workspace_bench_options(&bench_flags);
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
&cli_options.permissions_options(),
|
||||
)?;
|
||||
let log_level = cli_options.log_level();
|
||||
|
||||
let _ = watcher_communicator.watch_paths(cli_options.watch_paths());
|
||||
|
@ -530,11 +527,9 @@ pub async fn run_benchmarks_with_watch(
|
|||
.flatten()
|
||||
.collect::<Vec<_>>();
|
||||
let _ = watcher_communicator.watch_paths(watch_paths);
|
||||
let file_container =
|
||||
WorkspaceFileContainer::from_workspace_dirs_with_files(
|
||||
let workspace_files_factory =
|
||||
WorkspaceFilesFactory::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
&factory,
|
||||
None,
|
||||
|patterns, cli_options, _, _| {
|
||||
async move {
|
||||
let info = SpecifierInfo {
|
||||
|
@ -551,30 +546,21 @@ pub async fn run_benchmarks_with_watch(
|
|||
.boxed_local()
|
||||
},
|
||||
(),
|
||||
None,
|
||||
&cli_options,
|
||||
Some(&watcher_communicator),
|
||||
)
|
||||
.await?;
|
||||
|
||||
file_container.check().await?;
|
||||
workspace_files_factory.check().await?;
|
||||
|
||||
if workspace_bench_options.no_run {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
let factories_with_specifiers =
|
||||
if let Some(changed_paths) = changed_paths {
|
||||
file_container
|
||||
.worker_factories_with_dependent_checked_specifiers(
|
||||
&changed_paths.into_iter().collect(),
|
||||
)
|
||||
.await?
|
||||
} else {
|
||||
file_container.worker_factories_with_checked_specifiers()
|
||||
};
|
||||
|
||||
bench_specifiers(
|
||||
factories_with_specifiers,
|
||||
&permissions,
|
||||
permission_desc_parser,
|
||||
&workspace_files_factory,
|
||||
changed_paths.map(|p| p.into_iter().collect()).as_ref(),
|
||||
BenchSpecifierOptions {
|
||||
filter: TestFilter::from_flag(&workspace_bench_options.filter),
|
||||
json: workspace_bench_options.json,
|
||||
|
|
|
@ -30,9 +30,8 @@ use crate::cache::CacheDBHash;
|
|||
use crate::cache::Caches;
|
||||
use crate::cache::FastInsecureHasher;
|
||||
use crate::cache::TypeCheckCache;
|
||||
use crate::factory::CliFactory;
|
||||
use crate::factory::SpecifierInfo;
|
||||
use crate::factory::WorkspaceFileContainer;
|
||||
use crate::factory::WorkspaceFilesFactory;
|
||||
use crate::graph_util::BuildFastCheckGraphOptions;
|
||||
use crate::graph_util::ModuleGraphBuilder;
|
||||
use crate::npm::CliNpmResolver;
|
||||
|
@ -48,39 +47,40 @@ pub async fn check(
|
|||
flags: Arc<Flags>,
|
||||
check_flags: CheckFlags,
|
||||
) -> Result<(), AnyError> {
|
||||
let factory = CliFactory::from_flags(flags);
|
||||
let cli_options = factory.cli_options()?;
|
||||
let cli_options = CliOptions::from_flags(flags)?;
|
||||
let workspace_dirs_with_files =
|
||||
cli_options.resolve_file_flags_for_members(&FileFlags {
|
||||
ignore: Default::default(),
|
||||
include: check_flags.files,
|
||||
})?;
|
||||
let file_container = WorkspaceFileContainer::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
&factory,
|
||||
Some(extract_snippet_files),
|
||||
|patterns, cli_options, _, (doc, doc_only)| {
|
||||
async move {
|
||||
let info = SpecifierInfo {
|
||||
check: !doc_only,
|
||||
check_doc: doc || doc_only,
|
||||
};
|
||||
collect_specifiers(
|
||||
patterns,
|
||||
cli_options.vendor_dir_path().map(ToOwned::to_owned),
|
||||
|e| is_script_ext(e.path),
|
||||
)
|
||||
.map(|s| s.into_iter().map(|s| (s, info)).collect())
|
||||
}
|
||||
.boxed_local()
|
||||
},
|
||||
(check_flags.doc, check_flags.doc_only),
|
||||
)
|
||||
.await?;
|
||||
if !file_container.found_specifiers() {
|
||||
let workspace_files_factory =
|
||||
WorkspaceFilesFactory::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
|patterns, cli_options, _, (doc, doc_only)| {
|
||||
async move {
|
||||
let info = SpecifierInfo {
|
||||
check: !doc_only,
|
||||
check_doc: doc || doc_only,
|
||||
};
|
||||
collect_specifiers(
|
||||
patterns,
|
||||
cli_options.vendor_dir_path().map(ToOwned::to_owned),
|
||||
|e| is_script_ext(e.path),
|
||||
)
|
||||
.map(|s| s.into_iter().map(|s| (s, info)).collect())
|
||||
}
|
||||
.boxed_local()
|
||||
},
|
||||
(check_flags.doc, check_flags.doc_only),
|
||||
Some(extract_snippet_files),
|
||||
&cli_options,
|
||||
None,
|
||||
)
|
||||
.await?;
|
||||
if !workspace_files_factory.found_specifiers() {
|
||||
log::warn!("{} No matching files found.", colors::yellow("Warning"));
|
||||
}
|
||||
file_container.check().await
|
||||
workspace_files_factory.check().await
|
||||
}
|
||||
|
||||
/// Options for performing a check of a module graph. Note that the decision to
|
||||
|
|
|
@ -6,9 +6,8 @@ use crate::args::TestFlags;
|
|||
use crate::args::TestReporterConfig;
|
||||
use crate::colors;
|
||||
use crate::display;
|
||||
use crate::factory::CliFactory;
|
||||
use crate::factory::SpecifierInfo;
|
||||
use crate::factory::WorkspaceFileContainer;
|
||||
use crate::factory::WorkspaceFilesFactory;
|
||||
use crate::file_fetcher::FileFetcher;
|
||||
use crate::ops;
|
||||
use crate::util::extract::extract_doc_tests;
|
||||
|
@ -53,7 +52,6 @@ use deno_runtime::deno_io::StdioPipe;
|
|||
use deno_runtime::deno_permissions::Permissions;
|
||||
use deno_runtime::deno_permissions::PermissionsContainer;
|
||||
use deno_runtime::fmt_errors::format_js_error;
|
||||
use deno_runtime::permissions::RuntimePermissionDescriptorParser;
|
||||
use deno_runtime::tokio_util::create_and_run_current_thread;
|
||||
use deno_runtime::worker::MainWorker;
|
||||
use deno_runtime::WorkerExecutionMode;
|
||||
|
@ -77,6 +75,7 @@ use std::future::poll_fn;
|
|||
use std::io::Write;
|
||||
use std::num::NonZeroUsize;
|
||||
use std::path::Path;
|
||||
use std::path::PathBuf;
|
||||
use std::sync::atomic::AtomicBool;
|
||||
use std::sync::atomic::AtomicUsize;
|
||||
use std::sync::atomic::Ordering;
|
||||
|
@ -1163,24 +1162,37 @@ static HAS_TEST_RUN_SIGINT_HANDLER: AtomicBool = AtomicBool::new(false);
|
|||
|
||||
/// Test a collection of specifiers with test modes concurrently.
|
||||
async fn test_specifiers(
|
||||
factories_with_specifiers: Vec<(
|
||||
Arc<CliMainWorkerFactory>,
|
||||
Vec<ModuleSpecifier>,
|
||||
)>,
|
||||
permissions: &Permissions,
|
||||
permission_desc_parser: &Arc<RuntimePermissionDescriptorParser>,
|
||||
workspace_files_factory: &WorkspaceFilesFactory,
|
||||
changed_paths: Option<&HashSet<PathBuf>>,
|
||||
options: TestSpecifiersOptions,
|
||||
) -> Result<(), AnyError> {
|
||||
let mut specifiers_with_factory = factories_with_specifiers
|
||||
.into_iter()
|
||||
.flat_map(|(f, s)| {
|
||||
s.into_iter().map(|s| (s, f.clone())).collect::<Vec<_>>()
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
let mut specifiers_with_services = vec![];
|
||||
for factory in workspace_files_factory.dirs() {
|
||||
let worker_factory =
|
||||
Arc::new(factory.create_cli_main_worker_factory().await?);
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Arc::new(Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
factory.permissions_options(),
|
||||
)?);
|
||||
let specifiers = if let Some(changed_paths) = changed_paths {
|
||||
factory.dependent_checked_specifiers(changed_paths).await?
|
||||
} else {
|
||||
factory.checked_specifiers().collect()
|
||||
};
|
||||
specifiers_with_services.extend(specifiers.into_iter().map(|s| {
|
||||
(
|
||||
s.clone(),
|
||||
worker_factory.clone(),
|
||||
permission_desc_parser.clone(),
|
||||
permissions.clone(),
|
||||
)
|
||||
}));
|
||||
}
|
||||
if let Some(seed) = options.specifier.shuffle {
|
||||
let mut rng = SmallRng::seed_from_u64(seed);
|
||||
specifiers_with_factory.sort_by_cached_key(|(s, _)| s.to_string());
|
||||
specifiers_with_factory.shuffle(&mut rng);
|
||||
specifiers_with_services.sort_by_cached_key(|(s, ..)| s.to_string());
|
||||
specifiers_with_services.shuffle(&mut rng);
|
||||
}
|
||||
|
||||
let (test_event_sender_factory, receiver) = create_test_event_channel();
|
||||
|
@ -1195,11 +1207,11 @@ async fn test_specifiers(
|
|||
let reporter = get_test_reporter(&options);
|
||||
let fail_fast_tracker = FailFastTracker::new(options.fail_fast);
|
||||
|
||||
let join_handles = specifiers_with_factory.into_iter().map(
|
||||
move |(specifier, worker_factory)| {
|
||||
let join_handles = specifiers_with_services.into_iter().map(
|
||||
move |(specifier, worker_factory, permission_desc_parser, permissions)| {
|
||||
let permissions_container = PermissionsContainer::new(
|
||||
permission_desc_parser.clone(),
|
||||
permissions.clone(),
|
||||
permission_desc_parser,
|
||||
permissions.as_ref().clone(),
|
||||
);
|
||||
let worker_sender = test_event_sender_factory.worker();
|
||||
let fail_fast_tracker = fail_fast_tracker.clone();
|
||||
|
@ -1485,18 +1497,12 @@ pub async fn run_tests(
|
|||
flags: Arc<Flags>,
|
||||
test_flags: TestFlags,
|
||||
) -> Result<(), AnyError> {
|
||||
let factory = CliFactory::from_flags(flags);
|
||||
let cli_options = factory.cli_options()?;
|
||||
let cli_options = CliOptions::from_flags(flags)?;
|
||||
let workspace_test_options =
|
||||
cli_options.resolve_workspace_test_options(&test_flags);
|
||||
// Various test files should not share the same permissions in terms of
|
||||
// `PermissionsContainer` - otherwise granting/revoking permissions in one
|
||||
// file would have impact on other files, which is undesirable.
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
&cli_options.permissions_options(),
|
||||
)?;
|
||||
let log_level = cli_options.log_level();
|
||||
|
||||
let workspace_dirs_with_files = cli_options
|
||||
|
@ -1504,33 +1510,34 @@ pub async fn run_tests(
|
|||
.into_iter()
|
||||
.map(|(d, o)| (d, o.files))
|
||||
.collect();
|
||||
let file_container = WorkspaceFileContainer::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
&factory,
|
||||
Some(extract_doc_tests),
|
||||
|patterns, cli_options, file_fetcher, doc| {
|
||||
collect_specifiers_for_tests(patterns, cli_options, file_fetcher, doc)
|
||||
.boxed_local()
|
||||
},
|
||||
workspace_test_options.doc,
|
||||
)
|
||||
.await?;
|
||||
let workspace_files_factory =
|
||||
WorkspaceFilesFactory::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
|patterns, cli_options, file_fetcher, doc| {
|
||||
collect_specifiers_for_tests(patterns, cli_options, file_fetcher, doc)
|
||||
.boxed_local()
|
||||
},
|
||||
workspace_test_options.doc,
|
||||
Some(extract_doc_tests),
|
||||
&cli_options,
|
||||
None,
|
||||
)
|
||||
.await?;
|
||||
if !workspace_test_options.permit_no_files
|
||||
&& !file_container.found_specifiers()
|
||||
&& !workspace_files_factory.found_specifiers()
|
||||
{
|
||||
return Err(generic_error("No test modules found"));
|
||||
}
|
||||
|
||||
file_container.check().await?;
|
||||
workspace_files_factory.check().await?;
|
||||
|
||||
if workspace_test_options.no_run {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
test_specifiers(
|
||||
file_container.worker_factories_with_checked_specifiers(),
|
||||
&permissions,
|
||||
permission_desc_parser,
|
||||
&workspace_files_factory,
|
||||
None,
|
||||
TestSpecifiersOptions {
|
||||
cwd: Url::from_directory_path(cli_options.initial_cwd()).map_err(
|
||||
|_| {
|
||||
|
@ -1591,18 +1598,9 @@ pub async fn run_tests_with_watch(
|
|||
let test_flags = test_flags.clone();
|
||||
watcher_communicator.show_path_changed(changed_paths.clone());
|
||||
Ok(async move {
|
||||
let factory = CliFactory::from_flags_for_watcher(
|
||||
flags,
|
||||
watcher_communicator.clone(),
|
||||
);
|
||||
let cli_options = factory.cli_options()?;
|
||||
let cli_options = CliOptions::from_flags(flags)?;
|
||||
let workspace_test_options =
|
||||
cli_options.resolve_workspace_test_options(&test_flags);
|
||||
let permission_desc_parser = factory.permission_desc_parser()?;
|
||||
let permissions = Permissions::from_options(
|
||||
permission_desc_parser.as_ref(),
|
||||
&cli_options.permissions_options(),
|
||||
)?;
|
||||
let log_level = cli_options.log_level();
|
||||
|
||||
let _ = watcher_communicator.watch_paths(cli_options.watch_paths());
|
||||
|
@ -1619,11 +1617,9 @@ pub async fn run_tests_with_watch(
|
|||
.flatten()
|
||||
.collect::<Vec<_>>();
|
||||
let _ = watcher_communicator.watch_paths(watch_paths);
|
||||
let file_container =
|
||||
WorkspaceFileContainer::from_workspace_dirs_with_files(
|
||||
let workspace_files_factory =
|
||||
WorkspaceFilesFactory::from_workspace_dirs_with_files(
|
||||
workspace_dirs_with_files,
|
||||
&factory,
|
||||
Some(extract_doc_tests),
|
||||
|patterns, cli_options, file_fetcher, doc| {
|
||||
collect_specifiers_for_tests(
|
||||
patterns,
|
||||
|
@ -1634,30 +1630,21 @@ pub async fn run_tests_with_watch(
|
|||
.boxed_local()
|
||||
},
|
||||
workspace_test_options.doc,
|
||||
Some(extract_doc_tests),
|
||||
&cli_options,
|
||||
Some(&watcher_communicator),
|
||||
)
|
||||
.await?;
|
||||
|
||||
file_container.check().await?;
|
||||
workspace_files_factory.check().await?;
|
||||
|
||||
if workspace_test_options.no_run {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
let factories_with_specifiers =
|
||||
if let Some(changed_paths) = changed_paths {
|
||||
file_container
|
||||
.worker_factories_with_dependent_checked_specifiers(
|
||||
&changed_paths.into_iter().collect(),
|
||||
)
|
||||
.await?
|
||||
} else {
|
||||
file_container.worker_factories_with_checked_specifiers()
|
||||
};
|
||||
|
||||
test_specifiers(
|
||||
factories_with_specifiers,
|
||||
&permissions,
|
||||
permission_desc_parser,
|
||||
&workspace_files_factory,
|
||||
changed_paths.map(|p| p.into_iter().collect()).as_ref(),
|
||||
TestSpecifiersOptions {
|
||||
cwd: Url::from_directory_path(cli_options.initial_cwd()).map_err(
|
||||
|_| {
|
||||
|
|
Loading…
Add table
Reference in a new issue