-
Notifications
You must be signed in to change notification settings - Fork 1.1k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Expose helpers to allow synchronous initialization (#2924)
* Expose helpers to allow synchronous initialization * fixup: fix tests
- Loading branch information
Showing
12 changed files
with
216 additions
and
18 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
[package] | ||
name = "synchronous-instantiation" | ||
version = "0.1.0" | ||
authors = ["The wasm-bindgen Developers"] | ||
edition = "2018" | ||
|
||
[lib] | ||
crate-type = ["cdylib"] | ||
|
||
[dependencies] | ||
wasm-bindgen = "0.2.80" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
# Synchronous Instantiation | ||
|
||
[View documentation for this example online][dox] | ||
|
||
[dox]: https://rustwasm.github.io/docs/wasm-bindgen/examples/synchronous-instantiation.html | ||
|
||
You can build the example locally with: | ||
|
||
``` | ||
$ wasm-pack build --target web | ||
``` | ||
|
||
Then serve this directory in your favourite webserver and navigate to `host:port` | ||
to open the index.html in your browser: | ||
|
||
``` | ||
# static server from https://crates.io/crates/https | ||
http | ||
# or use python | ||
python2 -m SimpleHTTPServer | ||
python3 -m http.server | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
#!/bin/sh | ||
|
||
set -ex | ||
|
||
wasm-pack build --target web | ||
python3 -m http.server |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
<!DOCTYPE html> | ||
<html lang="en"> | ||
<head> | ||
<meta charset="UTF-8" /> | ||
<meta http-equiv="X-UA-Compatible" content="IE=edge" /> | ||
<meta name="viewport" content="width=device-width, initial-scale=1.0" /> | ||
<title>Document</title> | ||
</head> | ||
<body> | ||
<script> | ||
/** | ||
* First off we spawn a Web Worker. That's where our lib will be used. Note that | ||
* we set the `type` to `module` to enable support for ES modules. | ||
*/ | ||
const worker = new Worker("/worker.js", { type: "module" }); | ||
|
||
/** | ||
* Here we listen for messages from the worker. | ||
*/ | ||
worker.onmessage = ({ data }) => { | ||
const { type } = data; | ||
|
||
switch (type) { | ||
case "FETCH_WASM": { | ||
/** | ||
* The worker wants to fetch the bytes for the module and for that we can use the `fetch` API. | ||
* Then we convert the response into an `ArrayBuffer` and transfer the bytes back to the worker. | ||
* | ||
* @see https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API | ||
* @see https://developer.mozilla.org/en-US/docs/Glossary/Transferable_objects | ||
*/ | ||
fetch("/pkg/synchronous_instantiation_bg.wasm") | ||
.then((response) => response.arrayBuffer()) | ||
.then((bytes) => { | ||
worker.postMessage(bytes, [bytes]); | ||
}); | ||
break; | ||
} | ||
default: { | ||
break; | ||
} | ||
} | ||
}; | ||
</script> | ||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
use wasm_bindgen::prelude::*; | ||
|
||
#[wasm_bindgen] | ||
extern "C" { | ||
#[wasm_bindgen(js_namespace = console)] | ||
fn log(value: &str); | ||
} | ||
|
||
#[wasm_bindgen] | ||
pub fn greet(name: &str) { | ||
log(&format!("Hello, {}!", name)); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
import * as wasm from "./pkg/synchronous_instantiation.js"; | ||
|
||
self.onmessage = ({ data: bytes }) => { | ||
/** | ||
* When we receive the bytes as an `ArrayBuffer` we can use that to | ||
* synchronously initialize the module as opposed to asynchronously | ||
* via the default export. The synchronous method internally uses | ||
* `new WebAssembly.Module()` and `new WebAssembly.Instance()`. | ||
*/ | ||
wasm.initSync(bytes); | ||
|
||
/** | ||
* Once initialized we can call our exported `greet()` functions. | ||
*/ | ||
wasm.greet("Dominic"); | ||
}; | ||
|
||
/** | ||
* Once the Web Worker was spwaned we ask the main thread to fetch the bytes | ||
* for the WebAssembly module. Once fetched it will send the bytes back via | ||
* a `postMessage` (see above). | ||
*/ | ||
self.postMessage({ type: "FETCH_WASM" }); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
# Synchronous Instantiation | ||
|
||
[View full source code][code] | ||
|
||
[code]: https://github.com/rustwasm/wasm-bindgen/tree/master/examples/synchronous-instantiation | ||
|
||
This example shows how to synchronously initialize a WebAssembly module as opposed to [asynchronously][without-bundler]. In most cases, the default way of asynchronously initializing a module will suffice. However, there might be use cases where you'd like to lazy load a module on demand and synchronously compile and instantiate it. Note that this only works off the main thread and since compilation and instantiation of large modules can be expensive you should only use this method if it's absolutely required in your use case. Otherwise you should use the [default method][without-bundler]. | ||
|
||
For this deployment strategy bundlers like Webpack are not required. For more information on deployment see the [dedicated | ||
documentation][deployment]. | ||
|
||
First let's take a look at our tiny lib: | ||
|
||
```rust | ||
{{#include ../../../examples/synchronous-instantiation/src/lib.rs}} | ||
``` | ||
|
||
Next, let's have a look at the `index.html`: | ||
|
||
```html | ||
{{#include ../../../examples/synchronous-instantiation/index.html}} | ||
``` | ||
|
||
Otherwise the rest of the magic happens in `worker.js`: | ||
|
||
```js | ||
{{#include ../../../examples/synchronous-instantiation/worker.js}} | ||
``` | ||
|
||
And that's it! Be sure to read up on the [deployment options][deployment] to see what it means to deploy without a bundler. | ||
|
||
[deployment]: ../reference/deployment.html | ||
[without-bundler]: ./without-a-bundler.html |