0
0
Fork 0
mirror of https://github.com/denoland/deno.git synced 2025-03-03 17:34:47 -05:00

feat(test): Add support for "deno test --compat" (#13235)

This commit is contained in:
Steven Guerrero 2021-12-30 11:18:30 -05:00 committed by GitHub
parent 1adf8ee545
commit 39a6c94071
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
16 changed files with 220 additions and 36 deletions

View file

@ -102,15 +102,17 @@ fn try_resolve_builtin_module(specifier: &str) -> Option<Url> {
pub(crate) fn load_cjs_module(
js_runtime: &mut JsRuntime,
main_module: &str,
module: &str,
main: bool,
) -> Result<(), AnyError> {
let source_code = &format!(
r#"(async function loadCjsModule(main) {{
const Module = await import("{}");
Module.default._load(main, null, true);
}})('{}');"#,
MODULE_URL_STR.as_str(),
escape_for_single_quote_string(main_module),
r#"(async function loadCjsModule(module) {{
const Module = await import("{module_loader}");
Module.default._load(module, null, {main});
}})('{module}');"#,
module_loader = MODULE_URL_STR.as_str(),
main = main,
module = escape_for_single_quote_string(module),
);
js_runtime.execute_script(&located_script_name!(), source_code)?;

View file

@ -1174,6 +1174,7 @@ async fn run_command(
compat::load_cjs_module(
&mut worker.js_runtime,
&main_module.to_file_path().unwrap().display().to_string(),
true,
)?;
}
} else {

View file

@ -52,6 +52,44 @@ itest!(import_esm_from_cjs {
output_str: Some("function\n"),
});
itest!(test_runner_cjs {
args: "test --compat --unstable -A --quiet compat/test_runner/cjs.js",
exit_code: 1,
output: "compat/test_runner/cjs.out",
});
itest!(test_runner_esm {
args: "test --compat --unstable -A --quiet compat/test_runner/esm.mjs",
exit_code: 1,
output: "compat/test_runner/esm.out",
});
// Top level assertion test mostly just make sure that the test runner finishes correctly on compat mode
// when there is no tests
itest!(top_level_assertion_cjs {
args: "test --compat --unstable -A --quiet compat/test_runner/top_level_assertion_cjs.js",
exit_code: 0,
output: "compat/test_runner/top_level_assertion_cjs.out",
});
itest!(top_level_assertion_esm {
args: "test --compat --unstable -A --quiet compat/test_runner/top_level_assertion_esm.mjs",
exit_code: 0,
output: "compat/test_runner/top_level_assertion_esm.out",
});
itest!(top_level_fail_cjs {
args: "test --compat --unstable -A --quiet compat/test_runner/top_level_fail_cjs.js",
exit_code: 1,
output: "compat/test_runner/top_level_fail_cjs.out",
});
itest!(top_level_fail_esm {
args: "test --compat --unstable -A --quiet compat/test_runner/top_level_fail_esm.mjs",
exit_code: 1,
output: "compat/test_runner/top_level_fail_esm.out",
});
#[test]
fn globals_in_repl() {
let (out, _err) = util::run_and_collect_output_with_args(

View file

@ -0,0 +1,9 @@
const { strictEqual } = require("assert");
Deno.test("Correct assertion", () => {
strictEqual(20, 20);
});
Deno.test("Failed assertion", () => {
strictEqual(10, 20);
});

View file

@ -0,0 +1,25 @@
running 2 tests from [WILDCARD]
test Correct assertion ... ok ([WILDCARD])
test Failed assertion ... FAILED ([WILDCARD])
failures:
Failed assertion
AssertionError [ERR_ASSERTION]: Values are not strictly equal:
[Diff] Actual / Expected
- 10
+ 20
[WILDCARD]
failures:
[WILDCARD]Failed assertion
test result: FAILED. 1 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])
error: Test failed

View file

@ -0,0 +1,9 @@
import { strictEqual } from "assert";
Deno.test("Correct assertion", () => {
strictEqual(20, 20);
});
Deno.test("Failed assertion", () => {
strictEqual(10, 20);
});

View file

@ -0,0 +1,25 @@
running 2 tests from [WILDCARD]
test Correct assertion ... ok ([WILDCARD])
test Failed assertion ... FAILED ([WILDCARD])
failures:
Failed assertion
AssertionError [ERR_ASSERTION]: Values are not strictly equal:
[Diff] Actual / Expected
- 10
+ 20
[WILDCARD]
failures:
[WILDCARD]Failed assertion
test result: FAILED. 1 passed; 1 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])
error: Test failed

View file

@ -0,0 +1,4 @@
const { notStrictEqual, strictEqual } = require("assert");
notStrictEqual(require.main, module, "The module was loaded as a main module");
strictEqual(20, 20);

View file

@ -0,0 +1,4 @@
running 0 tests from [WILDCARD]
test result: ok. 0 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])

View file

@ -0,0 +1,4 @@
import assert, { strictEqual } from "assert";
assert(!import.meta.main, "The module was loaded as a main module");
strictEqual(20, 20);

View file

@ -0,0 +1,4 @@
running 0 tests from [WILDCARD]
test result: ok. 0 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])

View file

@ -0,0 +1,4 @@
const { notStrictEqual, strictEqual } = require("assert");
notStrictEqual(require.main, module, "The module was loaded as a main module");
strictEqual(10, 20);

View file

@ -0,0 +1,13 @@
test result: ok. 0 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])
error: Uncaught (in promise) AssertionError: Values are not strictly equal:
[Diff] Actual / Expected
- 10
+ 20
[WILDCARD]

