The Runtime Core is the foundational layer of Deno that bridges JavaScript execution with the operating system through V8 and Rust. This page provides an overview of:
globalThis and the Deno namespaceFileSystem trait and implementationsFor CLI-level concerns like argument parsing and module loading, see CLI Architecture. For specific extension implementations (HTTP, WebSocket, Crypto, etc.), see their dedicated pages. For Node.js compatibility, see Node.js Compatibility Layer.
The Deno runtime is structured in three layers: Rust (deno_core + extensions), JavaScript (bootstrap and runtime modules), and the execution environment (workers).
Deno Runtime Layering
Sources: runtime/Cargo.toml40-76 runtime/js/99_main.js1-50 ext/fs/lib.rs26-72 Cargo.toml5-61
The runtime bootstrap occurs in two phases: Rust initialization followed by JavaScript setup.
Runtime initialization begins with the BootstrapOptions struct and creates a JsRuntime with V8:
Bootstrap Initialization Flow
The WorkerExecutionMode enum in runtime/worker_bootstrap.rs14-36 defines execution contexts:
| Mode | Description | Behavior |
|---|---|---|
None | No special mode | Standard execution |
Worker | Web worker thread | Limited APIs, message passing |
Run | deno run | Default execution mode |
Repl | deno repl | Interactive mode with special hooks |
Test | deno test | Test harness enabled |
Bench | deno bench | Benchmark harness enabled |
ServeMain | deno serve main | HTTP server with worker pool |
ServeWorker | deno serve worker | HTTP request handler |
Sources: runtime/worker_bootstrap.rs14-36 runtime/worker_bootstrap.rs38-150
JavaScript bootstrap in runtime/js/99_main.js sets up the runtime environment:
JavaScript Bootstrap Sequence
Key bootstrap functions in runtime/js/99_main.js:
| Function | Lines | Purpose |
|---|---|---|
runtimeStart() | 394-409 | Initializes callbacks, sets version info |
bootstrap.mainRuntime() | 479-620 | Main worker setup with window APIs and Deno namespace |
bootstrap.workerRuntime() | 621-end | Web worker setup with message passing |
formatException() | 306-321 | Formats uncaught exceptions |
Sources: runtime/js/99_main.js394-409 runtime/js/99_main.js479-800
Extensions are modular units that provide functionality to the runtime through ops (operations) and JavaScript code.
Extensions are defined using the deno_core::extension! macro. Example from deno_fs:
Extension Macro Structure (deno_fs example)
The deno_fs extension in ext/fs/lib.rs26-72 registers:
| Component | Content | Example |
|---|---|---|
deps | Dependencies | deno_web (for streams) |
ops | 50+ operations | op_fs_open_sync, op_fs_read_file_async, op_fs_mkdir_sync |
esm | JavaScript modules | 30_fs.js |
esm_entry_point | Entry module | ext:deno_fs/30_fs.js |
Sources: ext/fs/lib.rs26-72 ext/node/lib.rs144-327
Ops bridge JavaScript and Rust using the #[op2] macro. They are invoked via core.ops.* in JavaScript.
Op Invocation Flow
Common op patterns in ext/fs/ops.rs:
| Pattern | Declaration | Example | Behavior |
|---|---|---|---|
| Sync | #[op2] | op_fs_open_sync | Blocks thread |
| Async | #[op2(async)] | op_fs_open_async | Returns Future, non-blocking |
| Fast | #[op2(fast)] | op_fs_chmod_sync | Optimized, fewer type checks |
| String return | #[op2] #[string] | op_fs_cwd | Returns String |
| Resource | Takes ResourceId | Uses state.resource_table | Operates on managed resources |
Sources: ext/fs/ops.rs70-200 ext/fs/30_fs.js1-100
OpState is a per-isolate type-map storing shared state accessible to all ops:
OpState Structure
Example op accessing OpState in ext/fs/ops.rs400-420:
Sources: ext/fs/ops.rs400-500 ext/io/lib.rs1-100
The global environment is constructed by layering web APIs, primordials, and Deno-specific APIs:
Global Environment Construction
Sources: runtime/js/99_main.js477-550 runtime/js/90_deno_ns.js runtime/js/98_global_scope_shared.js
The Deno namespace is assembled from multiple modules:
Deno Namespace Assembly
| Source File | Exports | Example APIs |
|---|---|---|
90_deno_ns.js | denoNs | Deno.readFile, Deno.writeFile, Deno.mkdir |
90_deno_ns.js | denoNsUnstableById | Feature-gated: Deno.Kv, Deno.cron |
98_global_scope_window.js | Main worker only | Deno.exit, Deno.mainModule |
Sources: runtime/js/99_main.js73-76 runtime/js/99_main.js515-545
Primordials are captured references to built-in JavaScript objects to prevent tampering:
Sources: runtime/js/99_main.js28-50
The permission system enforces security boundaries at the runtime level.
Permission Enforcement System
Sources: ext/fs/ops.rs400-450
Example from ext/fs/ops.rs400-450 showing typical permission check:
Sources: ext/fs/ops.rs400-500
CheckedPathBuf ensures paths are validated before use. It prevents time-of-check-to-time-of-use vulnerabilities:
CheckedPathBuf Flow
The CheckedPathBuf type guarantees the path was permission-checked. FileSystem trait methods accept &CheckedPath to enforce this:
Sources: ext/fs/ops.rs400-420 ext/fs/interface.rs60-100
The file system is abstracted through the FileSystem trait, allowing different implementations.
The FileSystem trait in ext/fs/interface.rs abstracts file system operations:
FileSystem Trait Design
Sources: ext/fs/interface.rs30-200 ext/fs/std_fs.rs29-33 ext/fs/lib.rs26-30
RealFs in ext/fs/std_fs.rs29-33 implements FileSystem using std::fs:
| FileSystem Method | Implementation | Description |
|---|---|---|
cwd() | std::env::current_dir() | Current working directory |
open_sync() | std::fs::File::open() | Synchronous file open |
open_async() | `spawn_blocking( | |
read_file_sync() | std::fs::read() | Read entire file into Vec |
read_file_async() | `spawn_blocking( | |
mkdir_sync() | std::fs::create_dir_all() | Create directory recursively |
stat_sync() | path.metadata() | Get file metadata |
lstat_sync() | path.symlink_metadata() | Get symlink metadata |
The spawn_blocking function from deno_core runs blocking operations on a thread pool to avoid blocking the event loop.
Sources: ext/fs/std_fs.rs29-600
Example: Deno.readFile(path) execution flow
Deno.readFile Execution
Sources: ext/fs/ops.rs700-850 ext/fs/30_fs.js400-450 ext/fs/std_fs.rs200-250
File handles and other resources are managed via ResourceTable using ResourceId (RID):
Resource Lifecycle
Example resource management in ext/io/lib.rs200-250:
Sources: ext/io/lib.rs200-350 ext/fs/ops.rs400-450
Runtime errors are registered in runtime/js/99_main.js323-392 to map Rust errors to JavaScript exception types:
Error Registration
Common error classes registered in runtime/js/99_main.js323-392:
| Error Class | Mapped Rust Error | JavaScript Constructor |
|---|---|---|
NotFound | io::ErrorKind::NotFound | Deno.errors.NotFound |
PermissionDenied | PermissionCheckError | Deno.errors.PermissionDenied |
AlreadyExists | io::ErrorKind::AlreadyExists | Deno.errors.AlreadyExists |
BrokenPipe | io::ErrorKind::BrokenPipe | Deno.errors.BrokenPipe |
ConnectionRefused | io::ErrorKind::ConnectionRefused | Deno.errors.ConnectionRefused |
InvalidData | io::ErrorKind::InvalidData | Deno.errors.InvalidData |
TimedOut | io::ErrorKind::TimedOut | Deno.errors.TimedOut |
DOMException error builders are also registered for web compatibility:
DOMExceptionOperationErrorDOMExceptionQuotaExceededErrorDOMExceptionNetworkErrorDOMExceptionAbortErrorSources: runtime/js/99_main.js323-392
The runtime supports two types of workers:
Worker Type Comparison
Key differences in runtime/js/99_main.js479-800:
| Aspect | MainWorker | WebWorker |
|---|---|---|
| Bootstrap function | bootstrapMainRuntime() | bootstrapWorkerRuntime() |
close() behavior | Exits process | Closes worker thread |
Deno.exit() | Available | Not available |
| stdio | Direct access | Not available |
| Communication | N/A | postMessage() / onmessage |
Sources: runtime/js/99_main.js479-800
Sources: runtime/js/99_main.js165-192 runtime/js/99_main.js207-259
Refresh this wiki