diff --git a/Cargo.lock b/Cargo.lock
index 928464fcf18b51..c199cf560f504f 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -635,8 +635,10 @@ dependencies = [
"deno_core",
"deno_crypto",
"deno_fetch",
+ "deno_url",
"deno_web",
"deno_webgpu",
+ "deno_webidl",
"deno_websocket",
"dlopen",
"encoding_rs",
@@ -668,13 +670,21 @@ dependencies = [
"winres",
]
+[[package]]
+name = "deno_url"
+version = "0.1.0"
+dependencies = [
+ "deno_core",
+ "idna",
+ "serde",
+]
+
[[package]]
name = "deno_web"
version = "0.30.3"
dependencies = [
"deno_core",
"futures",
- "serde",
]
[[package]]
@@ -688,6 +698,13 @@ dependencies = [
"wgpu-types",
]
+[[package]]
+name = "deno_webidl"
+version = "0.1.0"
+dependencies = [
+ "deno_core",
+]
+
[[package]]
name = "deno_websocket"
version = "0.5.3"
diff --git a/Cargo.toml b/Cargo.toml
index 8a5f1021c46476..e89ca19b7bee56 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -7,9 +7,13 @@ members = [
"runtime",
"test_plugin",
"test_util",
+ "op_crates/crypto",
"op_crates/fetch",
+ "op_crates/url",
"op_crates/web",
- "op_crates/crypto"
+ "op_crates/webgpu",
+ "op_crates/webidl",
+ "op_crates/websocket",
]
exclude = [
"std/hash/_wasm"
diff --git a/cli/build.rs b/cli/build.rs
index 236097cbf88c99..3f97a71b7465b9 100644
--- a/cli/build.rs
+++ b/cli/build.rs
@@ -10,6 +10,7 @@ use deno_core::JsRuntime;
use deno_core::RuntimeOptions;
use deno_runtime::deno_crypto;
use deno_runtime::deno_fetch;
+use deno_runtime::deno_url;
use deno_runtime::deno_web;
use deno_runtime::deno_webgpu;
use deno_runtime::deno_websocket;
@@ -61,6 +62,7 @@ fn create_compiler_snapshot(
) {
// libs that are being provided by op crates.
let mut op_crate_libs = HashMap::new();
+ op_crate_libs.insert("deno.url", deno_url::get_declaration());
op_crate_libs.insert("deno.web", deno_web::get_declaration());
op_crate_libs.insert("deno.fetch", deno_fetch::get_declaration());
op_crate_libs.insert("deno.webgpu", deno_webgpu::get_declaration());
@@ -254,6 +256,10 @@ fn main() {
println!("cargo:rustc-env=TS_VERSION={}", ts_version());
println!("cargo:rustc-env=GIT_COMMIT_HASH={}", git_commit_hash());
+ println!(
+ "cargo:rustc-env=DENO_URL_LIB_PATH={}",
+ deno_url::get_declaration().display()
+ );
println!(
"cargo:rustc-env=DENO_WEB_LIB_PATH={}",
deno_web::get_declaration().display()
diff --git a/cli/dts/lib.deno.shared_globals.d.ts b/cli/dts/lib.deno.shared_globals.d.ts
index 4332b757b1a02b..206cafdc3002c9 100644
--- a/cli/dts/lib.deno.shared_globals.d.ts
+++ b/cli/dts/lib.deno.shared_globals.d.ts
@@ -5,6 +5,7 @@
///
///
+///
///
///
///
diff --git a/cli/main.rs b/cli/main.rs
index 93639d34f7266e..8d685c6dbe8224 100644
--- a/cli/main.rs
+++ b/cli/main.rs
@@ -278,8 +278,9 @@ fn print_cache_info(
pub fn get_types(unstable: bool) -> String {
let mut types = format!(
- "{}\n{}\n{}\n{}\n{}\n{}\n{}",
+ "{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}",
crate::tsc::DENO_NS_LIB,
+ crate::tsc::DENO_URL_LIB,
crate::tsc::DENO_WEB_LIB,
crate::tsc::DENO_FETCH_LIB,
crate::tsc::DENO_WEBGPU_LIB,
diff --git a/cli/tsc.rs b/cli/tsc.rs
index 8d28b959d37d41..6bf8546509f737 100644
--- a/cli/tsc.rs
+++ b/cli/tsc.rs
@@ -29,6 +29,7 @@ use std::sync::Mutex;
// Declaration files
pub static DENO_NS_LIB: &str = include_str!("dts/lib.deno.ns.d.ts");
+pub static DENO_URL_LIB: &str = include_str!(env!("DENO_URL_LIB_PATH"));
pub static DENO_WEB_LIB: &str = include_str!(env!("DENO_WEB_LIB_PATH"));
pub static DENO_FETCH_LIB: &str = include_str!(env!("DENO_FETCH_LIB_PATH"));
pub static DENO_WEBGPU_LIB: &str = include_str!(env!("DENO_WEBGPU_LIB_PATH"));
diff --git a/op_crates/crypto/Cargo.toml b/op_crates/crypto/Cargo.toml
index 3d5af740e45699..8b0d2d3fa451c5 100644
--- a/op_crates/crypto/Cargo.toml
+++ b/op_crates/crypto/Cargo.toml
@@ -4,7 +4,7 @@
name = "deno_crypto"
version = "0.14.1"
edition = "2018"
-description = "Collection of WebCrypto APIs"
+description = "Web Cryptography API implementation for Deno"
authors = ["the Deno authors"]
license = "MIT"
readme = "README.md"
diff --git a/op_crates/crypto/README.md b/op_crates/crypto/README.md
index 0e1c248e64ce46..be07244584e75b 100644
--- a/op_crates/crypto/README.md
+++ b/op_crates/crypto/README.md
@@ -1,3 +1,5 @@
-# deno crypto
+# deno_crypto
-Op crate that implements crypto functions.
+This crate implements the Web Cryptography API.
+
+Spec: https://www.w3.org/TR/WebCryptoAPI/
diff --git a/op_crates/fetch/Cargo.toml b/op_crates/fetch/Cargo.toml
index 9491b87a36b71f..57a56d7409c0f9 100644
--- a/op_crates/fetch/Cargo.toml
+++ b/op_crates/fetch/Cargo.toml
@@ -4,7 +4,7 @@
name = "deno_fetch"
version = "0.22.3"
edition = "2018"
-description = "provides fetch Web API to deno_core"
+description = "Fetch API implementation for Deno"
authors = ["the Deno authors"]
license = "MIT"
readme = "README.md"
diff --git a/op_crates/fetch/README.md b/op_crates/fetch/README.md
index 1a6dcab1745c09..2c946197e053bc 100644
--- a/op_crates/fetch/README.md
+++ b/op_crates/fetch/README.md
@@ -1 +1,5 @@
-This crate provides the web standard fetch API to `deno_core`.
+# deno_fetch
+
+This crate implements the Fetch API.
+
+Spec: https://fetch.spec.whatwg.org/
diff --git a/op_crates/web/11_url.js b/op_crates/url/00_url.js
similarity index 90%
rename from op_crates/web/11_url.js
rename to op_crates/url/00_url.js
index d8f5bd5f7a9e00..9dd2b78007c3b5 100644
--- a/op_crates/web/11_url.js
+++ b/op_crates/url/00_url.js
@@ -28,7 +28,7 @@
init = init.slice(1);
}
- this.#params = core.jsonOpSync("op_parse_url_search_params", init);
+ this.#params = core.jsonOpSync("op_url_parse_search_params", init);
} else if (
Array.isArray(init) ||
typeof init?.[Symbol.iterator] == "function"
@@ -64,7 +64,7 @@
return;
}
const parseArgs = { href: url.href, setSearch: this.toString() };
- parts.set(url, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(url, core.jsonOpSync("op_url_parse", parseArgs));
};
append(name, value) {
@@ -189,7 +189,7 @@
}
toString() {
- return core.jsonOpSync("op_stringify_url_search_params", this.#params);
+ return core.jsonOpSync("op_url_stringify_search_params", this.#params);
}
}
@@ -206,7 +206,7 @@
} else {
base = base !== undefined ? String(base) : base;
const parseArgs = { href: String(url), baseHref: base };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
}
}
@@ -231,7 +231,7 @@
if (this.#searchParams != null) {
const params = paramLists.get(this.#searchParams);
const newParams = core.jsonOpSync(
- "op_parse_url_search_params",
+ "op_url_parse_search_params",
this.search.slice(1),
);
params.splice(0, params.length, ...newParams);
@@ -245,7 +245,7 @@
set hash(value) {
try {
const parseArgs = { href: this.href, setHash: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -258,7 +258,7 @@
set host(value) {
try {
const parseArgs = { href: this.href, setHost: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -271,7 +271,7 @@
set hostname(value) {
try {
const parseArgs = { href: this.href, setHostname: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -284,7 +284,7 @@
set href(value) {
try {
const parseArgs = { href: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
throw new TypeError("Invalid URL");
}
@@ -302,7 +302,7 @@
set password(value) {
try {
const parseArgs = { href: this.href, setPassword: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -315,7 +315,7 @@
set pathname(value) {
try {
const parseArgs = { href: this.href, setPathname: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -328,7 +328,7 @@
set port(value) {
try {
const parseArgs = { href: this.href, setPort: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -341,7 +341,7 @@
set protocol(value) {
try {
const parseArgs = { href: this.href, setProtocol: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
@@ -354,7 +354,7 @@
set search(value) {
try {
const parseArgs = { href: this.href, setSearch: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
this.#updateSearchParams();
} catch {
/* pass */
@@ -368,7 +368,7 @@
set username(value) {
try {
const parseArgs = { href: this.href, setUsername: String(value) };
- parts.set(this, core.jsonOpSync("op_parse_url", parseArgs));
+ parts.set(this, core.jsonOpSync("op_url_parse", parseArgs));
} catch {
/* pass */
}
diff --git a/op_crates/url/Cargo.toml b/op_crates/url/Cargo.toml
new file mode 100644
index 00000000000000..a07bfc7d3aae1d
--- /dev/null
+++ b/op_crates/url/Cargo.toml
@@ -0,0 +1,19 @@
+# Copyright 2018-2020 the Deno authors. All rights reserved. MIT license.
+
+[package]
+name = "deno_url"
+version = "0.1.0"
+edition = "2018"
+description = "URL API implementation for Deno"
+authors = ["the Deno authors"]
+license = "MIT"
+readme = "README.md"
+repository = "https://github.com/denoland/deno"
+
+[lib]
+path = "lib.rs"
+
+[dependencies]
+deno_core = { version = "0.80.2", path = "../../core" }
+idna = "0.2.1"
+serde = { version = "1.0.123", features = ["derive"] }
diff --git a/op_crates/url/README.md b/op_crates/url/README.md
new file mode 100644
index 00000000000000..991dd8b20078ad
--- /dev/null
+++ b/op_crates/url/README.md
@@ -0,0 +1,5 @@
+# deno_url
+
+This crate implements the URL API for Deno.
+
+Spec: https://url.spec.whatwg.org/
diff --git a/op_crates/url/internal.d.ts b/op_crates/url/internal.d.ts
new file mode 100644
index 00000000000000..f852928d354e9b
--- /dev/null
+++ b/op_crates/url/internal.d.ts
@@ -0,0 +1,13 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+
+///
+///
+
+declare namespace globalThis {
+ declare namespace __bootstrap {
+ declare var url: {
+ URL: typeof URL;
+ URLSearchParams: typeof URLSearchParams;
+ };
+ }
+}
diff --git a/op_crates/url/lib.deno_url.d.ts b/op_crates/url/lib.deno_url.d.ts
new file mode 100644
index 00000000000000..2a27fe6933692e
--- /dev/null
+++ b/op_crates/url/lib.deno_url.d.ts
@@ -0,0 +1,175 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+
+// deno-lint-ignore-file no-explicit-any
+
+///
+///
+
+declare class URLSearchParams {
+ constructor(
+ init?: string[][] | Record | string | URLSearchParams,
+ );
+ static toString(): string;
+
+ /** Appends a specified key/value pair as a new search parameter.
+ *
+ * ```ts
+ * let searchParams = new URLSearchParams();
+ * searchParams.append('name', 'first');
+ * searchParams.append('name', 'second');
+ * ```
+ */
+ append(name: string, value: string): void;
+
+ /** Deletes the given search parameter and its associated value,
+ * from the list of all search parameters.
+ *
+ * ```ts
+ * let searchParams = new URLSearchParams([['name', 'value']]);
+ * searchParams.delete('name');
+ * ```
+ */
+ delete(name: string): void;
+
+ /** Returns all the values associated with a given search parameter
+ * as an array.
+ *
+ * ```ts
+ * searchParams.getAll('name');
+ * ```
+ */
+ getAll(name: string): string[];
+
+ /** Returns the first value associated to the given search parameter.
+ *
+ * ```ts
+ * searchParams.get('name');
+ * ```
+ */
+ get(name: string): string | null;
+
+ /** Returns a Boolean that indicates whether a parameter with the
+ * specified name exists.
+ *
+ * ```ts
+ * searchParams.has('name');
+ * ```
+ */
+ has(name: string): boolean;
+
+ /** Sets the value associated with a given search parameter to the
+ * given value. If there were several matching values, this method
+ * deletes the others. If the search parameter doesn't exist, this
+ * method creates it.
+ *
+ * ```ts
+ * searchParams.set('name', 'value');
+ * ```
+ */
+ set(name: string, value: string): void;
+
+ /** Sort all key/value pairs contained in this object in place and
+ * return undefined. The sort order is according to Unicode code
+ * points of the keys.
+ *
+ * ```ts
+ * searchParams.sort();
+ * ```
+ */
+ sort(): void;
+
+ /** Calls a function for each element contained in this object in
+ * place and return undefined. Optionally accepts an object to use
+ * as this when executing callback as second argument.
+ *
+ * ```ts
+ * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
+ * params.forEach((value, key, parent) => {
+ * console.log(value, key, parent);
+ * });
+ * ```
+ *
+ */
+ forEach(
+ callbackfn: (value: string, key: string, parent: this) => void,
+ thisArg?: any,
+ ): void;
+
+ /** Returns an iterator allowing to go through all keys contained
+ * in this object.
+ *
+ * ```ts
+ * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
+ * for (const key of params.keys()) {
+ * console.log(key);
+ * }
+ * ```
+ */
+ keys(): IterableIterator;
+
+ /** Returns an iterator allowing to go through all values contained
+ * in this object.
+ *
+ * ```ts
+ * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
+ * for (const value of params.values()) {
+ * console.log(value);
+ * }
+ * ```
+ */
+ values(): IterableIterator;
+
+ /** Returns an iterator allowing to go through all key/value
+ * pairs contained in this object.
+ *
+ * ```ts
+ * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
+ * for (const [key, value] of params.entries()) {
+ * console.log(key, value);
+ * }
+ * ```
+ */
+ entries(): IterableIterator<[string, string]>;
+
+ /** Returns an iterator allowing to go through all key/value
+ * pairs contained in this object.
+ *
+ * ```ts
+ * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
+ * for (const [key, value] of params) {
+ * console.log(key, value);
+ * }
+ * ```
+ */
+ [Symbol.iterator](): IterableIterator<[string, string]>;
+
+ /** Returns a query string suitable for use in a URL.
+ *
+ * ```ts
+ * searchParams.toString();
+ * ```
+ */
+ toString(): string;
+}
+
+/** The URL interface represents an object providing static methods used for creating object URLs. */
+declare class URL {
+ constructor(url: string, base?: string | URL);
+ createObjectURL(object: any): string;
+ revokeObjectURL(url: string): void;
+
+ hash: string;
+ host: string;
+ hostname: string;
+ href: string;
+ toString(): string;
+ readonly origin: string;
+ password: string;
+ pathname: string;
+ port: string;
+ protocol: string;
+ search: string;
+ readonly searchParams: URLSearchParams;
+ username: string;
+ toJSON(): string;
+}
diff --git a/op_crates/url/lib.rs b/op_crates/url/lib.rs
new file mode 100644
index 00000000000000..a655d8c34be042
--- /dev/null
+++ b/op_crates/url/lib.rs
@@ -0,0 +1,155 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+
+use deno_core::error::generic_error;
+use deno_core::error::type_error;
+use deno_core::error::uri_error;
+use deno_core::error::AnyError;
+use deno_core::serde_json;
+use deno_core::serde_json::json;
+use deno_core::serde_json::Value;
+use deno_core::url::form_urlencoded;
+use deno_core::url::quirks;
+use deno_core::url::Url;
+use deno_core::JsRuntime;
+use deno_core::ZeroCopyBuf;
+use serde::Deserialize;
+use serde::Serialize;
+use std::panic::catch_unwind;
+use std::path::PathBuf;
+
+/// Parse `UrlParseArgs::href` with an optional `UrlParseArgs::base_href`, or an
+/// optional part to "set" after parsing. Return `UrlParts`.
+pub fn op_url_parse(
+ _state: &mut deno_core::OpState,
+ args: Value,
+ _zero_copy: &mut [ZeroCopyBuf],
+) -> Result {
+ #[derive(Deserialize)]
+ #[serde(rename_all = "camelCase")]
+ struct UrlParseArgs {
+ href: String,
+ base_href: Option,
+ // If one of the following are present, this is a setter call. Apply the
+ // proper `Url::set_*()` method after (re)parsing `href`.
+ set_hash: Option,
+ set_host: Option,
+ set_hostname: Option,
+ set_password: Option,
+ set_pathname: Option,
+ set_port: Option,
+ set_protocol: Option,
+ set_search: Option,
+ set_username: Option,
+ }
+ let args: UrlParseArgs = serde_json::from_value(args)?;
+ let base_url = args
+ .base_href
+ .as_ref()
+ .map(|b| Url::parse(b).map_err(|_| type_error("Invalid base URL")))
+ .transpose()?;
+ let mut url = Url::options()
+ .base_url(base_url.as_ref())
+ .parse(&args.href)
+ .map_err(|_| type_error("Invalid URL"))?;
+
+ if let Some(hash) = args.set_hash.as_ref() {
+ quirks::set_hash(&mut url, hash);
+ } else if let Some(host) = args.set_host.as_ref() {
+ quirks::set_host(&mut url, host).map_err(|_| uri_error("Invalid host"))?;
+ } else if let Some(hostname) = args.set_hostname.as_ref() {
+ quirks::set_hostname(&mut url, hostname)
+ .map_err(|_| uri_error("Invalid hostname"))?;
+ } else if let Some(password) = args.set_password.as_ref() {
+ quirks::set_password(&mut url, password)
+ .map_err(|_| uri_error("Invalid password"))?;
+ } else if let Some(pathname) = args.set_pathname.as_ref() {
+ quirks::set_pathname(&mut url, pathname);
+ } else if let Some(port) = args.set_port.as_ref() {
+ quirks::set_port(&mut url, port).map_err(|_| uri_error("Invalid port"))?;
+ } else if let Some(protocol) = args.set_protocol.as_ref() {
+ quirks::set_protocol(&mut url, protocol)
+ .map_err(|_| uri_error("Invalid protocol"))?;
+ } else if let Some(search) = args.set_search.as_ref() {
+ quirks::set_search(&mut url, search);
+ } else if let Some(username) = args.set_username.as_ref() {
+ quirks::set_username(&mut url, username)
+ .map_err(|_| uri_error("Invalid username"))?;
+ }
+
+ #[derive(Serialize)]
+ struct UrlParts<'a> {
+ href: &'a str,
+ hash: &'a str,
+ host: &'a str,
+ hostname: &'a str,
+ origin: &'a str,
+ password: &'a str,
+ pathname: &'a str,
+ port: &'a str,
+ protocol: &'a str,
+ search: &'a str,
+ username: &'a str,
+ }
+ // TODO(nayeemrmn): Panic that occurs in rust-url for the `non-spec:`
+ // url-constructor wpt tests: https://github.com/servo/rust-url/issues/670.
+ let username = catch_unwind(|| quirks::username(&url)).map_err(|_| {
+ generic_error(format!(
+ "Internal error while parsing \"{}\"{}, \
+ see https://github.com/servo/rust-url/issues/670",
+ args.href,
+ args
+ .base_href
+ .map(|b| format!(" against \"{}\"", b))
+ .unwrap_or_default()
+ ))
+ })?;
+ Ok(json!(UrlParts {
+ href: quirks::href(&url),
+ hash: quirks::hash(&url),
+ host: quirks::host(&url),
+ hostname: quirks::hostname(&url),
+ origin: &quirks::origin(&url),
+ password: quirks::password(&url),
+ pathname: quirks::pathname(&url),
+ port: quirks::port(&url),
+ protocol: quirks::protocol(&url),
+ search: quirks::search(&url),
+ username,
+ }))
+}
+
+pub fn op_url_parse_search_params(
+ _state: &mut deno_core::OpState,
+ args: Value,
+ _zero_copy: &mut [ZeroCopyBuf],
+) -> Result {
+ let search: String = serde_json::from_value(args)?;
+ let search_params: Vec<_> = form_urlencoded::parse(search.as_bytes())
+ .into_iter()
+ .collect();
+ Ok(json!(search_params))
+}
+
+pub fn op_url_stringify_search_params(
+ _state: &mut deno_core::OpState,
+ args: Value,
+ _zero_copy: &mut [ZeroCopyBuf],
+) -> Result {
+ let search_params: Vec<(String, String)> = serde_json::from_value(args)?;
+ let search = form_urlencoded::Serializer::new(String::new())
+ .extend_pairs(search_params)
+ .finish();
+ Ok(json!(search))
+}
+
+/// Load and execute the javascript code.
+pub fn init(isolate: &mut JsRuntime) {
+ let files = vec![("deno:op_crates/url/00_url.js", include_str!("00_url.js"))];
+ for (url, source_code) in files {
+ isolate.execute(url, source_code).unwrap();
+ }
+}
+
+pub fn get_declaration() -> PathBuf {
+ PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("lib.deno_url.d.ts")
+}
diff --git a/op_crates/web/01_dom_exception.js b/op_crates/web/01_dom_exception.js
index 14f4ca8e9346d0..f5bd3289bf43c6 100644
--- a/op_crates/web/01_dom_exception.js
+++ b/op_crates/web/01_dom_exception.js
@@ -2,6 +2,7 @@
// @ts-check
///
+///
///
///
diff --git a/op_crates/web/Cargo.toml b/op_crates/web/Cargo.toml
index d1d37c216d9d89..e8620788149de1 100644
--- a/op_crates/web/Cargo.toml
+++ b/op_crates/web/Cargo.toml
@@ -15,7 +15,6 @@ path = "lib.rs"
[dependencies]
deno_core = { version = "0.80.2", path = "../../core" }
-serde = { version = "1.0.123", features = ["derive"] }
[dev-dependencies]
futures = "0.3.12"
diff --git a/op_crates/web/internal.d.ts b/op_crates/web/internal.d.ts
index efafee26cd96dd..458f4a173c5a33 100644
--- a/op_crates/web/internal.d.ts
+++ b/op_crates/web/internal.d.ts
@@ -1,301 +1,14 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
-// deno-lint-ignore-file no-explicit-any ban-types
///
///
declare namespace globalThis {
declare namespace __bootstrap {
- declare namespace webidl {
- declare interface ConverterOpts {
- /**
- * The prefix for error messages created by this converter.
- * Examples:
- * - `Failed to construct 'Event'`
- * - `Failed to execute 'removeEventListener' on 'EventTarget'`
- */
- prefix: string;
- }
- declare interface ValueConverterOpts extends ConverterOpts {
- /**
- * The context of this value error messages created by this converter.
- * Examples:
- * - `Argument 1`
- * - `Argument 3`
- */
- context: string;
- }
- declare function makeException(
- ErrorType: any,
- message: string,
- opts: ValueConverterOpts,
- ): any;
- declare interface IntConverterOpts extends ValueConverterOpts {
- /**
- * Wether to throw if the number is outside of the acceptable values for
- * this type.
- */
- enforceRange?: boolean;
- /**
- * Wether to clamp this number to the acceptable values for this type.
- */
- clamp?: boolean;
- }
- declare interface StringConverterOpts extends ValueConverterOpts {
- /**
- * Wether to treat `null` value as an empty string.
- */
- treatNullAsEmptyString?: boolean;
- }
- declare interface BufferConverterOpts extends ValueConverterOpts {
- /**
- * Wether to allow `SharedArrayBuffer` (not just `ArrayBuffer`).
- */
- allowShared?: boolean;
- }
- declare const converters: {
- any(v: any): any;
- /**
- * Convert a value into a `boolean` (bool).
- */
- boolean(v: any, opts?: IntConverterOpts): boolean;
- /**
- * Convert a value into a `byte` (int8).
- */
- byte(v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `octet` (uint8).
- */
- octet(v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `short` (int16).
- */
- short(v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `unsigned short` (uint16).
- */
- ["unsigned short"](v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `long` (int32).
- */
- long(v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `unsigned long` (uint32).
- */
- ["unsigned long"](v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `long long` (int64).
- * **Note this is truncated to a JS number (53 bit precision).**
- */
- ["long long"](v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `unsigned long long` (uint64).
- * **Note this is truncated to a JS number (53 bit precision).**
- */
- ["unsigned long long"](v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `float` (f32).
- */
- float(v: any, opts?: ValueConverterOpts): number;
- /**
- * Convert a value into a `unrestricted float` (f32, infinity, or NaN).
- */
- ["unrestricted float"](v: any, opts?: ValueConverterOpts): number;
- /**
- * Convert a value into a `double` (f64).
- */
- double(v: any, opts?: ValueConverterOpts): number;
- /**
- * Convert a value into a `unrestricted double` (f64, infinity, or NaN).
- */
- ["unrestricted double"](v: any, opts?: ValueConverterOpts): number;
- /**
- * Convert a value into a `DOMString` (string).
- */
- DOMString(v: any, opts?: StringConverterOpts): string;
- /**
- * Convert a value into a `ByteString` (string with only u8 codepoints).
- */
- ByteString(v: any, opts?: StringConverterOpts): string;
- /**
- * Convert a value into a `USVString` (string with only valid non
- * surrogate Unicode code points).
- */
- USVString(v: any, opts?: StringConverterOpts): string;
- /**
- * Convert a value into an `object` (object).
- */
- object(v: any, opts?: ValueConverterOpts): object;
- /**
- * Convert a value into an `ArrayBuffer` (ArrayBuffer).
- */
- ArrayBuffer(v: any, opts?: BufferConverterOpts): ArrayBuffer;
- /**
- * Convert a value into a `DataView` (ArrayBuffer).
- */
- DataView(v: any, opts?: BufferConverterOpts): DataView;
- /**
- * Convert a value into a `Int8Array` (Int8Array).
- */
- Int8Array(v: any, opts?: BufferConverterOpts): Int8Array;
- /**
- * Convert a value into a `Int16Array` (Int16Array).
- */
- Int16Array(v: any, opts?: BufferConverterOpts): Int16Array;
- /**
- * Convert a value into a `Int32Array` (Int32Array).
- */
- Int32Array(v: any, opts?: BufferConverterOpts): Int32Array;
- /**
- * Convert a value into a `Uint8Array` (Uint8Array).
- */
- Uint8Array(v: any, opts?: BufferConverterOpts): Uint8Array;
- /**
- * Convert a value into a `Uint16Array` (Uint16Array).
- */
- Uint16Array(v: any, opts?: BufferConverterOpts): Uint16Array;
- /**
- * Convert a value into a `Uint32Array` (Uint32Array).
- */
- Uint32Array(v: any, opts?: BufferConverterOpts): Uint32Array;
- /**
- * Convert a value into a `Uint8ClampedArray` (Uint8ClampedArray).
- */
- Uint8ClampedArray(
- v: any,
- opts?: BufferConverterOpts,
- ): Uint8ClampedArray;
- /**
- * Convert a value into a `Float32Array` (Float32Array).
- */
- Float32Array(v: any, opts?: BufferConverterOpts): Float32Array;
- /**
- * Convert a value into a `Float64Array` (Float64Array).
- */
- Float64Array(v: any, opts?: BufferConverterOpts): Float64Array;
- /**
- * Convert a value into an `ArrayBufferView` (ArrayBufferView).
- */
- ArrayBufferView(v: any, opts?: BufferConverterOpts): ArrayBufferView;
- /**
- * Convert a value into a `BufferSource` (ArrayBuffer or ArrayBufferView).
- */
- BufferSource(
- v: any,
- opts?: BufferConverterOpts,
- ): ArrayBuffer | ArrayBufferView;
- /**
- * Convert a value into a `DOMTimeStamp` (u64). Alias for unsigned long long
- */
- DOMTimeStamp(v: any, opts?: IntConverterOpts): number;
- /**
- * Convert a value into a `Function` ((...args: any[]) => any).
- */
- Function(v: any, opts?: ValueConverterOpts): (...args: any) => any;
- /**
- * Convert a value into a `VoidFunction` (() => void).
- */
- VoidFunction(v: any, opts?: ValueConverterOpts): () => void;
- ["UVString?"](v: any, opts?: ValueConverterOpts): string | null;
- ["sequence"](v: any, opts?: ValueConverterOpts): number[];
-
- [type: string]: (v: any, opts: ValueConverterOpts) => any;
- };
-
- /**
- * Assert that the a function has at least a required amount of arguments.
- */
- declare function requiredArguments(
- length: number,
- required: number,
- opts: ConverterOpts,
- ): void;
- declare type Dictionary = DictionaryMember[];
- declare interface DictionaryMember {
- key: string;
- converter: (v: any, opts: ValueConverterOpts) => any;
- defaultValue?: any;
- required?: boolean;
- }
-
- /**
- * Create a converter for dictionaries.
- */
- declare function createDictionaryConverter(
- name: string,
- ...dictionaries: Dictionary[]
- ): (v: any, opts: ValueConverterOpts) => T;
-
- /**
- * Create a converter for enums.
- */
- declare function createEnumConverter(
- name: string,
- values: string[],
- ): (v: any, opts: ValueConverterOpts) => string;
-
- /**
- * Create a converter that makes the contained type nullable.
- */
- declare function createNullableConverter(
- converter: (v: any, opts: ValueConverterOpts) => T,
- ): (v: any, opts: ValueConverterOpts) => T | null;
-
- /**
- * Create a converter that converts a sequence of the inner type.
- */
- declare function createSequenceConverter(
- converter: (v: any, opts: ValueConverterOpts) => T,
- ): (v: any, opts: ValueConverterOpts) => T[];
-
- /**
- * Throw an illegal constructor error.
- */
- declare function illegalConstructor(): never;
-
- /**
- * The branding symbol.
- */
- declare const brand: unique symbol;
-
- /**
- * Create a branded instance of an interface.
- */
- declare function createBranded(self: any): any;
-
- /**
- * Assert that self is branded.
- */
- declare function assertBranded(self: any, type: any): void;
-
- /**
- * Create a converter for interfaces.
- */
- declare function createInterfaceConverter(
- name: string,
- prototype: any,
- ): (v: any, opts: ValueConverterOpts) => any;
-
- declare function createRecordConverter<
- K extends string | number | symbol,
- V,
- >(
- keyConverter: (v: any, opts: ValueConverterOpts) => K,
- valueConverter: (v: any, opts: ValueConverterOpts) => V,
- ): (
- v: Record,
- opts: ValueConverterOpts,
- ) => any;
- }
-
declare var eventTarget: {
EventTarget: typeof EventTarget;
};
- declare var url: {
- URLSearchParams: typeof URLSearchParams;
- };
-
declare var location: {
getLocationHref(): string | undefined;
};
diff --git a/op_crates/web/lib.deno_web.d.ts b/op_crates/web/lib.deno_web.d.ts
index 24a8f929d26996..79b56f68e28c42 100644
--- a/op_crates/web/lib.deno_web.d.ts
+++ b/op_crates/web/lib.deno_web.d.ts
@@ -313,172 +313,3 @@ declare var FileReader: {
readonly EMPTY: number;
readonly LOADING: number;
};
-
-declare class URLSearchParams {
- constructor(
- init?: string[][] | Record | string | URLSearchParams,
- );
- static toString(): string;
-
- /** Appends a specified key/value pair as a new search parameter.
- *
- * ```ts
- * let searchParams = new URLSearchParams();
- * searchParams.append('name', 'first');
- * searchParams.append('name', 'second');
- * ```
- */
- append(name: string, value: string): void;
-
- /** Deletes the given search parameter and its associated value,
- * from the list of all search parameters.
- *
- * ```ts
- * let searchParams = new URLSearchParams([['name', 'value']]);
- * searchParams.delete('name');
- * ```
- */
- delete(name: string): void;
-
- /** Returns all the values associated with a given search parameter
- * as an array.
- *
- * ```ts
- * searchParams.getAll('name');
- * ```
- */
- getAll(name: string): string[];
-
- /** Returns the first value associated to the given search parameter.
- *
- * ```ts
- * searchParams.get('name');
- * ```
- */
- get(name: string): string | null;
-
- /** Returns a Boolean that indicates whether a parameter with the
- * specified name exists.
- *
- * ```ts
- * searchParams.has('name');
- * ```
- */
- has(name: string): boolean;
-
- /** Sets the value associated with a given search parameter to the
- * given value. If there were several matching values, this method
- * deletes the others. If the search parameter doesn't exist, this
- * method creates it.
- *
- * ```ts
- * searchParams.set('name', 'value');
- * ```
- */
- set(name: string, value: string): void;
-
- /** Sort all key/value pairs contained in this object in place and
- * return undefined. The sort order is according to Unicode code
- * points of the keys.
- *
- * ```ts
- * searchParams.sort();
- * ```
- */
- sort(): void;
-
- /** Calls a function for each element contained in this object in
- * place and return undefined. Optionally accepts an object to use
- * as this when executing callback as second argument.
- *
- * ```ts
- * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
- * params.forEach((value, key, parent) => {
- * console.log(value, key, parent);
- * });
- * ```
- *
- */
- forEach(
- callbackfn: (value: string, key: string, parent: this) => void,
- thisArg?: any,
- ): void;
-
- /** Returns an iterator allowing to go through all keys contained
- * in this object.
- *
- * ```ts
- * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
- * for (const key of params.keys()) {
- * console.log(key);
- * }
- * ```
- */
- keys(): IterableIterator;
-
- /** Returns an iterator allowing to go through all values contained
- * in this object.
- *
- * ```ts
- * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
- * for (const value of params.values()) {
- * console.log(value);
- * }
- * ```
- */
- values(): IterableIterator;
-
- /** Returns an iterator allowing to go through all key/value
- * pairs contained in this object.
- *
- * ```ts
- * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
- * for (const [key, value] of params.entries()) {
- * console.log(key, value);
- * }
- * ```
- */
- entries(): IterableIterator<[string, string]>;
-
- /** Returns an iterator allowing to go through all key/value
- * pairs contained in this object.
- *
- * ```ts
- * const params = new URLSearchParams([["a", "b"], ["c", "d"]]);
- * for (const [key, value] of params) {
- * console.log(key, value);
- * }
- * ```
- */
- [Symbol.iterator](): IterableIterator<[string, string]>;
-
- /** Returns a query string suitable for use in a URL.
- *
- * ```ts
- * searchParams.toString();
- * ```
- */
- toString(): string;
-}
-
-/** The URL interface represents an object providing static methods used for creating object URLs. */
-declare class URL {
- constructor(url: string, base?: string | URL);
- createObjectURL(object: any): string;
- revokeObjectURL(url: string): void;
-
- hash: string;
- host: string;
- hostname: string;
- href: string;
- toString(): string;
- readonly origin: string;
- password: string;
- pathname: string;
- port: string;
- protocol: string;
- search: string;
- readonly searchParams: URLSearchParams;
- username: string;
- toJSON(): string;
-}
diff --git a/op_crates/web/lib.rs b/op_crates/web/lib.rs
index f67fd81a116bf3..81b51c6aebcd81 100644
--- a/op_crates/web/lib.rs
+++ b/op_crates/web/lib.rs
@@ -1,29 +1,11 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
-use deno_core::error::generic_error;
-use deno_core::error::type_error;
-use deno_core::error::uri_error;
-use deno_core::error::AnyError;
-use deno_core::serde_json;
-use deno_core::serde_json::json;
-use deno_core::serde_json::Value;
-use deno_core::url::form_urlencoded;
-use deno_core::url::quirks;
-use deno_core::url::Url;
use deno_core::JsRuntime;
-use deno_core::ZeroCopyBuf;
-use serde::Deserialize;
-use serde::Serialize;
-use std::panic::catch_unwind;
use std::path::PathBuf;
/// Load and execute the javascript code.
pub fn init(isolate: &mut JsRuntime) {
let files = vec![
- (
- "deno:op_crates/web/00_webidl.js",
- include_str!("00_webidl.js"),
- ),
(
"deno:op_crates/web/01_dom_exception.js",
include_str!("01_dom_exception.js"),
@@ -44,7 +26,6 @@ pub fn init(isolate: &mut JsRuntime) {
"deno:op_crates/web/08_text_encoding.js",
include_str!("08_text_encoding.js"),
),
- ("deno:op_crates/web/11_url.js", include_str!("11_url.js")),
(
"deno:op_crates/web/12_location.js",
include_str!("12_location.js"),
@@ -59,131 +40,6 @@ pub fn init(isolate: &mut JsRuntime) {
}
}
-/// Parse `UrlParseArgs::href` with an optional `UrlParseArgs::base_href`, or an
-/// optional part to "set" after parsing. Return `UrlParts`.
-pub fn op_parse_url(
- _state: &mut deno_core::OpState,
- args: Value,
- _zero_copy: &mut [ZeroCopyBuf],
-) -> Result {
- #[derive(Deserialize)]
- #[serde(rename_all = "camelCase")]
- struct UrlParseArgs {
- href: String,
- base_href: Option,
- // If one of the following are present, this is a setter call. Apply the
- // proper `Url::set_*()` method after (re)parsing `href`.
- set_hash: Option,
- set_host: Option,
- set_hostname: Option,
- set_password: Option,
- set_pathname: Option,
- set_port: Option,
- set_protocol: Option,
- set_search: Option,
- set_username: Option,
- }
- let args: UrlParseArgs = serde_json::from_value(args)?;
- let base_url = args
- .base_href
- .as_ref()
- .map(|b| Url::parse(b).map_err(|_| type_error("Invalid base URL")))
- .transpose()?;
- let mut url = Url::options()
- .base_url(base_url.as_ref())
- .parse(&args.href)
- .map_err(|_| type_error("Invalid URL"))?;
-
- if let Some(hash) = args.set_hash.as_ref() {
- quirks::set_hash(&mut url, hash);
- } else if let Some(host) = args.set_host.as_ref() {
- quirks::set_host(&mut url, host).map_err(|_| uri_error("Invalid host"))?;
- } else if let Some(hostname) = args.set_hostname.as_ref() {
- quirks::set_hostname(&mut url, hostname)
- .map_err(|_| uri_error("Invalid hostname"))?;
- } else if let Some(password) = args.set_password.as_ref() {
- quirks::set_password(&mut url, password)
- .map_err(|_| uri_error("Invalid password"))?;
- } else if let Some(pathname) = args.set_pathname.as_ref() {
- quirks::set_pathname(&mut url, pathname);
- } else if let Some(port) = args.set_port.as_ref() {
- quirks::set_port(&mut url, port).map_err(|_| uri_error("Invalid port"))?;
- } else if let Some(protocol) = args.set_protocol.as_ref() {
- quirks::set_protocol(&mut url, protocol)
- .map_err(|_| uri_error("Invalid protocol"))?;
- } else if let Some(search) = args.set_search.as_ref() {
- quirks::set_search(&mut url, search);
- } else if let Some(username) = args.set_username.as_ref() {
- quirks::set_username(&mut url, username)
- .map_err(|_| uri_error("Invalid username"))?;
- }
-
- #[derive(Serialize)]
- struct UrlParts<'a> {
- href: &'a str,
- hash: &'a str,
- host: &'a str,
- hostname: &'a str,
- origin: &'a str,
- password: &'a str,
- pathname: &'a str,
- port: &'a str,
- protocol: &'a str,
- search: &'a str,
- username: &'a str,
- }
- // TODO(nayeemrmn): Panic that occurs in rust-url for the `non-spec:`
- // url-constructor wpt tests: https://github.com/servo/rust-url/issues/670.
- let username = catch_unwind(|| quirks::username(&url)).map_err(|_| {
- generic_error(format!(
- "Internal error while parsing \"{}\"{}, \
- see https://github.com/servo/rust-url/issues/670",
- args.href,
- args
- .base_href
- .map(|b| format!(" against \"{}\"", b))
- .unwrap_or_default()
- ))
- })?;
- Ok(json!(UrlParts {
- href: quirks::href(&url),
- hash: quirks::hash(&url),
- host: quirks::host(&url),
- hostname: quirks::hostname(&url),
- origin: &quirks::origin(&url),
- password: quirks::password(&url),
- pathname: quirks::pathname(&url),
- port: quirks::port(&url),
- protocol: quirks::protocol(&url),
- search: quirks::search(&url),
- username,
- }))
-}
-
-pub fn op_parse_url_search_params(
- _state: &mut deno_core::OpState,
- args: Value,
- _zero_copy: &mut [ZeroCopyBuf],
-) -> Result {
- let search: String = serde_json::from_value(args)?;
- let search_params: Vec<_> = form_urlencoded::parse(search.as_bytes())
- .into_iter()
- .collect();
- Ok(json!(search_params))
-}
-
-pub fn op_stringify_url_search_params(
- _state: &mut deno_core::OpState,
- args: Value,
- _zero_copy: &mut [ZeroCopyBuf],
-) -> Result {
- let search_params: Vec<(String, String)> = serde_json::from_value(args)?;
- let search = form_urlencoded::Serializer::new(String::new())
- .extend_pairs(search_params)
- .finish();
- Ok(json!(search))
-}
-
pub fn get_declaration() -> PathBuf {
PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("lib.deno_web.d.ts")
}
diff --git a/op_crates/webgpu/Cargo.toml b/op_crates/webgpu/Cargo.toml
index f420106d31d643..603d0ad1be926e 100644
--- a/op_crates/webgpu/Cargo.toml
+++ b/op_crates/webgpu/Cargo.toml
@@ -4,7 +4,7 @@
name = "deno_webgpu"
version = "0.1.1"
edition = "2018"
-description = "provides webgpu Web API to deno_core"
+description = "WebGPU implementation for Deno"
authors = ["the Deno authors"]
license = "MIT"
readme = "README.md"
diff --git a/op_crates/web/00_webidl.js b/op_crates/webidl/00_webidl.js
similarity index 100%
rename from op_crates/web/00_webidl.js
rename to op_crates/webidl/00_webidl.js
diff --git a/op_crates/webidl/Cargo.toml b/op_crates/webidl/Cargo.toml
new file mode 100644
index 00000000000000..5d2b1799909f63
--- /dev/null
+++ b/op_crates/webidl/Cargo.toml
@@ -0,0 +1,17 @@
+# Copyright 2018-2020 the Deno authors. All rights reserved. MIT license.
+
+[package]
+name = "deno_webidl"
+version = "0.1.0"
+edition = "2018"
+description = "WebIDL implementation for Deno"
+authors = ["the Deno authors"]
+license = "MIT"
+readme = "README.md"
+repository = "https://github.com/denoland/deno"
+
+[lib]
+path = "lib.rs"
+
+[dependencies]
+deno_core = { version = "0.80.2", path = "../../core" }
diff --git a/op_crates/webidl/README.md b/op_crates/webidl/README.md
new file mode 100644
index 00000000000000..ce2d661e360b65
--- /dev/null
+++ b/op_crates/webidl/README.md
@@ -0,0 +1,6 @@
+# deno_webidl
+
+This crate implements WebIDL for Deno. It consists of infrastructure to do ECMA
+-> WebIDL conversions.
+
+Spec: https://heycam.github.io/webidl/
diff --git a/op_crates/webidl/internal.d.ts b/op_crates/webidl/internal.d.ts
new file mode 100644
index 00000000000000..425ee674e518d8
--- /dev/null
+++ b/op_crates/webidl/internal.d.ts
@@ -0,0 +1,291 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+// deno-lint-ignore-file no-explicit-any ban-types
+
+///
+///
+
+declare namespace globalThis {
+ declare namespace __bootstrap {
+ declare namespace webidl {
+ declare interface ConverterOpts {
+ /**
+ * The prefix for error messages created by this converter.
+ * Examples:
+ * - `Failed to construct 'Event'`
+ * - `Failed to execute 'removeEventListener' on 'EventTarget'`
+ */
+ prefix: string;
+ }
+ declare interface ValueConverterOpts extends ConverterOpts {
+ /**
+ * The context of this value error messages created by this converter.
+ * Examples:
+ * - `Argument 1`
+ * - `Argument 3`
+ */
+ context: string;
+ }
+ declare function makeException(
+ ErrorType: any,
+ message: string,
+ opts: ValueConverterOpts,
+ ): any;
+ declare interface IntConverterOpts extends ValueConverterOpts {
+ /**
+ * Wether to throw if the number is outside of the acceptable values for
+ * this type.
+ */
+ enforceRange?: boolean;
+ /**
+ * Wether to clamp this number to the acceptable values for this type.
+ */
+ clamp?: boolean;
+ }
+ declare interface StringConverterOpts extends ValueConverterOpts {
+ /**
+ * Wether to treat `null` value as an empty string.
+ */
+ treatNullAsEmptyString?: boolean;
+ }
+ declare interface BufferConverterOpts extends ValueConverterOpts {
+ /**
+ * Wether to allow `SharedArrayBuffer` (not just `ArrayBuffer`).
+ */
+ allowShared?: boolean;
+ }
+ declare const converters: {
+ any(v: any): any;
+ /**
+ * Convert a value into a `boolean` (bool).
+ */
+ boolean(v: any, opts?: IntConverterOpts): boolean;
+ /**
+ * Convert a value into a `byte` (int8).
+ */
+ byte(v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `octet` (uint8).
+ */
+ octet(v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `short` (int16).
+ */
+ short(v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `unsigned short` (uint16).
+ */
+ ["unsigned short"](v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `long` (int32).
+ */
+ long(v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `unsigned long` (uint32).
+ */
+ ["unsigned long"](v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `long long` (int64).
+ * **Note this is truncated to a JS number (53 bit precision).**
+ */
+ ["long long"](v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `unsigned long long` (uint64).
+ * **Note this is truncated to a JS number (53 bit precision).**
+ */
+ ["unsigned long long"](v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `float` (f32).
+ */
+ float(v: any, opts?: ValueConverterOpts): number;
+ /**
+ * Convert a value into a `unrestricted float` (f32, infinity, or NaN).
+ */
+ ["unrestricted float"](v: any, opts?: ValueConverterOpts): number;
+ /**
+ * Convert a value into a `double` (f64).
+ */
+ double(v: any, opts?: ValueConverterOpts): number;
+ /**
+ * Convert a value into a `unrestricted double` (f64, infinity, or NaN).
+ */
+ ["unrestricted double"](v: any, opts?: ValueConverterOpts): number;
+ /**
+ * Convert a value into a `DOMString` (string).
+ */
+ DOMString(v: any, opts?: StringConverterOpts): string;
+ /**
+ * Convert a value into a `ByteString` (string with only u8 codepoints).
+ */
+ ByteString(v: any, opts?: StringConverterOpts): string;
+ /**
+ * Convert a value into a `USVString` (string with only valid non
+ * surrogate Unicode code points).
+ */
+ USVString(v: any, opts?: StringConverterOpts): string;
+ /**
+ * Convert a value into an `object` (object).
+ */
+ object(v: any, opts?: ValueConverterOpts): object;
+ /**
+ * Convert a value into an `ArrayBuffer` (ArrayBuffer).
+ */
+ ArrayBuffer(v: any, opts?: BufferConverterOpts): ArrayBuffer;
+ /**
+ * Convert a value into a `DataView` (ArrayBuffer).
+ */
+ DataView(v: any, opts?: BufferConverterOpts): DataView;
+ /**
+ * Convert a value into a `Int8Array` (Int8Array).
+ */
+ Int8Array(v: any, opts?: BufferConverterOpts): Int8Array;
+ /**
+ * Convert a value into a `Int16Array` (Int16Array).
+ */
+ Int16Array(v: any, opts?: BufferConverterOpts): Int16Array;
+ /**
+ * Convert a value into a `Int32Array` (Int32Array).
+ */
+ Int32Array(v: any, opts?: BufferConverterOpts): Int32Array;
+ /**
+ * Convert a value into a `Uint8Array` (Uint8Array).
+ */
+ Uint8Array(v: any, opts?: BufferConverterOpts): Uint8Array;
+ /**
+ * Convert a value into a `Uint16Array` (Uint16Array).
+ */
+ Uint16Array(v: any, opts?: BufferConverterOpts): Uint16Array;
+ /**
+ * Convert a value into a `Uint32Array` (Uint32Array).
+ */
+ Uint32Array(v: any, opts?: BufferConverterOpts): Uint32Array;
+ /**
+ * Convert a value into a `Uint8ClampedArray` (Uint8ClampedArray).
+ */
+ Uint8ClampedArray(
+ v: any,
+ opts?: BufferConverterOpts,
+ ): Uint8ClampedArray;
+ /**
+ * Convert a value into a `Float32Array` (Float32Array).
+ */
+ Float32Array(v: any, opts?: BufferConverterOpts): Float32Array;
+ /**
+ * Convert a value into a `Float64Array` (Float64Array).
+ */
+ Float64Array(v: any, opts?: BufferConverterOpts): Float64Array;
+ /**
+ * Convert a value into an `ArrayBufferView` (ArrayBufferView).
+ */
+ ArrayBufferView(v: any, opts?: BufferConverterOpts): ArrayBufferView;
+ /**
+ * Convert a value into a `BufferSource` (ArrayBuffer or ArrayBufferView).
+ */
+ BufferSource(
+ v: any,
+ opts?: BufferConverterOpts,
+ ): ArrayBuffer | ArrayBufferView;
+ /**
+ * Convert a value into a `DOMTimeStamp` (u64). Alias for unsigned long long
+ */
+ DOMTimeStamp(v: any, opts?: IntConverterOpts): number;
+ /**
+ * Convert a value into a `Function` ((...args: any[]) => any).
+ */
+ Function(v: any, opts?: ValueConverterOpts): (...args: any) => any;
+ /**
+ * Convert a value into a `VoidFunction` (() => void).
+ */
+ VoidFunction(v: any, opts?: ValueConverterOpts): () => void;
+ ["UVString?"](v: any, opts?: ValueConverterOpts): string | null;
+ ["sequence"](v: any, opts?: ValueConverterOpts): number[];
+
+ [type: string]: (v: any, opts: ValueConverterOpts) => any;
+ };
+
+ /**
+ * Assert that the a function has at least a required amount of arguments.
+ */
+ declare function requiredArguments(
+ length: number,
+ required: number,
+ opts: ConverterOpts,
+ ): void;
+ declare type Dictionary = DictionaryMember[];
+ declare interface DictionaryMember {
+ key: string;
+ converter: (v: any, opts: ValueConverterOpts) => any;
+ defaultValue?: any;
+ required?: boolean;
+ }
+
+ /**
+ * Create a converter for dictionaries.
+ */
+ declare function createDictionaryConverter(
+ name: string,
+ ...dictionaries: Dictionary[]
+ ): (v: any, opts: ValueConverterOpts) => T;
+
+ /**
+ * Create a converter for enums.
+ */
+ declare function createEnumConverter(
+ name: string,
+ values: string[],
+ ): (v: any, opts: ValueConverterOpts) => string;
+
+ /**
+ * Create a converter that makes the contained type nullable.
+ */
+ declare function createNullableConverter(
+ converter: (v: any, opts: ValueConverterOpts) => T,
+ ): (v: any, opts: ValueConverterOpts) => T | null;
+
+ /**
+ * Create a converter that converts a sequence of the inner type.
+ */
+ declare function createSequenceConverter(
+ converter: (v: any, opts: ValueConverterOpts) => T,
+ ): (v: any, opts: ValueConverterOpts) => T[];
+
+ /**
+ * Throw an illegal constructor error.
+ */
+ declare function illegalConstructor(): never;
+
+ /**
+ * The branding symbol.
+ */
+ declare const brand: unique symbol;
+
+ /**
+ * Create a branded instance of an interface.
+ */
+ declare function createBranded(self: any): any;
+
+ /**
+ * Assert that self is branded.
+ */
+ declare function assertBranded(self: any, type: any): void;
+
+ /**
+ * Create a converter for interfaces.
+ */
+ declare function createInterfaceConverter(
+ name: string,
+ prototype: any,
+ ): (v: any, opts: ValueConverterOpts) => any;
+
+ declare function createRecordConverter<
+ K extends string | number | symbol,
+ V,
+ >(
+ keyConverter: (v: any, opts: ValueConverterOpts) => K,
+ valueConverter: (v: any, opts: ValueConverterOpts) => V,
+ ): (
+ v: Record,
+ opts: ValueConverterOpts,
+ ) => any;
+ }
+ }
+}
diff --git a/op_crates/webidl/lib.rs b/op_crates/webidl/lib.rs
new file mode 100644
index 00000000000000..7e617c7a766121
--- /dev/null
+++ b/op_crates/webidl/lib.rs
@@ -0,0 +1,14 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+
+use deno_core::JsRuntime;
+
+/// Load and execute the javascript code.
+pub fn init(isolate: &mut JsRuntime) {
+ let files = vec![(
+ "deno:op_crates/webidl/00_webidl.js",
+ include_str!("00_webidl.js"),
+ )];
+ for (url, source_code) in files {
+ isolate.execute(url, source_code).unwrap();
+ }
+}
diff --git a/runtime/Cargo.toml b/runtime/Cargo.toml
index 0ece4228ebc3f8..f654e015c0472e 100644
--- a/runtime/Cargo.toml
+++ b/runtime/Cargo.toml
@@ -22,6 +22,8 @@ deno_core = { path = "../core", version = "0.80.2" }
deno_crypto = { path = "../op_crates/crypto", version = "0.14.1" }
deno_fetch = { path = "../op_crates/fetch", version = "0.22.3" }
deno_web = { path = "../op_crates/web", version = "0.30.3" }
+deno_url = { path = "../op_crates/url", version = "0.1.0" }
+deno_webidl = { path = "../op_crates/webidl", version = "0.1.0" }
deno_websocket = { path = "../op_crates/websocket", version = "0.5.3" }
deno_webgpu = { path = "../op_crates/webgpu", version = "0.1.1" }
@@ -34,6 +36,8 @@ deno_core = { path = "../core", version = "0.80.2" }
deno_crypto = { path = "../op_crates/crypto", version = "0.14.1" }
deno_fetch = { path = "../op_crates/fetch", version = "0.22.3" }
deno_web = { path = "../op_crates/web", version = "0.30.3" }
+deno_url = { path = "../op_crates/url", version = "0.1.0" }
+deno_webidl = { path = "../op_crates/webidl", version = "0.1.0" }
deno_websocket = { path = "../op_crates/websocket", version = "0.5.3" }
deno_webgpu = { path = "../op_crates/webgpu", version = "0.1.1" }
diff --git a/runtime/build.rs b/runtime/build.rs
index 2481485684b762..67f80c8672bd17 100644
--- a/runtime/build.rs
+++ b/runtime/build.rs
@@ -13,6 +13,8 @@ fn create_snapshot(
snapshot_path: &Path,
files: Vec,
) {
+ deno_webidl::init(&mut js_runtime);
+ deno_url::init(&mut js_runtime);
deno_web::init(&mut js_runtime);
deno_fetch::init(&mut js_runtime);
deno_websocket::init(&mut js_runtime);
diff --git a/runtime/lib.rs b/runtime/lib.rs
index c523b24b7abf71..1406372616593f 100644
--- a/runtime/lib.rs
+++ b/runtime/lib.rs
@@ -9,8 +9,10 @@ extern crate log;
pub use deno_crypto;
pub use deno_fetch;
+pub use deno_url;
pub use deno_web;
pub use deno_webgpu;
+pub use deno_webidl;
pub use deno_websocket;
pub mod colors;
diff --git a/runtime/ops/mod.rs b/runtime/ops/mod.rs
index 0ef04ff3cf8de9..6b64b8042f8887 100644
--- a/runtime/ops/mod.rs
+++ b/runtime/ops/mod.rs
@@ -20,6 +20,7 @@ pub mod signal;
pub mod timers;
pub mod tls;
pub mod tty;
+pub mod url;
pub mod web_worker;
pub mod webgpu;
pub mod websocket;
diff --git a/runtime/ops/url.rs b/runtime/ops/url.rs
new file mode 100644
index 00000000000000..4add9132d6f769
--- /dev/null
+++ b/runtime/ops/url.rs
@@ -0,0 +1,18 @@
+// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
+use deno_url::op_url_parse;
+use deno_url::op_url_parse_search_params;
+use deno_url::op_url_stringify_search_params;
+
+pub fn init(rt: &mut deno_core::JsRuntime) {
+ super::reg_json_sync(rt, "op_url_parse", op_url_parse);
+ super::reg_json_sync(
+ rt,
+ "op_url_parse_search_params",
+ op_url_parse_search_params,
+ );
+ super::reg_json_sync(
+ rt,
+ "op_url_stringify_search_params",
+ op_url_stringify_search_params,
+ );
+}
diff --git a/runtime/web_worker.rs b/runtime/web_worker.rs
index 73d351c9c64d09..f35b38d3ba90f5 100644
--- a/runtime/web_worker.rs
+++ b/runtime/web_worker.rs
@@ -231,17 +231,7 @@ impl WebWorker {
);
ops::reg_json_sync(js_runtime, "op_close", deno_core::op_close);
ops::reg_json_sync(js_runtime, "op_resources", deno_core::op_resources);
- ops::reg_json_sync(js_runtime, "op_parse_url", deno_web::op_parse_url);
- ops::reg_json_sync(
- js_runtime,
- "op_parse_url_search_params",
- deno_web::op_parse_url_search_params,
- );
- ops::reg_json_sync(
- js_runtime,
- "op_stringify_url_search_params",
- deno_web::op_stringify_url_search_params,
- );
+ ops::url::init(js_runtime);
ops::io::init(js_runtime);
ops::webgpu::init(js_runtime);
ops::websocket::init(
diff --git a/runtime/worker.rs b/runtime/worker.rs
index e63fdbe18cf3fc..51fe1dc273adeb 100644
--- a/runtime/worker.rs
+++ b/runtime/worker.rs
@@ -127,17 +127,7 @@ impl MainWorker {
ops::crypto::init(js_runtime, options.seed);
ops::reg_json_sync(js_runtime, "op_close", deno_core::op_close);
ops::reg_json_sync(js_runtime, "op_resources", deno_core::op_resources);
- ops::reg_json_sync(js_runtime, "op_parse_url", deno_web::op_parse_url);
- ops::reg_json_sync(
- js_runtime,
- "op_parse_url_search_params",
- deno_web::op_parse_url_search_params,
- );
- ops::reg_json_sync(
- js_runtime,
- "op_stringify_url_search_params",
- deno_web::op_stringify_url_search_params,
- );
+ ops::url::init(js_runtime);
ops::fs_events::init(js_runtime);
ops::fs::init(js_runtime);
ops::io::init(js_runtime);