View file

@ -0,0 +1,4 @@
import assert, { strictEqual } from "assert";
assert(!import.meta.main, "The module was loaded as a main module");
strictEqual(10, 20);

View file

@ -0,0 +1,13 @@
test result: ok. 0 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out ([WILDCARD])
error: Uncaught AssertionError: Values are not strictly equal:
[Diff] Actual / Expected
- 10
+ 20
[WILDCARD]

View file

@ -4,6 +4,7 @@ use crate::ast::Location;
use crate::cache;
use crate::cache::CacherLoader;
use crate::colors;
use crate::compat;
use crate::create_main_worker;
use crate::emit;
use crate::file_fetcher::File;
@ -150,6 +151,15 @@ pub struct TestSummary {
pub failures: Vec<(TestDescription, String)>,
}
#[derive(Debug, Clone, Deserialize)]
struct TestSpecifierOptions {
compat_mode: bool,
concurrent_jobs: NonZeroUsize,
fail_fast: Option<NonZeroUsize>,
filter: Option<String>,
shuffle: Option<u64>,
}
impl TestSummary {
fn new() -> TestSummary {
TestSummary {
@ -448,9 +458,8 @@ async fn test_specifier(
permissions: Permissions,
specifier: ModuleSpecifier,
mode: TestMode,
filter: Option<String>,
shuffle: Option<u64>,
channel: Sender<TestEvent>,
options: TestSpecifierOptions,
) -> Result<(), AnyError> {
let mut worker = create_main_worker(
&ps,
@ -477,8 +486,26 @@ async fn test_specifier(
// We only execute the specifier as a module if it is tagged with TestMode::Module or
// TestMode::Both.
if mode != TestMode::Documentation {
// We execute the module module as a side module so that import.meta.main is not set.
worker.execute_side_module(&specifier).await?;
if options.compat_mode {
worker.execute_side_module(&compat::GLOBAL_URL).await?;
worker.execute_side_module(&compat::MODULE_URL).await?;
let use_esm_loader = compat::check_if_should_use_esm_loader(&specifier)?;
if use_esm_loader {
worker.execute_side_module(&specifier).await?;
} else {
compat::load_cjs_module(
&mut worker.js_runtime,
&specifier.to_file_path().unwrap().display().to_string(),
false,
)?;
worker.run_event_loop(false).await?;
}
} else {
// We execute the module module as a side module so that import.meta.main is not set.
worker.execute_side_module(&specifier).await?;
}
}
worker.dispatch_load_event(&located_script_name!())?;
@ -488,8 +515,8 @@ async fn test_specifier(
&format!(
r#"Deno[Deno.internal].runTests({})"#,
json!({
"filter": filter,
"shuffle": shuffle,
"filter": options.filter,
"shuffle": options.shuffle,
}),
),
)?;
@ -758,13 +785,10 @@ async fn test_specifiers(
ps: ProcState,
permissions: Permissions,
specifiers_with_mode: Vec<(ModuleSpecifier, TestMode)>,
fail_fast: Option<NonZeroUsize>,
filter: Option<String>,
shuffle: Option<u64>,
concurrent_jobs: NonZeroUsize,
options: TestSpecifierOptions,
) -> Result<(), AnyError> {
let log_level = ps.flags.log_level;
let specifiers_with_mode = if let Some(seed) = shuffle {
let specifiers_with_mode = if let Some(seed) = options.shuffle {
let mut rng = SmallRng::seed_from_u64(seed);
let mut specifiers_with_mode = specifiers_with_mode.clone();
specifiers_with_mode.sort_by_key(|(specifier, _)| specifier.clone());
@ -775,6 +799,8 @@ async fn test_specifiers(
};
let (sender, receiver) = channel::<TestEvent>();
let concurrent_jobs = options.concurrent_jobs;
let fail_fast = options.fail_fast;
let join_handles =
specifiers_with_mode.iter().map(move |(specifier, mode)| {
@ -782,20 +808,13 @@ async fn test_specifiers(
let permissions = permissions.clone();
let specifier = specifier.clone();
let mode = mode.clone();
let filter = filter.clone();
let sender = sender.clone();
let options = options.clone();
tokio::task::spawn_blocking(move || {
let join_handle = std::thread::spawn(move || {
let future = test_specifier(
ps,
permissions,
specifier,
mode,
filter,
shuffle,
sender,
);
let future =
test_specifier(ps, permissions, specifier, mode, sender, options);
run_basic(future)
});
@ -1029,10 +1048,13 @@ pub async fn run_tests(
ps,
permissions,
specifiers_with_mode,
test_flags.fail_fast,
test_flags.filter,
test_flags.shuffle,
test_flags.concurrent_jobs,
TestSpecifierOptions {
compat_mode: flags.compat,
concurrent_jobs: test_flags.concurrent_jobs,
fail_fast: test_flags.fail_fast,
filter: test_flags.filter,
shuffle: test_flags.shuffle,
},
)
.await?;
@ -1256,10 +1278,13 @@ pub async fn run_tests_with_watch(
ps.clone(),
permissions.clone(),
specifiers_with_mode,
test_flags.fail_fast,
filter.clone(),
test_flags.shuffle,
test_flags.concurrent_jobs,
TestSpecifierOptions {
compat_mode: flags.compat,
concurrent_jobs: test_flags.concurrent_jobs,
fail_fast: test_flags.fail_fast,
filter: filter.clone(),
shuffle: test_flags.shuffle,
},
)
.await?;