From 68c733c325b0f0f263020782b2450bf6495aa920 Mon Sep 17 00:00:00 2001 From: Axetroy Date: Sat, 13 May 2023 20:59:29 +0800 Subject: [PATCH] refactor --- Cargo.toml | 34 +++---- Makefile | 5 + README.md | 17 ++++ crate/lib/Cargo.toml | 36 +++++++ crate/lib/src/lib.rs | 55 +++++++++++ crate/md5/Cargo.toml | 42 ++++++++ crate/md5/LICENSE | 46 +++++++++ crate/md5/README.md | 5 + crate/md5/src/lib.rs | 27 ++++++ crate/sha1/Cargo.toml | 42 ++++++++ crate/sha1/LICENSE | 46 +++++++++ crate/sha1/README.md | 5 + crate/sha1/src/lib.rs | 27 ++++++ crate/sha2/Cargo.toml | 42 ++++++++ crate/sha2/LICENSE | 46 +++++++++ crate/sha2/README.md | 5 + crate/sha2/src/lib.rs | 69 +++++++++++++ crate/sha3/Cargo.toml | 42 ++++++++ crate/sha3/LICENSE | 46 +++++++++ crate/sha3/README.md | 5 + crate/sha3/src/lib.rs | 69 +++++++++++++ crate/sm3/Cargo.toml | 42 ++++++++ crate/sm3/LICENSE | 46 +++++++++ crate/sm3/README.md | 5 + crate/sm3/src/lib.rs | 28 ++++++ src/lib.rs | 219 +----------------------------------------- 26 files changed, 818 insertions(+), 233 deletions(-) create mode 100644 crate/lib/Cargo.toml create mode 100644 crate/lib/src/lib.rs create mode 100644 crate/md5/Cargo.toml create mode 100644 crate/md5/LICENSE create mode 100644 crate/md5/README.md create mode 100644 crate/md5/src/lib.rs create mode 100644 crate/sha1/Cargo.toml create mode 100644 crate/sha1/LICENSE create mode 100644 crate/sha1/README.md create mode 100644 crate/sha1/src/lib.rs create mode 100644 crate/sha2/Cargo.toml create mode 100644 crate/sha2/LICENSE create mode 100644 crate/sha2/README.md create mode 100644 crate/sha2/src/lib.rs create mode 100644 crate/sha3/Cargo.toml create mode 100644 crate/sha3/LICENSE create mode 100644 crate/sha3/README.md create mode 100644 crate/sha3/src/lib.rs create mode 100644 crate/sm3/Cargo.toml create mode 100644 crate/sm3/LICENSE create mode 100644 crate/sm3/README.md create mode 100644 crate/sm3/src/lib.rs diff --git a/Cargo.toml b/Cargo.toml index eccfe9e..fa98d4e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -31,21 +31,12 @@ default = ["wee_alloc"] lto = true [dependencies] -# The `wasm-bindgen` crate provides the bare minimum functionality needed -# to interact with JavaScript. -wasm-bindgen = "0.2.85" -md-5 = "0.10.5" -sha1 = "0.10.5" -sha2 = "0.10.5" -sha3 = "0.10.5" -sm3 = "0.4.1" -js-sys = "0.3.62" -digest = "0.10.6" -wasm-bindgen-futures = "0.4.35" -# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size -# compared to the default allocator's ~10K. However, it is slower than the default -# allocator, so it's not enabled by default. wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-md5 = { path = "./crate/md5", default-features = false } +wasm-hasher-sha1 = { path = "./crate/sha1", default-features = false } +wasm-hasher-sha2 = { path = "./crate/sha2", default-features = false } +wasm-hasher-sha3 = { path = "./crate/sha3", default-features = false } +wasm-hasher-sm3 = { path = "./crate/sm3", default-features = false } # The `web-sys` crate allows you to interact with the various browser APIs, # like the DOM. @@ -53,8 +44,13 @@ wee_alloc = { version = "0.4.2", optional = true } version = "0.3.61" features = ["console", "FileReader", "Blob", "AbortSignal"] -# These crates are used for running unit tests. -[dev-dependencies] -wasm-bindgen-test = "0.2.45" -futures = "0.1.27" -js-sys = "0.3.62" + +[workspace] +members = [ + "crate/lib", + "crate/md5", + "crate/sha1", + "crate/sha2", + "crate/sha3", + "crate/sm3", +] diff --git a/Makefile b/Makefile index f80f6d0..1e7ef02 100644 --- a/Makefile +++ b/Makefile @@ -1,3 +1,8 @@ .DEFAULT: build: @wasm-pack build --release --target bundler --scope axetroy --out-dir out + @wasm-pack build --release --target bundler --scope axetroy --out-dir out ./crate/md5 + @wasm-pack build --release --target bundler --scope axetroy --out-dir out ./crate/sha1 + @wasm-pack build --release --target bundler --scope axetroy --out-dir out ./crate/sha2 + @wasm-pack build --release --target bundler --scope axetroy --out-dir out ./crate/sha3 + @wasm-pack build --release --target bundler --scope axetroy --out-dir out ./crate/sm3 diff --git a/README.md b/README.md index ffc4eda..580f616 100644 --- a/README.md +++ b/README.md @@ -17,6 +17,7 @@ The difference with [github.com/fuyoo/wasm-hasher](https://github.com/fuyoo/wasm 1. Hash process can be interrupted with `abortController` 2. The exposed function can specify the chunks size for each read. Larger chunks use more CPU. 3. `onProgress` callback is optional. Set to `null` to improve performance if you don't need it. +4. separate packages, smaller wasm files ## Usage @@ -34,8 +35,24 @@ import("@axetroy/wasm-hasher").then(({ default: hasher }) => { ```bash npm install @axetroy/wasm-hasher +npm install @axetroy/wasm-hasher-md5 +npm install @axetroy/wasm-hasher-sha1 +npm install @axetroy/wasm-hasher-sha2 +npm install @axetroy/wasm-hasher-sha3 +npm install @axetroy/wasm-hasher-sm3 ``` +### Packages + +| Package | Description | Version | +| ------------------------- | ---------------------------- | --------------------------------------------------------------------------------------------------------------------------- | +| @axetroy/wasm-hasher | Including all supported hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher) | +| @axetroy/wasm-hasher-md5 | Including md5 hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher-md5) | +| @axetroy/wasm-hasher-sha1 | Including sha1 hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher-sha1) | +| @axetroy/wasm-hasher-sha2 | Including sha2 hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher-sha2) | +| @axetroy/wasm-hasher-sha3 | Including sha3 hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher-sha3) | +| @axetroy/wasm-hasher-sm3 | Including sm3 hash | [![npm version](https://badge.fury.io/js/@axetroy%2Fwasm-hasher.svg)](https://badge.fury.io/js/@axetroy%2Fwasm-hasher-sm3) | + ### 🛠️ Build from source Make sure you have install [rust^1.69](https://www.rust-lang.org/) and [wasm-pack](https://rustwasm.github.io/wasm-pack/installer/) diff --git a/crate/lib/Cargo.toml b/crate/lib/Cargo.toml new file mode 100644 index 0000000..299af1c --- /dev/null +++ b/crate/lib/Cargo.toml @@ -0,0 +1,36 @@ +[package] +name = "wasm-hasher-lib" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = [] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/lib/src/lib.rs b/crate/lib/src/lib.rs new file mode 100644 index 0000000..110c64e --- /dev/null +++ b/crate/lib/src/lib.rs @@ -0,0 +1,55 @@ +use digest::Digest; +use js_sys::{Function, Uint8Array}; +use wasm_bindgen::prelude::*; +use wasm_bindgen_futures::JsFuture; +use web_sys::{AbortSignal, Blob}; + +pub async fn computed( + signal: AbortSignal, + blob: Blob, + chunk_size: Option, + cb: &Option, + hasher: &mut D, +) -> Result<(), JsValue> { + let size = blob.size(); + + let chunk = match chunk_size { + Some(size) => size, + None => (1024 * 1024 * 5) as f64, + }; + + let chunks = (size / chunk).ceil() as i64; + let mut start: f64 = 0.0; + + for _ in 0..chunks { + if signal.aborted() { + return Err(JsValue::from("Signal has been abort!")); + } + + let mut end = start + chunk; + end = if end >= size { size } else { end }; + let data = blob + .slice_with_f64_and_f64(start, end) + .expect("slice blob failed!"); + let buffer: JsValue = JsFuture::from(data.array_buffer()) + .await + .expect("get arrayBuffer failed!"); + hasher.update(&Uint8Array::new(&buffer).to_vec()); + match cb { + Some(func) => { + let _ = func.call1(&JsValue::null(), &JsValue::from(start / size * 100.0)); + } + None => (), + } + start += chunk; + } + + match cb { + Some(func) => { + let _ = func.call1(&JsValue::null(), &JsValue::from(100.0)); + } + None => (), + } + + Ok(()) +} diff --git a/crate/md5/Cargo.toml b/crate/md5/Cargo.toml new file mode 100644 index 0000000..1c83cd0 --- /dev/null +++ b/crate/md5/Cargo.toml @@ -0,0 +1,42 @@ +[package] +name = "wasm-hasher-md5" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["md5", "wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = ["wee_alloc"] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +md-5 = "0.10.5" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" +# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size +# compared to the default allocator's ~10K. However, it is slower than the default +# allocator, so it's not enabled by default. +wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-lib = { path = "../lib" } + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/md5/LICENSE b/crate/md5/LICENSE new file mode 100644 index 0000000..426eba1 --- /dev/null +++ b/crate/md5/LICENSE @@ -0,0 +1,46 @@ +Copyright (c) 2023 Axetroy + +Anti 996 License Version 1.0 (Draft) + +Permission is hereby granted to any individual or legal entity +obtaining a copy of this licensed work (including the source code, +documentation and/or related items, hereinafter collectively referred +to as the "licensed work"), free of charge, to deal with the licensed +work for any purpose, including without limitation, the rights to use, +reproduce, modify, prepare derivative works of, distribute, publish +and sublicense the licensed work, subject to the following conditions: + +1. The individual or the legal entity must conspicuously display, +without modification, this License and the notice on each redistributed +or derivative copy of the Licensed Work. + +2. The individual or the legal entity must strictly comply with all +applicable laws, regulations, rules and standards of the jurisdiction +relating to labor and employment where the individual is physically +located or where the individual was born or naturalized; or where the +legal entity is registered or is operating (whichever is stricter). In +case that the jurisdiction has no such laws, regulations, rules and +standards or its laws, regulations, rules and standards are +unenforceable, the individual or the legal entity are required to +comply with Core International Labor Standards. + +3. The individual or the legal entity shall not induce or force its +employee(s), whether full-time or part-time, or its independent +contractor(s), in any methods, to agree in oral or written form, to +directly or indirectly restrict, weaken or relinquish his or her +rights or remedies under such laws, regulations, rules and standards +relating to labor and employment as mentioned above, no matter whether +such written or oral agreement are enforceable under the laws of the +said jurisdiction, nor shall such individual or the legal entity +limit, in any methods, the rights of its employee(s) or independent +contractor(s) from reporting or complaining to the copyright holder or +relevant authorities monitoring the compliance of the license about +its violation(s) of the said license. + +THE LICENSED WORK IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, +DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +OTHERWISE, ARISING FROM, OUT OF OR IN ANY WAY CONNECTION WITH THE +LICENSED WORK OR THE USE OR OTHER DEALINGS IN THE LICENSED WORK. \ No newline at end of file diff --git a/crate/md5/README.md b/crate/md5/README.md new file mode 100644 index 0000000..1b2f788 --- /dev/null +++ b/crate/md5/README.md @@ -0,0 +1,5 @@ +### Usage + +```js +import pkg from "@axetroy/wasm-hasher-md5"; +``` diff --git a/crate/md5/src/lib.rs b/crate/md5/src/lib.rs new file mode 100644 index 0000000..8598fb1 --- /dev/null +++ b/crate/md5/src/lib.rs @@ -0,0 +1,27 @@ +use digest::Digest; +use js_sys::Function; +use md5::Md5; +use wasm_bindgen::prelude::*; +use web_sys::{AbortSignal, Blob}; + +// When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global +// allocator. +// +// If you don't want to use `wee_alloc`, you can safely delete this. +#[cfg(feature = "wee_alloc")] +#[global_allocator] +static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; + +#[wasm_bindgen] +pub async fn md5( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Md5::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} diff --git a/crate/sha1/Cargo.toml b/crate/sha1/Cargo.toml new file mode 100644 index 0000000..b907e59 --- /dev/null +++ b/crate/sha1/Cargo.toml @@ -0,0 +1,42 @@ +[package] +name = "wasm-hasher-sha1" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["sha1", "wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = ["wee_alloc"] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +sha1 = "0.10.5" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" +# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size +# compared to the default allocator's ~10K. However, it is slower than the default +# allocator, so it's not enabled by default. +wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-lib = { path = "../lib" } + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/sha1/LICENSE b/crate/sha1/LICENSE new file mode 100644 index 0000000..426eba1 --- /dev/null +++ b/crate/sha1/LICENSE @@ -0,0 +1,46 @@ +Copyright (c) 2023 Axetroy + +Anti 996 License Version 1.0 (Draft) + +Permission is hereby granted to any individual or legal entity +obtaining a copy of this licensed work (including the source code, +documentation and/or related items, hereinafter collectively referred +to as the "licensed work"), free of charge, to deal with the licensed +work for any purpose, including without limitation, the rights to use, +reproduce, modify, prepare derivative works of, distribute, publish +and sublicense the licensed work, subject to the following conditions: + +1. The individual or the legal entity must conspicuously display, +without modification, this License and the notice on each redistributed +or derivative copy of the Licensed Work. + +2. The individual or the legal entity must strictly comply with all +applicable laws, regulations, rules and standards of the jurisdiction +relating to labor and employment where the individual is physically +located or where the individual was born or naturalized; or where the +legal entity is registered or is operating (whichever is stricter). In +case that the jurisdiction has no such laws, regulations, rules and +standards or its laws, regulations, rules and standards are +unenforceable, the individual or the legal entity are required to +comply with Core International Labor Standards. + +3. The individual or the legal entity shall not induce or force its +employee(s), whether full-time or part-time, or its independent +contractor(s), in any methods, to agree in oral or written form, to +directly or indirectly restrict, weaken or relinquish his or her +rights or remedies under such laws, regulations, rules and standards +relating to labor and employment as mentioned above, no matter whether +such written or oral agreement are enforceable under the laws of the +said jurisdiction, nor shall such individual or the legal entity +limit, in any methods, the rights of its employee(s) or independent +contractor(s) from reporting or complaining to the copyright holder or +relevant authorities monitoring the compliance of the license about +its violation(s) of the said license. + +THE LICENSED WORK IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, +DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +OTHERWISE, ARISING FROM, OUT OF OR IN ANY WAY CONNECTION WITH THE +LICENSED WORK OR THE USE OR OTHER DEALINGS IN THE LICENSED WORK. \ No newline at end of file diff --git a/crate/sha1/README.md b/crate/sha1/README.md new file mode 100644 index 0000000..4d399ae --- /dev/null +++ b/crate/sha1/README.md @@ -0,0 +1,5 @@ +### Usage + +```js +import pkg from "@axetroy/wasm-hasher-sha1"; +``` diff --git a/crate/sha1/src/lib.rs b/crate/sha1/src/lib.rs new file mode 100644 index 0000000..d1f2fae --- /dev/null +++ b/crate/sha1/src/lib.rs @@ -0,0 +1,27 @@ +use digest::Digest; +use js_sys::Function; +use sha1::Sha1; +use wasm_bindgen::prelude::*; +use web_sys::{AbortSignal, Blob}; + +// When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global +// allocator. +// +// If you don't want to use `wee_alloc`, you can safely delete this. +#[cfg(feature = "wee_alloc")] +#[global_allocator] +static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; + +#[wasm_bindgen] +pub async fn sha1( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha1::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} diff --git a/crate/sha2/Cargo.toml b/crate/sha2/Cargo.toml new file mode 100644 index 0000000..24d3082 --- /dev/null +++ b/crate/sha2/Cargo.toml @@ -0,0 +1,42 @@ +[package] +name = "wasm-hasher-sha2" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["sha2", "wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = ["wee_alloc"] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +sha2 = "0.10.5" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" +# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size +# compared to the default allocator's ~10K. However, it is slower than the default +# allocator, so it's not enabled by default. +wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-lib = { path = "../lib" } + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/sha2/LICENSE b/crate/sha2/LICENSE new file mode 100644 index 0000000..426eba1 --- /dev/null +++ b/crate/sha2/LICENSE @@ -0,0 +1,46 @@ +Copyright (c) 2023 Axetroy + +Anti 996 License Version 1.0 (Draft) + +Permission is hereby granted to any individual or legal entity +obtaining a copy of this licensed work (including the source code, +documentation and/or related items, hereinafter collectively referred +to as the "licensed work"), free of charge, to deal with the licensed +work for any purpose, including without limitation, the rights to use, +reproduce, modify, prepare derivative works of, distribute, publish +and sublicense the licensed work, subject to the following conditions: + +1. The individual or the legal entity must conspicuously display, +without modification, this License and the notice on each redistributed +or derivative copy of the Licensed Work. + +2. The individual or the legal entity must strictly comply with all +applicable laws, regulations, rules and standards of the jurisdiction +relating to labor and employment where the individual is physically +located or where the individual was born or naturalized; or where the +legal entity is registered or is operating (whichever is stricter). In +case that the jurisdiction has no such laws, regulations, rules and +standards or its laws, regulations, rules and standards are +unenforceable, the individual or the legal entity are required to +comply with Core International Labor Standards. + +3. The individual or the legal entity shall not induce or force its +employee(s), whether full-time or part-time, or its independent +contractor(s), in any methods, to agree in oral or written form, to +directly or indirectly restrict, weaken or relinquish his or her +rights or remedies under such laws, regulations, rules and standards +relating to labor and employment as mentioned above, no matter whether +such written or oral agreement are enforceable under the laws of the +said jurisdiction, nor shall such individual or the legal entity +limit, in any methods, the rights of its employee(s) or independent +contractor(s) from reporting or complaining to the copyright holder or +relevant authorities monitoring the compliance of the license about +its violation(s) of the said license. + +THE LICENSED WORK IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, +DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +OTHERWISE, ARISING FROM, OUT OF OR IN ANY WAY CONNECTION WITH THE +LICENSED WORK OR THE USE OR OTHER DEALINGS IN THE LICENSED WORK. \ No newline at end of file diff --git a/crate/sha2/README.md b/crate/sha2/README.md new file mode 100644 index 0000000..98ba771 --- /dev/null +++ b/crate/sha2/README.md @@ -0,0 +1,5 @@ +### Usage + +```js +import pkg from "@axetroy/wasm-hasher-sha2"; +``` diff --git a/crate/sha2/src/lib.rs b/crate/sha2/src/lib.rs new file mode 100644 index 0000000..12be38d --- /dev/null +++ b/crate/sha2/src/lib.rs @@ -0,0 +1,69 @@ +use digest::Digest; +use js_sys::Function; +use sha2::{Sha224, Sha256, Sha384, Sha512}; +use wasm_bindgen::prelude::*; +use web_sys::{AbortSignal, Blob}; + +// When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global +// allocator. +// +// If you don't want to use `wee_alloc`, you can safely delete this. +#[cfg(feature = "wee_alloc")] +#[global_allocator] +static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; + +#[wasm_bindgen] +pub async fn sha2_224( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha224::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha2_256( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha256::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha2_384( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha384::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha2_512( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha512::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} diff --git a/crate/sha3/Cargo.toml b/crate/sha3/Cargo.toml new file mode 100644 index 0000000..7fe1bd4 --- /dev/null +++ b/crate/sha3/Cargo.toml @@ -0,0 +1,42 @@ +[package] +name = "wasm-hasher-sha3" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["sha3", "wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = ["wee_alloc"] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +sha3 = "0.10.5" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" +# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size +# compared to the default allocator's ~10K. However, it is slower than the default +# allocator, so it's not enabled by default. +wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-lib = { path = "../lib" } + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/sha3/LICENSE b/crate/sha3/LICENSE new file mode 100644 index 0000000..426eba1 --- /dev/null +++ b/crate/sha3/LICENSE @@ -0,0 +1,46 @@ +Copyright (c) 2023 Axetroy + +Anti 996 License Version 1.0 (Draft) + +Permission is hereby granted to any individual or legal entity +obtaining a copy of this licensed work (including the source code, +documentation and/or related items, hereinafter collectively referred +to as the "licensed work"), free of charge, to deal with the licensed +work for any purpose, including without limitation, the rights to use, +reproduce, modify, prepare derivative works of, distribute, publish +and sublicense the licensed work, subject to the following conditions: + +1. The individual or the legal entity must conspicuously display, +without modification, this License and the notice on each redistributed +or derivative copy of the Licensed Work. + +2. The individual or the legal entity must strictly comply with all +applicable laws, regulations, rules and standards of the jurisdiction +relating to labor and employment where the individual is physically +located or where the individual was born or naturalized; or where the +legal entity is registered or is operating (whichever is stricter). In +case that the jurisdiction has no such laws, regulations, rules and +standards or its laws, regulations, rules and standards are +unenforceable, the individual or the legal entity are required to +comply with Core International Labor Standards. + +3. The individual or the legal entity shall not induce or force its +employee(s), whether full-time or part-time, or its independent +contractor(s), in any methods, to agree in oral or written form, to +directly or indirectly restrict, weaken or relinquish his or her +rights or remedies under such laws, regulations, rules and standards +relating to labor and employment as mentioned above, no matter whether +such written or oral agreement are enforceable under the laws of the +said jurisdiction, nor shall such individual or the legal entity +limit, in any methods, the rights of its employee(s) or independent +contractor(s) from reporting or complaining to the copyright holder or +relevant authorities monitoring the compliance of the license about +its violation(s) of the said license. + +THE LICENSED WORK IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, +DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +OTHERWISE, ARISING FROM, OUT OF OR IN ANY WAY CONNECTION WITH THE +LICENSED WORK OR THE USE OR OTHER DEALINGS IN THE LICENSED WORK. \ No newline at end of file diff --git a/crate/sha3/README.md b/crate/sha3/README.md new file mode 100644 index 0000000..c528e4b --- /dev/null +++ b/crate/sha3/README.md @@ -0,0 +1,5 @@ +### Usage + +```js +import pkg from "@axetroy/wasm-hasher-sha3"; +``` diff --git a/crate/sha3/src/lib.rs b/crate/sha3/src/lib.rs new file mode 100644 index 0000000..188905a --- /dev/null +++ b/crate/sha3/src/lib.rs @@ -0,0 +1,69 @@ +use digest::Digest; +use js_sys::Function; +use sha3::{Sha3_224, Sha3_256, Sha3_384, Sha3_512}; +use wasm_bindgen::prelude::*; +use web_sys::{AbortSignal, Blob}; + +// When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global +// allocator. +// +// If you don't want to use `wee_alloc`, you can safely delete this. +#[cfg(feature = "wee_alloc")] +#[global_allocator] +static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; + +#[wasm_bindgen] +pub async fn sha3_224( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha3_224::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha3_256( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha3_256::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha3_384( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha3_384::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} + +#[wasm_bindgen] +pub async fn sha3_512( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sha3_512::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} diff --git a/crate/sm3/Cargo.toml b/crate/sm3/Cargo.toml new file mode 100644 index 0000000..37be775 --- /dev/null +++ b/crate/sm3/Cargo.toml @@ -0,0 +1,42 @@ +[package] +name = "wasm-hasher-sm3" +version = "0.1.0" +authors = ["Axetroy "] +edition = "2021" +repository = "https://github.com/axetroy/wasm-hasher" +readme = "README.md" +description = "computed data hash by webAssembly" +license = "Anti-996" +keywords = ["sm3", "wasm", "webassembly"] + +[lib] +crate-type = ["cdylib", "rlib"] + +[features] +default = ["wee_alloc"] + +[dependencies] +# The `wasm-bindgen` crate provides the bare minimum functionality needed +# to interact with JavaScript. +wasm-bindgen = "0.2.85" +sm3 = "0.4.1" +js-sys = "0.3.62" +digest = "0.10.6" +wasm-bindgen-futures = "0.4.35" +# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size +# compared to the default allocator's ~10K. However, it is slower than the default +# allocator, so it's not enabled by default. +wee_alloc = { version = "0.4.2", optional = true } +wasm-hasher-lib = { path = "../lib" } + +# The `web-sys` crate allows you to interact with the various browser APIs, +# like the DOM. +[dependencies.web-sys] +version = "0.3.61" +features = ["console", "FileReader", "Blob", "AbortSignal"] + +# These crates are used for running unit tests. +[dev-dependencies] +wasm-bindgen-test = "0.2.45" +futures = "0.1.27" +js-sys = "0.3.62" diff --git a/crate/sm3/LICENSE b/crate/sm3/LICENSE new file mode 100644 index 0000000..426eba1 --- /dev/null +++ b/crate/sm3/LICENSE @@ -0,0 +1,46 @@ +Copyright (c) 2023 Axetroy + +Anti 996 License Version 1.0 (Draft) + +Permission is hereby granted to any individual or legal entity +obtaining a copy of this licensed work (including the source code, +documentation and/or related items, hereinafter collectively referred +to as the "licensed work"), free of charge, to deal with the licensed +work for any purpose, including without limitation, the rights to use, +reproduce, modify, prepare derivative works of, distribute, publish +and sublicense the licensed work, subject to the following conditions: + +1. The individual or the legal entity must conspicuously display, +without modification, this License and the notice on each redistributed +or derivative copy of the Licensed Work. + +2. The individual or the legal entity must strictly comply with all +applicable laws, regulations, rules and standards of the jurisdiction +relating to labor and employment where the individual is physically +located or where the individual was born or naturalized; or where the +legal entity is registered or is operating (whichever is stricter). In +case that the jurisdiction has no such laws, regulations, rules and +standards or its laws, regulations, rules and standards are +unenforceable, the individual or the legal entity are required to +comply with Core International Labor Standards. + +3. The individual or the legal entity shall not induce or force its +employee(s), whether full-time or part-time, or its independent +contractor(s), in any methods, to agree in oral or written form, to +directly or indirectly restrict, weaken or relinquish his or her +rights or remedies under such laws, regulations, rules and standards +relating to labor and employment as mentioned above, no matter whether +such written or oral agreement are enforceable under the laws of the +said jurisdiction, nor shall such individual or the legal entity +limit, in any methods, the rights of its employee(s) or independent +contractor(s) from reporting or complaining to the copyright holder or +relevant authorities monitoring the compliance of the license about +its violation(s) of the said license. + +THE LICENSED WORK IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, +DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +OTHERWISE, ARISING FROM, OUT OF OR IN ANY WAY CONNECTION WITH THE +LICENSED WORK OR THE USE OR OTHER DEALINGS IN THE LICENSED WORK. \ No newline at end of file diff --git a/crate/sm3/README.md b/crate/sm3/README.md new file mode 100644 index 0000000..058b7e7 --- /dev/null +++ b/crate/sm3/README.md @@ -0,0 +1,5 @@ +### Usage + +```js +import pkg from "@axetroy/wasm-hasher-sm3"; +``` diff --git a/crate/sm3/src/lib.rs b/crate/sm3/src/lib.rs new file mode 100644 index 0000000..7f5a46c --- /dev/null +++ b/crate/sm3/src/lib.rs @@ -0,0 +1,28 @@ +use digest::Digest; +use js_sys::Function; +use sm3::Sm3; +use wasm_bindgen::prelude::*; +use web_sys::{AbortSignal, Blob}; + +// When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global +// allocator. +// +// If you don't want to use `wee_alloc`, you can safely delete this. +#[cfg(feature = "wee_alloc")] +#[global_allocator] +static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; + + +#[wasm_bindgen] +pub async fn sm3( + signal: AbortSignal, + blob: Blob, + chunk: Option, + on_progress: Option, +) -> Result { + let mut hasher = Sm3::new(); + match wasm_hasher_lib::computed(signal, blob, chunk, &on_progress, &mut hasher).await { + Ok(_) => Ok(format!("{:x}", hasher.finalize())), + Err(err) => Err(err), + } +} \ No newline at end of file diff --git a/src/lib.rs b/src/lib.rs index 34f92a8..d541ce1 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,14 +1,3 @@ -use digest::Digest; -use js_sys::{Function, Uint8Array}; -use md5::Md5; -use sha1::Sha1; -use sha2::{Sha224, Sha256, Sha384, Sha512}; -use sha3::{Sha3_224, Sha3_256, Sha3_384, Sha3_512}; -use sm3::Sm3; -use wasm_bindgen::prelude::*; -use wasm_bindgen_futures::JsFuture; -use web_sys::{AbortSignal, Blob}; - // When the `wee_alloc` feature is enabled, this uses `wee_alloc` as the global // allocator. // @@ -17,206 +6,8 @@ use web_sys::{AbortSignal, Blob}; #[global_allocator] static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; -#[wasm_bindgen] -pub async fn md5( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Md5::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha2_224( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha224::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha2_256( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha256::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha2_384( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha384::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha2_512( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha512::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha1( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha1::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha3_224( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha3_224::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha3_256( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha3_256::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha3_384( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha3_384::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sha3_512( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sha3_512::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -#[wasm_bindgen] -pub async fn sm3( - signal: AbortSignal, - blob: Blob, - chunk: Option, - on_progress: Option, -) -> Result { - let mut hasher = Sm3::new(); - match computed(signal, blob, chunk, &on_progress, &mut hasher).await { - Ok(_) => Ok(format!("{:x}", hasher.finalize())), - Err(err) => Err(err), - } -} - -pub async fn computed( - signal: AbortSignal, - blob: Blob, - chunk_size: Option, - cb: &Option, - hasher: &mut D, -) -> Result<(), JsValue> { - let size = blob.size(); - - let chunk = match chunk_size { - Some(size) => size, - None => (1024 * 1024 * 5) as f64, - }; - - let chunks = (size / chunk).ceil() as i64; - let mut start: f64 = 0.0; - - for _ in 0..chunks { - if signal.aborted() { - return Err(JsValue::from("Signal has been abort!")); - } - - let mut end = start + chunk; - end = if end >= size { size } else { end }; - let data = blob - .slice_with_f64_and_f64(start, end) - .expect("slice blob failed!"); - let buffer: JsValue = JsFuture::from(data.array_buffer()) - .await - .expect("get arrayBuffer failed!"); - hasher.update(&Uint8Array::new(&buffer).to_vec()); - match cb { - Some(func) => { - let _ = func.call1(&JsValue::null(), &JsValue::from(start / size * 100.0)); - } - None => (), - } - start += chunk; - } - - match cb { - Some(func) => { - let _ = func.call1(&JsValue::null(), &JsValue::from(100.0)); - } - None => (), - } - - Ok(()) -} +pub use wasm_hasher_md5::*; +pub use wasm_hasher_sha1::*; +pub use wasm_hasher_sha2::*; +pub use wasm_hasher_sha3::*; +pub use wasm_hasher_sm3::*;