1
0
Fork 0
mirror of https://github.com/denoland/deno.git synced 2024-12-25 16:49:18 -05:00

refactor: merge deno_file crate into deno_web (#10914)

This refactor makes it so there's one less crate to publish on each release.
This commit is contained in:
Bartek Iwańczuk 2021-06-10 15:26:10 +02:00 committed by GitHub
parent fb20a6af76
commit 6091ea098a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
40 changed files with 173 additions and 268 deletions

13
Cargo.lock generated
View file

@ -535,7 +535,6 @@ dependencies = [
"deno_crypto", "deno_crypto",
"deno_doc", "deno_doc",
"deno_fetch", "deno_fetch",
"deno_file",
"deno_lint", "deno_lint",
"deno_runtime", "deno_runtime",
"deno_timers", "deno_timers",
@ -674,7 +673,7 @@ dependencies = [
"bytes", "bytes",
"data-url", "data-url",
"deno_core", "deno_core",
"deno_file", "deno_web",
"http", "http",
"reqwest", "reqwest",
"serde", "serde",
@ -683,14 +682,6 @@ dependencies = [
"tokio-util", "tokio-util",
] ]
[[package]]
name = "deno_file"
version = "0.7.0"
dependencies = [
"deno_core",
"uuid",
]
[[package]] [[package]]
name = "deno_lint" name = "deno_lint"
version = "0.6.1" version = "0.6.1"
@ -722,7 +713,6 @@ dependencies = [
"deno_core", "deno_core",
"deno_crypto", "deno_crypto",
"deno_fetch", "deno_fetch",
"deno_file",
"deno_timers", "deno_timers",
"deno_url", "deno_url",
"deno_web", "deno_web",
@ -790,6 +780,7 @@ dependencies = [
"encoding_rs", "encoding_rs",
"futures", "futures",
"serde", "serde",
"uuid",
] ]
[[package]] [[package]]

View file

@ -12,7 +12,6 @@ members = [
"extensions/console", "extensions/console",
"extensions/crypto", "extensions/crypto",
"extensions/fetch", "extensions/fetch",
"extensions/file",
"extensions/timers", "extensions/timers",
"extensions/url", "extensions/url",
"extensions/web", "extensions/web",

View file

@ -25,7 +25,6 @@ deno_console = { version = "0.8.0", path = "../extensions/console" }
deno_core = { version = "0.89.0", path = "../core" } deno_core = { version = "0.89.0", path = "../core" }
deno_crypto = { version = "0.22.0", path = "../extensions/crypto" } deno_crypto = { version = "0.22.0", path = "../extensions/crypto" }
deno_fetch = { version = "0.30.0", path = "../extensions/fetch" } deno_fetch = { version = "0.30.0", path = "../extensions/fetch" }
deno_file = { version = "0.7.0", path = "../extensions/file" }
deno_timers = { version = "0.6.0", path = "../extensions/timers" } deno_timers = { version = "0.6.0", path = "../extensions/timers" }
deno_url = { version = "0.8.0", path = "../extensions/url" } deno_url = { version = "0.8.0", path = "../extensions/url" }
deno_web = { version = "0.39.0", path = "../extensions/web" } deno_web = { version = "0.39.0", path = "../extensions/web" }

View file

@ -59,7 +59,6 @@ fn create_compiler_snapshot(
op_crate_libs.insert("deno.console", deno_console::get_declaration()); op_crate_libs.insert("deno.console", deno_console::get_declaration());
op_crate_libs.insert("deno.url", deno_url::get_declaration()); 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.web", deno_web::get_declaration());
op_crate_libs.insert("deno.file", deno_file::get_declaration());
op_crate_libs.insert("deno.fetch", deno_fetch::get_declaration()); op_crate_libs.insert("deno.fetch", deno_fetch::get_declaration());
op_crate_libs.insert("deno.webgpu", deno_webgpu::get_declaration()); op_crate_libs.insert("deno.webgpu", deno_webgpu::get_declaration());
op_crate_libs.insert("deno.websocket", deno_websocket::get_declaration()); op_crate_libs.insert("deno.websocket", deno_websocket::get_declaration());
@ -275,10 +274,6 @@ fn main() {
"cargo:rustc-env=DENO_WEB_LIB_PATH={}", "cargo:rustc-env=DENO_WEB_LIB_PATH={}",
deno_web::get_declaration().display() deno_web::get_declaration().display()
); );
println!(
"cargo:rustc-env=DENO_FILE_LIB_PATH={}",
deno_file::get_declaration().display()
);
println!( println!(
"cargo:rustc-env=DENO_FETCH_LIB_PATH={}", "cargo:rustc-env=DENO_FETCH_LIB_PATH={}",
deno_fetch::get_declaration().display() deno_fetch::get_declaration().display()

View file

@ -6,7 +6,6 @@
/// <reference no-default-lib="true" /> /// <reference no-default-lib="true" />
/// <reference lib="esnext" /> /// <reference lib="esnext" />
/// <reference lib="deno.console" /> /// <reference lib="deno.console" />
/// <reference lib="deno.file" />
/// <reference lib="deno.url" /> /// <reference lib="deno.url" />
/// <reference lib="deno.web" /> /// <reference lib="deno.web" />
/// <reference lib="deno.fetch" /> /// <reference lib="deno.fetch" />

View file

@ -19,7 +19,7 @@ use deno_core::futures;
use deno_core::futures::future::FutureExt; use deno_core::futures::future::FutureExt;
use deno_core::ModuleSpecifier; use deno_core::ModuleSpecifier;
use deno_runtime::deno_fetch::reqwest; use deno_runtime::deno_fetch::reqwest;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use deno_runtime::permissions::Permissions; use deno_runtime::permissions::Permissions;
use log::debug; use log::debug;
use log::info; use log::info;
@ -579,7 +579,7 @@ mod tests {
use deno_core::error::get_custom_error_class; use deno_core::error::get_custom_error_class;
use deno_core::resolve_url; use deno_core::resolve_url;
use deno_core::resolve_url_or_path; use deno_core::resolve_url_or_path;
use deno_runtime::deno_file::Blob; use deno_runtime::deno_web::Blob;
use std::rc::Rc; use std::rc::Rc;
use tempfile::TempDir; use tempfile::TempDir;

View file

@ -26,7 +26,7 @@ use deno_core::serde_json::json;
use deno_core::url::Position; use deno_core::url::Position;
use deno_core::url::Url; use deno_core::url::Url;
use deno_core::ModuleSpecifier; use deno_core::ModuleSpecifier;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use deno_runtime::permissions::Permissions; use deno_runtime::permissions::Permissions;
use log::error; use log::error;
use lspower::lsp; use lspower::lsp;

View file

@ -330,12 +330,11 @@ fn print_cache_info(
pub fn get_types(unstable: bool) -> String { pub fn get_types(unstable: bool) -> String {
let mut types = format!( let mut types = format!(
"{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}", "{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}\n{}",
crate::tsc::DENO_NS_LIB, crate::tsc::DENO_NS_LIB,
crate::tsc::DENO_CONSOLE_LIB, crate::tsc::DENO_CONSOLE_LIB,
crate::tsc::DENO_URL_LIB, crate::tsc::DENO_URL_LIB,
crate::tsc::DENO_WEB_LIB, crate::tsc::DENO_WEB_LIB,
crate::tsc::DENO_FILE_LIB,
crate::tsc::DENO_FETCH_LIB, crate::tsc::DENO_FETCH_LIB,
crate::tsc::DENO_WEBGPU_LIB, crate::tsc::DENO_WEBGPU_LIB,
crate::tsc::DENO_WEBSOCKET_LIB, crate::tsc::DENO_WEBSOCKET_LIB,

View file

@ -16,7 +16,7 @@ use crate::source_maps::SourceMapGetter;
use crate::specifier_handler::FetchHandler; use crate::specifier_handler::FetchHandler;
use crate::version; use crate::version;
use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel; use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use deno_runtime::inspector_server::InspectorServer; use deno_runtime::inspector_server::InspectorServer;
use deno_runtime::permissions::Permissions; use deno_runtime::permissions::Permissions;

View file

@ -574,7 +574,7 @@ pub mod tests {
use crate::file_fetcher::CacheSetting; use crate::file_fetcher::CacheSetting;
use crate::http_cache::HttpCache; use crate::http_cache::HttpCache;
use deno_core::resolve_url_or_path; use deno_core::resolve_url_or_path;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use tempfile::TempDir; use tempfile::TempDir;
macro_rules! map ( macro_rules! map (

View file

@ -23,7 +23,7 @@ use deno_core::ModuleLoader;
use deno_core::ModuleSpecifier; use deno_core::ModuleSpecifier;
use deno_core::OpState; use deno_core::OpState;
use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel; use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use deno_runtime::permissions::Permissions; use deno_runtime::permissions::Permissions;
use deno_runtime::permissions::PermissionsOptions; use deno_runtime::permissions::PermissionsOptions;
use deno_runtime::worker::MainWorker; use deno_runtime::worker::MainWorker;

View file

@ -33,7 +33,6 @@ pub static DENO_NS_LIB: &str = include_str!("dts/lib.deno.ns.d.ts");
pub static DENO_CONSOLE_LIB: &str = include_str!(env!("DENO_CONSOLE_LIB_PATH")); pub static DENO_CONSOLE_LIB: &str = include_str!(env!("DENO_CONSOLE_LIB_PATH"));
pub static DENO_URL_LIB: &str = include_str!(env!("DENO_URL_LIB_PATH")); 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_WEB_LIB: &str = include_str!(env!("DENO_WEB_LIB_PATH"));
pub static DENO_FILE_LIB: &str = include_str!(env!("DENO_FILE_LIB_PATH"));
pub static DENO_FETCH_LIB: &str = include_str!(env!("DENO_FETCH_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")); pub static DENO_WEBGPU_LIB: &str = include_str!(env!("DENO_WEBGPU_LIB_PATH"));
pub static DENO_WEBSOCKET_LIB: &str = pub static DENO_WEBSOCKET_LIB: &str =

View file

@ -3,8 +3,7 @@
// @ts-check // @ts-check
/// <reference path="../webidl/internal.d.ts" /> /// <reference path="../webidl/internal.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -3,8 +3,7 @@
// @ts-check // @ts-check
/// <reference path="../webidl/internal.d.ts" /> /// <reference path="../webidl/internal.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -5,8 +5,7 @@
/// <reference path="../url/internal.d.ts" /> /// <reference path="../url/internal.d.ts" />
/// <reference path="../url/lib.deno_url.d.ts" /> /// <reference path="../url/lib.deno_url.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -4,8 +4,7 @@
/// <reference path="../webidl/internal.d.ts" /> /// <reference path="../webidl/internal.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../url/internal.d.ts" /> /// <reference path="../url/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -3,8 +3,7 @@
// @ts-check // @ts-check
/// <reference path="../webidl/internal.d.ts" /> /// <reference path="../webidl/internal.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -4,8 +4,7 @@
/// <reference path="../webidl/internal.d.ts" /> /// <reference path="../webidl/internal.d.ts" />
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../url/internal.d.ts" /> /// <reference path="../url/internal.d.ts" />
/// <reference path="../file/internal.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="../file/lib.deno_file.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./11_streams_types.d.ts" /> /// <reference path="./11_streams_types.d.ts" />
/// <reference path="./lib.deno_fetch.d.ts" /> /// <reference path="./lib.deno_fetch.d.ts" />

View file

@ -17,7 +17,7 @@ path = "lib.rs"
bytes = "1.0.1" bytes = "1.0.1"
data-url = "0.1.0" data-url = "0.1.0"
deno_core = { version = "0.89.0", path = "../../core" } deno_core = { version = "0.89.0", path = "../../core" }
deno_file = { version = "0.7.0", path = "../file" } deno_web = { version = "0.39.0", path = "../web" }
http = "0.2.4" http = "0.2.4"
reqwest = { version = "0.11.3", default-features = false, features = ["rustls-tls", "stream", "gzip", "brotli"] } reqwest = { version = "0.11.3", default-features = false, features = ["rustls-tls", "stream", "gzip", "brotli"] }
serde = { version = "1.0.125", features = ["derive"] } serde = { version = "1.0.125", features = ["derive"] }

View file

@ -25,7 +25,7 @@ use deno_core::ResourceId;
use deno_core::ZeroCopyBuf; use deno_core::ZeroCopyBuf;
use data_url::DataUrl; use data_url::DataUrl;
use deno_file::BlobUrlStore; use deno_web::BlobUrlStore;
use reqwest::header::HeaderMap; use reqwest::header::HeaderMap;
use reqwest::header::HeaderName; use reqwest::header::HeaderName;
use reqwest::header::HeaderValue; use reqwest::header::HeaderValue;

View file

@ -1,18 +0,0 @@
# Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
[package]
name = "deno_file"
version = "0.7.0"
edition = "2018"
description = "File 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.89.0", path = "../../core" }
uuid = { version = "0.8.2", features = ["v4"] }

View file

@ -1,5 +0,0 @@
# deno_file
This crate implements the File API.
Spec: https://w3c.github.io/FileAPI

View file

@ -1,18 +0,0 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
/// <reference no-default-lib="true" />
/// <reference lib="esnext" />
declare namespace globalThis {
declare namespace __bootstrap {
declare var file: {
Blob: typeof Blob & {
[globalThis.__bootstrap.file._byteSequence]: Uint8Array;
};
readonly _byteSequence: unique symbol;
File: typeof File & {
[globalThis.__bootstrap.file._byteSequence]: Uint8Array;
};
};
}
}

View file

@ -1,40 +0,0 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
/// <reference no-default-lib="true" />
/// <reference lib="esnext" />
type BlobPart = BufferSource | Blob | string;
interface BlobPropertyBag {
type?: string;
endings?: "transparent" | "native";
}
/** A file-like object of immutable, raw data. Blobs represent data that isn't necessarily in a JavaScript-native format. The File interface is based on Blob, inheriting blob functionality and expanding it to support files on the user's system. */
declare class Blob {
constructor(blobParts?: BlobPart[], options?: BlobPropertyBag);
readonly size: number;
readonly type: string;
arrayBuffer(): Promise<ArrayBuffer>;
slice(start?: number, end?: number, contentType?: string): Blob;
stream(): ReadableStream<Uint8Array>;
text(): Promise<string>;
}
interface FilePropertyBag extends BlobPropertyBag {
lastModified?: number;
}
/** Provides information about files and allows JavaScript in a web page to
* access their content. */
declare class File extends Blob {
constructor(
fileBits: BlobPart[],
fileName: string,
options?: FilePropertyBag,
);
readonly lastModified: number;
readonly name: string;
}

View file

@ -1,120 +0,0 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
use deno_core::error::null_opbuf;
use deno_core::error::AnyError;
use deno_core::include_js_files;
use deno_core::op_sync;
use deno_core::url::Url;
use deno_core::Extension;
use deno_core::ModuleSpecifier;
use deno_core::ZeroCopyBuf;
use std::collections::HashMap;
use std::path::PathBuf;
use std::sync::Arc;
use std::sync::Mutex;
use uuid::Uuid;
#[derive(Debug, Clone)]
pub struct Blob {
pub data: Vec<u8>,
pub media_type: String,
}
pub struct Location(pub Url);
#[derive(Debug, Default, Clone)]
pub struct BlobUrlStore(Arc<Mutex<HashMap<Url, Blob>>>);
impl BlobUrlStore {
pub fn get(&self, mut url: Url) -> Result<Option<Blob>, AnyError> {
let blob_store = self.0.lock().unwrap();
url.set_fragment(None);
Ok(blob_store.get(&url).cloned())
}
pub fn insert(&self, blob: Blob, maybe_location: Option<Url>) -> Url {
let origin = if let Some(location) = maybe_location {
location.origin().ascii_serialization()
} else {
"null".to_string()
};
let id = Uuid::new_v4();
let url = Url::parse(&format!("blob:{}/{}", origin, id)).unwrap();
let mut blob_store = self.0.lock().unwrap();
blob_store.insert(url.clone(), blob);
url
}
pub fn remove(&self, url: &ModuleSpecifier) {
let mut blob_store = self.0.lock().unwrap();
blob_store.remove(&url);
}
}
pub fn op_file_create_object_url(
state: &mut deno_core::OpState,
media_type: String,
zero_copy: Option<ZeroCopyBuf>,
) -> Result<String, AnyError> {
let data = zero_copy.ok_or_else(null_opbuf)?;
let blob = Blob {
data: data.to_vec(),
media_type,
};
let maybe_location = state.try_borrow::<Location>();
let blob_store = state.borrow::<BlobUrlStore>();
let url =
blob_store.insert(blob, maybe_location.map(|location| location.0.clone()));
Ok(url.to_string())
}
pub fn op_file_revoke_object_url(
state: &mut deno_core::OpState,
url: String,
_: (),
) -> Result<(), AnyError> {
let url = Url::parse(&url)?;
let blob_store = state.borrow::<BlobUrlStore>();
blob_store.remove(&url);
Ok(())
}
pub fn init(
blob_url_store: BlobUrlStore,
maybe_location: Option<Url>,
) -> Extension {
Extension::builder()
.js(include_js_files!(
prefix "deno:extensions/file",
"01_file.js",
"02_filereader.js",
"03_blob_url.js",
))
.ops(vec![
(
"op_file_create_object_url",
op_sync(op_file_create_object_url),
),
(
"op_file_revoke_object_url",
op_sync(op_file_revoke_object_url),
),
])
.state(move |state| {
state.put(blob_url_store.clone());
if let Some(location) = maybe_location.clone() {
state.put(Location(location));
}
Ok(())
})
.build()
}
pub fn get_declaration() -> PathBuf {
PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("lib.deno_file.d.ts")
}

View file

@ -7,7 +7,6 @@
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../web/lib.deno_web.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./lib.deno_file.d.ts" />
/// <reference lib="esnext" /> /// <reference lib="esnext" />
"use strict"; "use strict";

View file

@ -7,7 +7,6 @@
/// <reference path="../web/internal.d.ts" /> /// <reference path="../web/internal.d.ts" />
/// <reference path="../web/lib.deno_web.d.ts" /> /// <reference path="../web/lib.deno_web.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./lib.deno_file.d.ts" />
/// <reference lib="esnext" /> /// <reference lib="esnext" />
"use strict"; "use strict";

View file

@ -9,7 +9,6 @@
/// <reference path="../url/internal.d.ts" /> /// <reference path="../url/internal.d.ts" />
/// <reference path="../url/lib.deno_url.d.ts" /> /// <reference path="../url/lib.deno_url.d.ts" />
/// <reference path="./internal.d.ts" /> /// <reference path="./internal.d.ts" />
/// <reference path="./lib.deno_file.d.ts" />
/// <reference lib="esnext" /> /// <reference lib="esnext" />
"use strict"; "use strict";

View file

@ -18,6 +18,7 @@ base64 = "0.13.0"
deno_core = { version = "0.89.0", path = "../../core" } deno_core = { version = "0.89.0", path = "../../core" }
encoding_rs = "0.8.28" encoding_rs = "0.8.28"
serde = "1.0" serde = "1.0"
uuid = { version = "0.8.2", features = ["v4"] }
[dev-dependencies] [dev-dependencies]
futures = "0.3.15" futures = "0.3.15"

View file

@ -1,5 +1,6 @@
# deno web # deno web
Op crate that implements Event, TextEncoder, TextDecoder. Op crate that implements Event, TextEncoder, TextDecoder and File API
(https://w3c.github.io/FileAPI).
Testing for text encoding is done via WPT in cli/. Testing for text encoding is done via WPT in cli/.

View file

@ -70,5 +70,15 @@ declare namespace globalThis {
atob(data: string): string; atob(data: string): string;
btoa(data: string): string; btoa(data: string): string;
}; };
declare var file: {
Blob: typeof Blob & {
[globalThis.__bootstrap.file._byteSequence]: Uint8Array;
};
readonly _byteSequence: unique symbol;
File: typeof File & {
[globalThis.__bootstrap.file._byteSequence]: Uint8Array;
};
};
} }
} }

View file

@ -341,3 +341,39 @@ declare var FileReader: {
readonly EMPTY: number; readonly EMPTY: number;
readonly LOADING: number; readonly LOADING: number;
}; };
type BlobPart = BufferSource | Blob | string;
interface BlobPropertyBag {
type?: string;
endings?: "transparent" | "native";
}
/** A file-like object of immutable, raw data. Blobs represent data that isn't necessarily in a JavaScript-native format. The File interface is based on Blob, inheriting blob functionality and expanding it to support files on the user's system. */
declare class Blob {
constructor(blobParts?: BlobPart[], options?: BlobPropertyBag);
readonly size: number;
readonly type: string;
arrayBuffer(): Promise<ArrayBuffer>;
slice(start?: number, end?: number, contentType?: string): Blob;
stream(): ReadableStream<Uint8Array>;
text(): Promise<string>;
}
interface FilePropertyBag extends BlobPropertyBag {
lastModified?: number;
}
/** Provides information about files and allows JavaScript in a web page to
* access their content. */
declare class File extends Blob {
constructor(
fileBits: BlobPart[],
fileName: string,
options?: FilePropertyBag,
);
readonly lastModified: number;
readonly name: string;
}

View file

@ -1,12 +1,15 @@
// Copyright 2018-2021 the Deno authors. All rights reserved. MIT license. // Copyright 2018-2021 the Deno authors. All rights reserved. MIT license.
use deno_core::error::bad_resource_id; use deno_core::error::bad_resource_id;
use deno_core::error::null_opbuf;
use deno_core::error::range_error; use deno_core::error::range_error;
use deno_core::error::type_error; use deno_core::error::type_error;
use deno_core::error::AnyError; use deno_core::error::AnyError;
use deno_core::include_js_files; use deno_core::include_js_files;
use deno_core::op_sync; use deno_core::op_sync;
use deno_core::url::Url;
use deno_core::Extension; use deno_core::Extension;
use deno_core::ModuleSpecifier;
use deno_core::OpState; use deno_core::OpState;
use deno_core::Resource; use deno_core::Resource;
use deno_core::ResourceId; use deno_core::ResourceId;
@ -17,15 +20,21 @@ use encoding_rs::DecoderResult;
use encoding_rs::Encoding; use encoding_rs::Encoding;
use serde::Deserialize; use serde::Deserialize;
use serde::Serialize; use serde::Serialize;
use std::borrow::Cow; use std::borrow::Cow;
use std::cell::RefCell; use std::cell::RefCell;
use std::collections::HashMap;
use std::fmt; use std::fmt;
use std::path::PathBuf; use std::path::PathBuf;
use std::sync::Arc;
use std::sync::Mutex;
use std::usize; use std::usize;
use uuid::Uuid;
/// Load and execute the javascript code. /// Load and execute the javascript code.
pub fn init() -> Extension { pub fn init(
blob_url_store: BlobUrlStore,
maybe_location: Option<Url>,
) -> Extension {
Extension::builder() Extension::builder()
.js(include_js_files!( .js(include_js_files!(
prefix "deno:extensions/web", prefix "deno:extensions/web",
@ -38,6 +47,9 @@ pub fn init() -> Extension {
"04_global_interfaces.js", "04_global_interfaces.js",
"05_base64.js", "05_base64.js",
"08_text_encoding.js", "08_text_encoding.js",
"09_file.js",
"10_filereader.js",
"11_blob_url.js",
"12_location.js", "12_location.js",
)) ))
.ops(vec![ .ops(vec![
@ -50,7 +62,22 @@ pub fn init() -> Extension {
("op_encoding_new_decoder", op_sync(op_encoding_new_decoder)), ("op_encoding_new_decoder", op_sync(op_encoding_new_decoder)),
("op_encoding_decode", op_sync(op_encoding_decode)), ("op_encoding_decode", op_sync(op_encoding_decode)),
("op_encoding_encode_into", op_sync(op_encoding_encode_into)), ("op_encoding_encode_into", op_sync(op_encoding_encode_into)),
(
"op_file_create_object_url",
op_sync(op_file_create_object_url),
),
(
"op_file_revoke_object_url",
op_sync(op_file_revoke_object_url),
),
]) ])
.state(move |state| {
state.put(blob_url_store.clone());
if let Some(location) = maybe_location.clone() {
state.put(Location(location));
}
Ok(())
})
.build() .build()
} }
@ -318,3 +345,73 @@ pub fn get_error_class_name(e: &AnyError) -> Option<&'static str> {
.map(|_| "DOMExceptionInvalidCharacterError") .map(|_| "DOMExceptionInvalidCharacterError")
}) })
} }
#[derive(Debug, Clone)]
pub struct Blob {
pub data: Vec<u8>,
pub media_type: String,
}
pub struct Location(pub Url);
#[derive(Debug, Default, Clone)]
pub struct BlobUrlStore(Arc<Mutex<HashMap<Url, Blob>>>);
impl BlobUrlStore {
pub fn get(&self, mut url: Url) -> Result<Option<Blob>, AnyError> {
let blob_store = self.0.lock().unwrap();
url.set_fragment(None);
Ok(blob_store.get(&url).cloned())
}
pub fn insert(&self, blob: Blob, maybe_location: Option<Url>) -> Url {
let origin = if let Some(location) = maybe_location {
location.origin().ascii_serialization()
} else {
"null".to_string()
};
let id = Uuid::new_v4();
let url = Url::parse(&format!("blob:{}/{}", origin, id)).unwrap();
let mut blob_store = self.0.lock().unwrap();
blob_store.insert(url.clone(), blob);
url
}
pub fn remove(&self, url: &ModuleSpecifier) {
let mut blob_store = self.0.lock().unwrap();
blob_store.remove(&url);
}
}
pub fn op_file_create_object_url(
state: &mut deno_core::OpState,
media_type: String,
zero_copy: Option<ZeroCopyBuf>,
) -> Result<String, AnyError> {
let data = zero_copy.ok_or_else(null_opbuf)?;
let blob = Blob {
data: data.to_vec(),
media_type,
};
let maybe_location = state.try_borrow::<Location>();
let blob_store = state.borrow::<BlobUrlStore>();
let url =
blob_store.insert(blob, maybe_location.map(|location| location.0.clone()));
Ok(url.to_string())
}
pub fn op_file_revoke_object_url(
state: &mut deno_core::OpState,
url: String,
_: (),
) -> Result<(), AnyError> {
let url = Url::parse(&url)?;
let blob_store = state.borrow::<BlobUrlStore>();
blob_store.remove(&url);
Ok(())
}

View file

@ -23,7 +23,6 @@ deno_console = { version = "0.8.0", path = "../extensions/console" }
deno_core = { version = "0.89.0", path = "../core" } deno_core = { version = "0.89.0", path = "../core" }
deno_crypto = { version = "0.22.0", path = "../extensions/crypto" } deno_crypto = { version = "0.22.0", path = "../extensions/crypto" }
deno_fetch = { version = "0.30.0", path = "../extensions/fetch" } deno_fetch = { version = "0.30.0", path = "../extensions/fetch" }
deno_file = { version = "0.7.0", path = "../extensions/file" }
deno_timers = { version = "0.6.0", path = "../extensions/timers" } deno_timers = { version = "0.6.0", path = "../extensions/timers" }
deno_url = { version = "0.8.0", path = "../extensions/url" } deno_url = { version = "0.8.0", path = "../extensions/url" }
deno_web = { version = "0.39.0", path = "../extensions/web" } deno_web = { version = "0.39.0", path = "../extensions/web" }
@ -42,7 +41,6 @@ deno_console = { version = "0.8.0", path = "../extensions/console" }
deno_core = { version = "0.89.0", path = "../core" } deno_core = { version = "0.89.0", path = "../core" }
deno_crypto = { version = "0.22.0", path = "../extensions/crypto" } deno_crypto = { version = "0.22.0", path = "../extensions/crypto" }
deno_fetch = { version = "0.30.0", path = "../extensions/fetch" } deno_fetch = { version = "0.30.0", path = "../extensions/fetch" }
deno_file = { version = "0.7.0", path = "../extensions/file" }
deno_timers = { version = "0.6.0", path = "../extensions/timers" } deno_timers = { version = "0.6.0", path = "../extensions/timers" }
deno_url = { version = "0.8.0", path = "../extensions/url" } deno_url = { version = "0.8.0", path = "../extensions/url" }
deno_web = { version = "0.39.0", path = "../extensions/web" } deno_web = { version = "0.39.0", path = "../extensions/web" }

View file

@ -41,8 +41,7 @@ fn create_runtime_snapshot(snapshot_path: &Path, files: Vec<PathBuf>) {
deno_webidl::init(), deno_webidl::init(),
deno_console::init(), deno_console::init(),
deno_url::init(), deno_url::init(),
deno_web::init(), deno_web::init(Default::default(), Default::default()),
deno_file::init(Default::default(), Default::default()),
deno_fetch::init::<deno_fetch::NoFetchPermissions>("".to_owned(), None), deno_fetch::init::<deno_fetch::NoFetchPermissions>("".to_owned(), None),
deno_websocket::init::<deno_websocket::NoWebSocketPermissions>( deno_websocket::init::<deno_websocket::NoWebSocketPermissions>(
"".to_owned(), "".to_owned(),

View file

@ -3,7 +3,7 @@
use deno_core::error::AnyError; use deno_core::error::AnyError;
use deno_core::FsModuleLoader; use deno_core::FsModuleLoader;
use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel; use deno_runtime::deno_broadcast_channel::InMemoryBroadcastChannel;
use deno_runtime::deno_file::BlobUrlStore; use deno_runtime::deno_web::BlobUrlStore;
use deno_runtime::permissions::Permissions; use deno_runtime::permissions::Permissions;
use deno_runtime::worker::MainWorker; use deno_runtime::worker::MainWorker;
use deno_runtime::worker::WorkerOptions; use deno_runtime::worker::WorkerOptions;

View file

@ -4,7 +4,6 @@ pub use deno_broadcast_channel;
pub use deno_console; pub use deno_console;
pub use deno_crypto; pub use deno_crypto;
pub use deno_fetch; pub use deno_fetch;
pub use deno_file;
pub use deno_timers; pub use deno_timers;
pub use deno_url; pub use deno_url;
pub use deno_web; pub use deno_web;

View file

@ -28,7 +28,7 @@ use deno_core::ModuleLoader;
use deno_core::ModuleSpecifier; use deno_core::ModuleSpecifier;
use deno_core::RuntimeOptions; use deno_core::RuntimeOptions;
use deno_core::ZeroCopyBuf; use deno_core::ZeroCopyBuf;
use deno_file::BlobUrlStore; use deno_web::BlobUrlStore;
use log::debug; use log::debug;
use std::cell::RefCell; use std::cell::RefCell;
use std::env; use std::env;
@ -255,11 +255,7 @@ impl WebWorker {
deno_webidl::init(), deno_webidl::init(),
deno_console::init(), deno_console::init(),
deno_url::init(), deno_url::init(),
deno_web::init(), deno_web::init(options.blob_url_store.clone(), Some(main_module.clone())),
deno_file::init(
options.blob_url_store.clone(),
Some(main_module.clone()),
),
deno_fetch::init::<Permissions>( deno_fetch::init::<Permissions>(
options.user_agent.clone(), options.user_agent.clone(),
options.ca_data.clone(), options.ca_data.clone(),

View file

@ -23,7 +23,7 @@ use deno_core::ModuleId;
use deno_core::ModuleLoader; use deno_core::ModuleLoader;
use deno_core::ModuleSpecifier; use deno_core::ModuleSpecifier;
use deno_core::RuntimeOptions; use deno_core::RuntimeOptions;
use deno_file::BlobUrlStore; use deno_web::BlobUrlStore;
use log::debug; use log::debug;
use std::env; use std::env;
use std::pin::Pin; use std::pin::Pin;
@ -96,8 +96,7 @@ impl MainWorker {
deno_webidl::init(), deno_webidl::init(),
deno_console::init(), deno_console::init(),
deno_url::init(), deno_url::init(),
deno_web::init(), deno_web::init(options.blob_url_store.clone(), options.location.clone()),
deno_file::init(options.blob_url_store.clone(), options.location.clone()),
deno_fetch::init::<Permissions>( deno_fetch::init::<Permissions>(
options.user_agent.clone(), options.user_agent.clone(),
options.ca_data.clone(), options.ca_data.clone(),

View file

@ -34,10 +34,8 @@ between the crates, it must be done in specific order:
first first
- `bench_util` - `bench_util`
- crates in `extensions/` directory - crates in `extensions/` directory
- `deno_crypto` and `deno_webstorage` depend on `deno_web`, so the latter must - `deno_fetch`, `deno_crypto` and `deno_webstorage` depend on `deno_web`, so
be bumped and released first the latter must be bumped and released first
- `deno_fetch` depends on `deno_file`, so the latter must be bumped and
released first
- `runtime` - this crate depends on `deno_core` and all crates in `extensions/` - `runtime` - this crate depends on `deno_core` and all crates in `extensions/`
directory directory