summaryrefslogtreecommitdiff
path: root/runtime
diff options
context:
space:
mode:
authorMatt Mastracci <matthew@mastracci.com>2024-04-24 15:45:49 -0400
committerGitHub <noreply@github.com>2024-04-24 19:45:49 +0000
commit2f8825a935bfdf21ca592284556cd86c1552ac8d (patch)
tree68beddeb5547861212be188f126113e6b1afc1df /runtime
parentc1bd9503dd0288a3c209ca2724d2a1de9d5d122b (diff)
feat: Add `deno serve` subcommand (#23511)
By default, `deno serve` will assign port 8000 (like `Deno.serve`). Users may choose a different port using `--port`. `deno serve /tmp/file.ts` `server.ts`: ```ts export default { fetch(req) { return new Response("hello world!\n"); }, }; ```
Diffstat (limited to 'runtime')
-rw-r--r--runtime/js/99_main.js58
-rw-r--r--runtime/lib.rs1
-rw-r--r--runtime/worker_bootstrap.rs42
3 files changed, 101 insertions, 0 deletions
diff --git a/runtime/js/99_main.js b/runtime/js/99_main.js
index 8164e0c9a..59d2a1434 100644
--- a/runtime/js/99_main.js
+++ b/runtime/js/99_main.js
@@ -35,6 +35,7 @@ const {
ObjectAssign,
ObjectDefineProperties,
ObjectDefineProperty,
+ ObjectHasOwn,
ObjectKeys,
ObjectPrototypeIsPrototypeOf,
ObjectSetPrototypeOf,
@@ -52,6 +53,7 @@ const {
const {
isNativeError,
} = core;
+import { registerDeclarativeServer } from "ext:deno_http/00_serve.ts";
import * as event from "ext:deno_web/02_event.js";
import * as location from "ext:deno_web/12_location.js";
import * as version from "ext:runtime/01_version.ts";
@@ -679,6 +681,18 @@ const {
target,
} = op_snapshot_options();
+const executionModes = {
+ none: 0,
+ worker: 1,
+ run: 2,
+ repl: 3,
+ eval: 4,
+ test: 5,
+ bench: 6,
+ serve: 7,
+ jupyter: 8,
+};
+
function bootstrapMainRuntime(runtimeOptions, warmup = false) {
if (!warmup) {
if (hasBootstrapped) {
@@ -695,8 +709,52 @@ function bootstrapMainRuntime(runtimeOptions, warmup = false) {
7: shouldDisableDeprecatedApiWarning,
8: shouldUseVerboseDeprecatedApiWarning,
9: future,
+ 10: mode,
+ 11: servePort,
+ 12: serveHost,
} = runtimeOptions;
+ if (mode === executionModes.run || mode === executionModes.serve) {
+ let serve = undefined;
+ core.addMainModuleHandler((main) => {
+ if (ObjectHasOwn(main, "default")) {
+ try {
+ serve = registerDeclarativeServer(main.default);
+ } catch (e) {
+ if (mode === executionModes.serve) {
+ throw e;
+ }
+ }
+ }
+
+ if (mode === executionModes.serve && !serve) {
+ console.error(
+ `%cerror: %cdeno serve requires %cexport default { fetch }%c in the main module, did you mean to run \"deno run\"?`,
+ "color: yellow;",
+ "color: inherit;",
+ "font-weight: bold;",
+ "font-weight: normal;",
+ );
+ return;
+ }
+
+ if (serve) {
+ if (mode === executionModes.run) {
+ console.error(
+ `%cwarning: %cDetected %cexport default { fetch }%c, did you mean to run \"deno serve\"?`,
+ "color: yellow;",
+ "color: inherit;",
+ "font-weight: bold;",
+ "font-weight: normal;",
+ );
+ }
+ if (mode === executionModes.serve) {
+ serve({ servePort, serveHost });
+ }
+ }
+ });
+ }
+
// TODO(iuioiua): remove in Deno v2. This allows us to dynamically delete
// class properties within constructors for classes that are not defined
// within the Deno namespace.
diff --git a/runtime/lib.rs b/runtime/lib.rs
index f33e9b7e3..ec751f207 100644
--- a/runtime/lib.rs
+++ b/runtime/lib.rs
@@ -41,6 +41,7 @@ pub mod worker;
mod worker_bootstrap;
pub use worker_bootstrap::BootstrapOptions;
+pub use worker_bootstrap::WorkerExecutionMode;
pub use worker_bootstrap::WorkerLogLevel;
mod shared;
diff --git a/runtime/worker_bootstrap.rs b/runtime/worker_bootstrap.rs
index c019dae1a..ee3b81c62 100644
--- a/runtime/worker_bootstrap.rs
+++ b/runtime/worker_bootstrap.rs
@@ -4,10 +4,36 @@ use deno_core::v8;
use deno_core::ModuleSpecifier;
use serde::Serialize;
use std::cell::RefCell;
+use std::num::NonZeroU16;
use std::thread;
use deno_terminal::colors;
+/// The execution mode for this worker. Some modes may have implicit behaviour.
+#[derive(Copy, Clone)]
+#[repr(u8)]
+pub enum WorkerExecutionMode {
+ /// No special behaviour.
+ None,
+
+ /// Running in a worker.
+ Worker,
+ /// `deno run`
+ Run,
+ /// `deno repl`
+ Repl,
+ /// `deno eval`
+ Eval,
+ /// `deno test`
+ Test,
+ /// `deno bench`
+ Bench,
+ /// `deno serve`
+ Serve,
+ /// `deno jupyter`
+ Jupyter,
+}
+
/// The log level to use when printing diagnostic log messages, warnings,
/// or errors in the worker.
///
@@ -63,6 +89,10 @@ pub struct BootstrapOptions {
pub disable_deprecated_api_warning: bool,
pub verbose_deprecated_api_warning: bool,
pub future: bool,
+ pub mode: WorkerExecutionMode,
+ // Used by `deno serve`
+ pub serve_port: Option<NonZeroU16>,
+ pub serve_host: Option<String>,
}
impl Default for BootstrapOptions {
@@ -94,6 +124,9 @@ impl Default for BootstrapOptions {
disable_deprecated_api_warning: false,
verbose_deprecated_api_warning: false,
future: false,
+ mode: WorkerExecutionMode::None,
+ serve_port: Default::default(),
+ serve_host: Default::default(),
}
}
}
@@ -129,6 +162,12 @@ struct BootstrapV8<'a>(
bool,
// future
bool,
+ // mode
+ i32,
+ // serve port
+ u16,
+ // serve host
+ Option<&'a str>,
);
impl BootstrapOptions {
@@ -151,6 +190,9 @@ impl BootstrapOptions {
self.disable_deprecated_api_warning,
self.verbose_deprecated_api_warning,
self.future,
+ self.mode as u8 as _,
+ self.serve_port.map(|x| x.into()).unwrap_or_default(),
+ self.serve_host.as_deref(),
);
bootstrap.serialize(ser).unwrap()