From 286e5d0be9bb11a69d55f0eedd4a6678b0d48e7d Mon Sep 17 00:00:00 2001 From: Leo Kettmeir Date: Wed, 8 Feb 2023 22:40:18 +0100 Subject: refactor: internal runtime code TS support (#17672) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is a proof of concept for being able to snapshot TypeScript files. Currently only a single runtime file is authored in TypeScript - "runtime/js/01_version.ts". Not needed infrastructure was removed from "core/snapshot_util.rs". --------- Co-authored-by: Bartek IwaƄczuk --- runtime/Cargo.toml | 1 + runtime/build.rs | 87 ++++++++++++++++++++++++++++++++++++++++-------- runtime/js.rs | 8 ++--- runtime/js/01_version.js | 24 ------------- runtime/js/01_version.ts | 30 +++++++++++++++++ runtime/js/90_deno_ns.js | 2 +- runtime/js/99_main.js | 2 +- 7 files changed, 109 insertions(+), 45 deletions(-) delete mode 100644 runtime/js/01_version.js create mode 100644 runtime/js/01_version.ts (limited to 'runtime') diff --git a/runtime/Cargo.toml b/runtime/Cargo.toml index 039bb5293..2d93f9dff 100644 --- a/runtime/Cargo.toml +++ b/runtime/Cargo.toml @@ -24,6 +24,7 @@ name = "hello_runtime" path = "examples/hello_runtime.rs" [build-dependencies] +deno_ast.workspace = true deno_broadcast_channel.workspace = true deno_cache.workspace = true deno_console.workspace = true diff --git a/runtime/build.rs b/runtime/build.rs index bba4394f8..e892e7485 100644 --- a/runtime/build.rs +++ b/runtime/build.rs @@ -1,7 +1,7 @@ // Copyright 2018-2023 the Deno authors. All rights reserved. MIT license. +use deno_core::include_js_files_dir; use std::env; - use std::path::PathBuf; // This is a shim that allows to generate documentation on docs.rs @@ -13,6 +13,39 @@ mod not_docs { use deno_core::snapshot_util::*; use deno_core::Extension; + use deno_ast::MediaType; + use deno_ast::ParseParams; + use deno_ast::SourceTextInfo; + use deno_core::error::AnyError; + use deno_core::ExtensionFileSource; + + fn transpile_ts_for_snapshotting( + file_source: &ExtensionFileSource, + ) -> Result { + let media_type = MediaType::from(Path::new(&file_source.specifier)); + + let should_transpile = match media_type { + MediaType::JavaScript => false, + MediaType::TypeScript => true, + _ => panic!("Unsupported media type for snapshotting {media_type:?}"), + }; + + if !should_transpile { + return Ok(file_source.code.to_string()); + } + + let parsed = deno_ast::parse_module(ParseParams { + specifier: file_source.specifier.to_string(), + text_info: SourceTextInfo::from_string(file_source.code.to_string()), + media_type, + capture_tokens: false, + scope_analysis: false, + maybe_syntax: None, + })?; + let transpiled_source = parsed.transpile(&Default::default())?; + Ok(transpiled_source.text) + } + struct Permissions; impl deno_fetch::FetchPermissions for Permissions { @@ -120,7 +153,10 @@ mod not_docs { } } - fn create_runtime_snapshot(snapshot_path: PathBuf, esm_files: Vec) { + fn create_runtime_snapshot( + snapshot_path: PathBuf, + additional_extension: Extension, + ) { let extensions_with_js: Vec = vec![ deno_webidl::init(), deno_console::init(), @@ -149,6 +185,7 @@ mod not_docs { deno_napi::init::(false), deno_http::init(), deno_flash::init::(false), // No --unstable + additional_extension, ]; create_snapshot(CreateSnapshotOptions { @@ -157,8 +194,6 @@ mod not_docs { startup_snapshot: None, extensions: vec![], extensions_with_js, - additional_files: vec![], - additional_esm_files: esm_files, compression_cb: Some(Box::new(|vec, snapshot_slice| { lzzzz::lz4_hc::compress_to_vec( snapshot_slice, @@ -167,24 +202,50 @@ mod not_docs { ) .expect("snapshot compression failed"); })), + snapshot_module_load_cb: Some(Box::new(transpile_ts_for_snapshotting)), }); } pub fn build_snapshot(runtime_snapshot_path: PathBuf) { - #[allow(unused_mut)] - let mut esm_files = get_js_files( - env!("CARGO_MANIFEST_DIR"), - "js", - Some(Box::new(|path| !path.ends_with("99_main.js"))), + #[allow(unused_mut, unused_assignments)] + let mut esm_files = include_js_files_dir!( + dir "js", + "01_build.js", + "01_errors.js", + "01_version.ts", + "06_util.js", + "10_permissions.js", + "11_workers.js", + "12_io.js", + "13_buffer.js", + "30_fs.js", + "30_os.js", + "40_diagnostics.js", + "40_files.js", + "40_fs_events.js", + "40_http.js", + "40_process.js", + "40_read_file.js", + "40_signals.js", + "40_spawn.js", + "40_tty.js", + "40_write_file.js", + "41_prompt.js", + "90_deno_ns.js", + "98_global_scope.js", ); #[cfg(not(feature = "snapshot_from_snapshot"))] { - let manifest = env!("CARGO_MANIFEST_DIR"); - let path = PathBuf::from(manifest); - esm_files.push(path.join("js").join("99_main.js")); + esm_files.push(ExtensionFileSource { + specifier: "js/99_main.js".to_string(), + code: include_str!("js/99_main.js"), + }); } - create_runtime_snapshot(runtime_snapshot_path, esm_files); + + let additional_extension = + Extension::builder("runtime").esm(esm_files).build(); + create_runtime_snapshot(runtime_snapshot_path, additional_extension); } } diff --git a/runtime/js.rs b/runtime/js.rs index 3d14c744c..82e58a09c 100644 --- a/runtime/js.rs +++ b/runtime/js.rs @@ -2,7 +2,6 @@ use deno_core::Snapshot; use log::debug; use once_cell::sync::Lazy; -use std::path::PathBuf; pub static RUNTIME_SNAPSHOT: Lazy> = Lazy::new( #[allow(clippy::uninit_vec)] @@ -35,8 +34,5 @@ pub fn deno_isolate_init() -> Snapshot { Snapshot::Static(&RUNTIME_SNAPSHOT) } -pub fn get_99_main() -> PathBuf { - let manifest = env!("CARGO_MANIFEST_DIR"); - let path = PathBuf::from(manifest); - path.join("js").join("99_main.js") -} +#[cfg(feature = "snapshot_from_snapshot")] +pub static SOURCE_CODE_FOR_99_MAIN_JS: &str = include_str!("js/99_main.js"); diff --git a/runtime/js/01_version.js b/runtime/js/01_version.js deleted file mode 100644 index 62f3df17c..000000000 --- a/runtime/js/01_version.js +++ /dev/null @@ -1,24 +0,0 @@ -// Copyright 2018-2023 the Deno authors. All rights reserved. MIT license. - -const primordials = globalThis.__bootstrap.primordials; -const { ObjectFreeze } = primordials; - -const version = { - deno: "", - v8: "", - typescript: "", -}; - -function setVersions( - denoVersion, - v8Version, - tsVersion, -) { - version.deno = denoVersion; - version.v8 = v8Version; - version.typescript = tsVersion; - - ObjectFreeze(version); -} - -export { setVersions, version }; diff --git a/runtime/js/01_version.ts b/runtime/js/01_version.ts new file mode 100644 index 000000000..cbbbd8d03 --- /dev/null +++ b/runtime/js/01_version.ts @@ -0,0 +1,30 @@ +// Copyright 2018-2023 the Deno authors. All rights reserved. MIT license. + +const primordials = globalThis.__bootstrap.primordials; +const { ObjectFreeze } = primordials; + +interface Version { + deno: string; + v8: string; + typescript: string; +} + +const version: Version = { + deno: "", + v8: "", + typescript: "", +}; + +function setVersions( + denoVersion, + v8Version, + tsVersion, +) { + version.deno = denoVersion; + version.v8 = v8Version; + version.typescript = tsVersion; + + ObjectFreeze(version); +} + +export { setVersions, version }; diff --git a/runtime/js/90_deno_ns.js b/runtime/js/90_deno_ns.js index 5321bf1d3..fe59ea1a7 100644 --- a/runtime/js/90_deno_ns.js +++ b/runtime/js/90_deno_ns.js @@ -12,7 +12,7 @@ import * as http from "internal:deno_http/01_http.js"; import * as flash from "internal:deno_flash/01_http.js"; import * as build from "internal:runtime/js/01_build.js"; import * as errors from "internal:runtime/js/01_errors.js"; -import * as version from "internal:runtime/js/01_version.js"; +import * as version from "internal:runtime/js/01_version.ts"; import * as permissions from "internal:runtime/js/10_permissions.js"; import * as io from "internal:runtime/js/12_io.js"; import * as buffer from "internal:runtime/js/13_buffer.js"; diff --git a/runtime/js/99_main.js b/runtime/js/99_main.js index 5d9012bc4..fd7b93e24 100644 --- a/runtime/js/99_main.js +++ b/runtime/js/99_main.js @@ -43,7 +43,7 @@ import * as util from "internal:runtime/js/06_util.js"; import * as event from "internal:deno_web/02_event.js"; import * as location from "internal:deno_web/12_location.js"; import * as build from "internal:runtime/js/01_build.js"; -import * as version from "internal:runtime/js/01_version.js"; +import * as version from "internal:runtime/js/01_version.ts"; import * as os from "internal:runtime/js/30_os.js"; import * as timers from "internal:deno_web/02_timers.js"; import * as colors from "internal:deno_console/01_colors.js"; -- cgit v1.2.3