parent
bf39e3ed80
commit
4b1e684ffc
@ -1,16 +1,19 @@ |
||||
# Summary |
||||
|
||||
- [Prerequisites](./prerequisites.md) |
||||
- [Setup](./setup.md) |
||||
- [Prerequisites](./prerequisites/index.md) |
||||
- [Rust](./prerequisites/rust.md) |
||||
- [npm](./prerequisites/npm.md) |
||||
- [Getting Started](./getting-started/index.md) |
||||
- [Installation](./getting-started/installation.md) |
||||
- [Project Setup](./getting-started/project-setup/index.md) |
||||
- [Using a Template](./getting-started/project-setup/using-a-template.md) |
||||
- [Manual Setup](./getting-started/project-setup/manual-setup.md) |
||||
- [Commands](./commands/index.md) |
||||
- [`init`](./commands/init.md) |
||||
- [`init` (DEPRECATED)](./commands/init.md) |
||||
- [`build`](./commands/build.md) |
||||
- [`pack` and `publish`](./command/pack-and-publish.md) |
||||
- [Tutorial](./tutorial/index.md) |
||||
- [Setup](./tutorial/setup.md) |
||||
- [Getting Started](./tutorial/getting-started.md) |
||||
- [Writing a Rust-WebAssembly Library](./tutorial/writing-a-rust-webassembly-library.md) |
||||
- [Packaging and Publishing](./tutorial/packaging-and-publishing.md) |
||||
- [Using your Library](./tutorial/using-your-library.md) |
||||
- [Next Steps](./tutorial/next-steps.md) |
||||
- [Contributing](./contributing.md) |
||||
|
@ -1 +1,11 @@ |
||||
# Commands |
||||
|
||||
`wasm-pack` has several commands to help you during the process of building |
||||
a Rust-generated WebAssembly project. |
||||
|
||||
- `init`: This command has been deprecated in favor of `build`. |
||||
- `build`: This command builds a `pkg` directory for you with compiled wasm and generated JS. [Learn more][build] |
||||
- `pack` and `publish`: These command will create a tarball, and optionally publish it to a registry, such as npm. [Learn more][pack-pub] |
||||
|
||||
[build]: /commands/build.html |
||||
[pack-pub]: /commands/pack-and-publish.html |
||||
|
@ -1,49 +1,6 @@ |
||||
# wasm-pack init(Deprecated) |
||||
# wasm-pack init (DEPRECATED) |
||||
|
||||
The `wasm-pack init` command creates the files neccessary for JavaScript |
||||
interoperability and for publishing a package to npm. This involves |
||||
generating a pkg folder. This pkg folder will contain the |
||||
`README` and a `package.json` file. |
||||
This command has been deprecated in favor of `build`, which does the same thing, but is |
||||
a much more representative name for the command. [Read the docs for `build`.][build] |
||||
|
||||
## Path |
||||
|
||||
The `wasm-pack init` command can be given an optional path argument, e.g.: |
||||
|
||||
``` |
||||
wasm-pack init examples/js-hello-world |
||||
``` |
||||
|
||||
This path should point to a directory that contains a `Cargo.toml` file. If no |
||||
path is given, the `init` command will run in the current directory. |
||||
|
||||
## Target |
||||
|
||||
The init command accepts a `--target` argument. This will customize the output files |
||||
to align with a particular type of JS module. This allows wasm-pack to generate either |
||||
ES6 modules or CommonJS modules for use in browser and in NodeJS. Defaults to `browser`. |
||||
The options are: |
||||
|
||||
``` |
||||
wasm-pack init --target nodejs |
||||
``` |
||||
|
||||
| Option | Description | |
||||
|-----------|-----------------------------------------------------------------------------------------------------------------| |
||||
| `nodejs` | Outputs JS that uses CommonJS modules, for use with a `require` statement. | |
||||
| `browser` | Outputs JS that uses ES6 modules, primarily for use with `import` statements and/or bundlers such as `webpack`. | |
||||
|
||||
## Scope |
||||
|
||||
The init command also accepts an optional `--scope` argument. This will scope |
||||
your package name, which is useful if your package name might conflict with |
||||
something in the public registry. For example: |
||||
|
||||
``` |
||||
wasm-pack init examples/js-hello-world --scope test |
||||
``` |
||||
|
||||
This command would create a `package.json` file for a package called |
||||
`@test/js-hello-world`. For more information about scoping, you can refer to |
||||
the npm documentation [here][npm-scope-documentation]. |
||||
|
||||
[npm-scope-documentation]: https://docs.npmjs.com/misc/scope |
||||
[build]: /commands/build.html |
||||
|
@ -0,0 +1,7 @@ |
||||
# Getting Started |
||||
|
||||
In this section, we'll teach you how to get `wasm-pack` installed and how to setup a project |
||||
to use `wasm-pack` with. |
||||
|
||||
- [Installation](/getting-started/installation.html) |
||||
- [Project Setup](/getting-started/project-setup/index.html) |
@ -0,0 +1,14 @@ |
||||
## Installation |
||||
|
||||
You can install `wasm-pack` using the following command: |
||||
|
||||
``` |
||||
cargo install wasm-pack |
||||
``` |
||||
|
||||
If you have already installed `wasm-pack` and want to install a newer version, |
||||
you can use the `--force` option, like this: |
||||
|
||||
``` |
||||
cargo install wasm-pack --force |
||||
``` |
@ -0,0 +1,8 @@ |
||||
# Project Setup |
||||
|
||||
There are a few things you need to do to setup a project for `wasm-pack`. |
||||
We strongly recommending [using a template], but you can also set the project |
||||
up [manually]. |
||||
|
||||
[using a template]: /getting-started/project-setup/using-a-template.html |
||||
[manually]: /getting-started/project-setup/manual-setup.html |
@ -0,0 +1,40 @@ |
||||
# Manual Setup |
||||
|
||||
You can create a new Rust project named `my-lib` using this command. |
||||
|
||||
``` |
||||
cargo new --lib my-lib |
||||
``` |
||||
|
||||
The `--lib` flag specifies that the project is a library, which is important |
||||
because we will be calling this code from JavaScript. |
||||
|
||||
#### Cargo.toml changes |
||||
|
||||
You will need to add `wasm-bindgen` to your `Cargo.toml` in the dependencies |
||||
section. `wasm-bindgen` is a tool that facilitates interoperability between |
||||
wasm modules and JavaScript. |
||||
|
||||
Next, add a `[lib]` section, with a new field named `crate-type` set to |
||||
`"cdylib"`. This specifies that the library is a C compatible dynamic library, |
||||
which helps `cargo` pass the correct flags to the Rust compiler when targeting |
||||
`wasm32`. |
||||
|
||||
After making these changes, your `Cargo.toml` file should look something like |
||||
this: |
||||
|
||||
``` |
||||
[package] |
||||
name = "wasm-add" |
||||
version = "0.1.0" |
||||
authors = ["Michael Gattozzi <mgattozzi@gmail.com>"] |
||||
description = "Code used to demonstrate how to use wasm-pack" |
||||
license = "MIT/Apache-2.0" |
||||
repository = "https://github.com/mgattozzi/wasm-add" |
||||
|
||||
[lib] |
||||
crate-type = ["cdylib"] |
||||
|
||||
[dependencies] |
||||
wasm-bindgen="0.2" |
||||
``` |
@ -0,0 +1,20 @@ |
||||
# Using a Template |
||||
|
||||
You can create a new Rust-WebAssembly project by using the [rustwasm wasm-pack-template]. |
||||
|
||||
To so do, you'll need the `cargo-generate` tool. To install `cargo-generate`: |
||||
|
||||
``` |
||||
cargo install cargo-generate |
||||
``` |
||||
|
||||
Then run: |
||||
|
||||
``` |
||||
cargo generate --git https://github.com/rustwasm/wasm-pack-template |
||||
``` |
||||
|
||||
You will be prompted to give your project a name. Once you do, you will have a directory |
||||
with a new project, ready to go. |
||||
|
||||
[rustwasm wasm-pack-template]: https://github.com/rustwasm/wasm-pack-template |
@ -0,0 +1,6 @@ |
||||
# Prerequisites |
||||
|
||||
To run `wasm-pack` you'll need to have both Rust and npm installed and configured. |
||||
|
||||
- [Rust](/prerequisites/rust.html) |
||||
- [npm](/prerequisites/npm.html) |
@ -0,0 +1,20 @@ |
||||
# npm |
||||
|
||||
Currently, `wasm-pack` requires that you have npm installed to pack and publish your |
||||
package. Longterm, this will be replaced by a Rust only version. |
||||
|
||||
If you would rather use another package manager that interfaces with the npm registry |
||||
you may, however, the `pack` and `publish` commands depend on having npm installed. |
||||
|
||||
You can install [npm] by following [these instructions][npm-install-info]. |
||||
|
||||
### npm Account |
||||
|
||||
Regardless of which package manager CLI tool you'l like to you, if you wish to publish |
||||
your package to the npm registry, or another npm-like registry, you'll need an npm |
||||
account. |
||||
|
||||
You can find information about signing up for npm [here][npm-signup-info]. |
||||
|
||||
[npm-install-info]: https://www.npmjs.com/get-npm |
||||
[npm-signup-info]: https://www.npmjs.com/signup |
@ -0,0 +1,31 @@ |
||||
# Rust |
||||
|
||||
`wasm-pack` is a tool written in Rust, and distributed with `cargo`. As a result, |
||||
you'll need Rust and `cargo` to use `wasm-pack`. |
||||
|
||||
To install Rust, visit this [page](https://www.rust-lang.org/en-US/install.html). |
||||
|
||||
You can be sure you have Rust and Cargo installed by running: |
||||
|
||||
``` |
||||
rustc --version |
||||
cargo --version |
||||
``` |
||||
|
||||
### `nightly` Rust |
||||
|
||||
`wasm-pack` depends on `wasm-bindgen` which currently requires Rust features that |
||||
have not yet been stabilized. As a result, you'll need to use a nightly version of |
||||
Rust to run `wasm-pack`. |
||||
|
||||
You can install the nightly channel by running: |
||||
|
||||
``` |
||||
rustup install nightly |
||||
``` |
||||
|
||||
You can configure rustup to always use `nightly` in a directory by running: |
||||
|
||||
``` |
||||
rustup override set nightly |
||||
``` |
Before Width: | Height: | Size: 21 KiB After Width: | Height: | Size: 21 KiB |
@ -1 +0,0 @@ |
||||
# Getting Started |
@ -1 +1,12 @@ |
||||
# Tutorial |
||||
|
||||
The goal of this tutorial is to introduce you to the `wasm-pack` workflow. |
||||
|
||||
This tutorial is aimed at folks who are both beginners to WebAssembly and Rust- you don't need |
||||
much Rust knowledge to complete this tutorial. |
||||
|
||||
Be sure to have done the following before starting: |
||||
|
||||
1. Read and install all the [Prerequisites](/prerequisites.html). |
||||
2. [Install `wasm-pack`](/getting-started/installation.html). |
||||
3. [Setup a new project](/getting-started/project-setup/using-a-template.html). |
||||
|
@ -1,81 +0,0 @@ |
||||
# Project Initialization |
||||
|
||||
Now that we've installed all of our tools and setup our npm account we can actually start coding! |
||||
We'll be writing up a small crate that adds two numbers and outputs the numbers. While this will |
||||
be a simple example, we're really trying to focus on how to use wasm-pack. You'll be provided links |
||||
to other resources so you can make more complicated code to package and ship them to npm! |
||||
|
||||
Let's get started then! First off run this command to create our project: |
||||
|
||||
```bash |
||||
$ cargo new --lib wasm-add |
||||
``` |
||||
|
||||
This will create a new Rust project in a directory called `wasm-add`. We've also specified that |
||||
we're building a library, since we'll be calling this code from JS. |
||||
|
||||
Now just: |
||||
|
||||
```bash |
||||
$ cd wasm-add |
||||
``` |
||||
|
||||
You'll find everything in here ready to get started. First though we'll need to add a dependency to |
||||
our code and make a few small changes. Open up your `Cargo.toml` file. You should see something like |
||||
this inside: |
||||
|
||||
```toml |
||||
[package] |
||||
name = "wasm-add" |
||||
version = "0.1.0" |
||||
authors = ["Michael Gattozzi <mgattozzi@gmail.com>"] |
||||
|
||||
[dependencies] |
||||
``` |
||||
|
||||
This configuration file sets up everything we need to get started but we'll need a few extra fields |
||||
and settings to get this to work for wasm and be ready for npm |
||||
|
||||
```toml |
||||
[package] |
||||
name = "wasm-add" |
||||
version = "0.1.0" |
||||
authors = ["Michael Gattozzi <mgattozzi@gmail.com>"] |
||||
description = "Code used to demonstrate how to use wasm-pack" |
||||
license = "MIT/Apache-2.0" |
||||
repository = "https://github.com/mgattozzi/wasm-add" |
||||
|
||||
[lib] |
||||
crate-type = ["cdylib"] |
||||
|
||||
[dependencies] |
||||
wasm-bindgen = "0.2" |
||||
``` |
||||
|
||||
First off lets look at the last three fields added to the package section `description`, `license`, |
||||
and `repository`. npm requires this metadata and so `wasm-pack` won't package your code up until you |
||||
have them set. There are more fields that you can add that are more specific to `crates.io` that you |
||||
can find [here](https://doc.rust-lang.org/cargo/reference/manifest.html) but for the sake of this |
||||
tutorial that's all you need for that section. |
||||
|
||||
You'll also notice we add a new section titled `[lib]`. In here we added this line: |
||||
|
||||
```toml |
||||
crate-type = ["cdylib"] |
||||
``` |
||||
|
||||
Normally Rust compiles the code for the library in a format meant for other Rust packages. We want |
||||
our code to work with wasm though! We specify that it's a dynamic library that's C compatible. This |
||||
sounds a bit weird but the `wasm32` target will know to interpret this option and instead produce |
||||
a wasm binary properly. This is meant to get `cargo` to pass the right parameters to the compiler! |
||||
|
||||
Alright the last thing we added was this to the `[dependencies]` section: |
||||
|
||||
```toml |
||||
wasm-bindgen = "0.2" |
||||
``` |
||||
|
||||
This is the `wasm-bindgen` crate. We'll be using it very shortly to make our functions work nicely |
||||
with wasm and not have to worry about a lot of nitty gritty details. |
||||
|
||||
We've got our package's metadata all set up, so let's actually write some code! |
@ -1,17 +0,0 @@ |
||||
# Introduction |
||||
|
||||
`wasm-pack` is a brand new tool designed to make packaging up binaries that include wasm (that may |
||||
or may not have JS in them) and make publishing them on npm easy to do. We can't necessarily |
||||
distribute Rust code to developers directly and expect them |
||||
to build it from scratch. npm is used to install packages for frontend work but it doesn't know how |
||||
to compile Rust! With wasm though it's not a problem. Once it's compiled it's all good to go. |
||||
However, getting it ready to be distributed, packaging it up properly for npm, and then sending it |
||||
to npm can be a bit of a hassle. `wasm-pack` is here to make that easier. |
||||
|
||||
We'll step through creating a simple Rust library, using `wasm-pack` to get it ready for |
||||
distribution, sending it to npm, then using it as a package from npm to verify it works! |
||||
|
||||
As with all software in the early stages, this is bleeding edge! Expect some nicks and bruises! If |
||||
you run into issues or a bug please file an issue over at it's [repo]. |
||||
|
||||
[repo]: https://github.com/rustwasm/wasm-pack/issues |
@ -1,6 +0,0 @@ |
||||
# Next Steps |
||||
|
||||
This was an introduction to wasm-pack but also using wasm code from npm. From here you could |
||||
actually improve on the project setup, expand out what your wasm code can actually do, or expand out |
||||
how you would use the package you've created. The whole wasm space is completely open so there's no |
||||
limit to what you can and can't do really! Go out there and try some cool new things. Happy hacking! |
@ -1,30 +0,0 @@ |
||||
# Tools Setup |
||||
|
||||
## Rust |
||||
|
||||
If you haven't already, you'll need to install nightly Rust with the wasm toolchain! |
||||
See [the setup section](setup.html) for more details. Once you've done that you'll need to install |
||||
the latest version of `wasm-pack`. |
||||
|
||||
```bash |
||||
$ cargo install wasm-pack |
||||
``` |
||||
|
||||
## npm |
||||
|
||||
If you also have not installed npm already you'll need to do so! Follow the docs available on |
||||
[npm](https://www.npmjs.com/get-npm). |
||||
|
||||
To confirm you've succeeded run: |
||||
|
||||
```bash |
||||
$ npm --version |
||||
``` |
||||
|
||||
You should see the version number pop out in your terminal if you installed it successfully! |
||||
|
||||
## npm account |
||||
|
||||
After you have npm installed you'll need to sign up for an account on npm if you have not already |
||||
done so in order to complete the tutorial and so you can publish your package. The sign up page can |
||||
be found [here](https://www.npmjs.com/signup). |
@ -1,137 +0,0 @@ |
||||
# Rust Code |
||||
|
||||
If you open up `src/lib.rs` you should see a file that looks like this: |
||||
|
||||
```rust |
||||
#[cfg(test)] |
||||
mod tests { |
||||
#[test] |
||||
fn it_works() { |
||||
assert_eq!(2 + 2, 4); |
||||
} |
||||
} |
||||
``` |
||||
|
||||
Let's quickly modify the test suite to work for what we'll be doing. It should look like this: |
||||
|
||||
```rust |
||||
#[test] |
||||
fn it_works() { |
||||
assert_eq!(add(2, 2), 4); |
||||
} |
||||
``` |
||||
|
||||
We'll use this later to make sure our `add` function works! |
||||
|
||||
Now we need to add this to the top of the file: |
||||
|
||||
```rust |
||||
#![feature(use_extern_macros, wasm_import_module, wasm_custom_section)] |
||||
extern crate wasm_bindgen; |
||||
use wasm_bindgen::prelude::*; |
||||
``` |
||||
|
||||
Let's step through this line by line. First up is the list of nightly features. We're enabling this for |
||||
the whole crate. What this means is that we will later tag code with an attribute and this will |
||||
allow Rust to generate code that we don't have to write by hand. In our case it'll use |
||||
`wasm-bindgen.` It should be noted that `#![feature(...)]` implies using the nightly |
||||
compiler. This gated feature will hopefully be stabilized and landed soon so that you won't need it! |
||||
|
||||
`wasm-bindgen` knows how to make code that works well with wasm so we don't have to |
||||
worry about it too much and just write Rust code for the most part. If you want to know the full |
||||
extent of its capabilities check out the README on its repo which can be found |
||||
[here](https://github.com/alexcrichton/wasm-bindgen). For our purposes we need to know that if we |
||||
want functions to work with wasm easily we'll need it. |
||||
|
||||
The next line says we're importing the `wasm-bindgen` crate and the line after that imports the |
||||
prelude from `wasm-bindgen`. The `extern crate` call lets the compiler know what crates to link in |
||||
and the `prelude` contains all the types and functions that `wasm-bindgen` needs to work properly! |
||||
|
||||
Cool let's import the `alert` function from JS so that we can call it in our Rust code! |
||||
|
||||
```rust |
||||
#[wasm_bindgen] |
||||
extern { |
||||
fn alert(s: &str); |
||||
} |
||||
``` |
||||
|
||||
Alright so we have our external bit of code and we have everything imported so let's write the |
||||
actual `add` function, as well as an `add_alert` function that will use `add` in itself but also |
||||
call `alert` to print out the results before returning the value. |
||||
|
||||
```rust |
||||
#[wasm_bindgen] |
||||
pub fn add(a: i32, b: i32) -> i32 { |
||||
a + b |
||||
} |
||||
|
||||
#[wasm_bindgen] |
||||
pub fn alert_add(a: i32, b: i32) -> i32 { |
||||
let c = add(a, b); |
||||
alert(&format!("Hello from Rust! {} + {} = {}", a, b, c)); |
||||
c |
||||
} |
||||
``` |
||||
|
||||
These functions are fairly straightforward if you're familiar with Rust, but if you're not we'll walk |
||||
through it. Both functions take a value `a` and a value `b`. We have said that both are 32 bit |
||||
integers (`i32`). We then say both will return an `i32`. The last line in a function returns the value |
||||
if there is no semicolon. So in the `add` function the value of `a + b` gets calculated and it's |
||||
value is returned! In the case of `alert_add` we store the value of the `add` function we just made |
||||
into the variable `c`. We then call `alert` saying what the add operation looked like and what the |
||||
value was! We then return what was inside `c`. Neat! |
||||
|
||||
This is all the Rust code we need to write. Your `lib.rs` file should look like this by now: |
||||
|
||||
```rust |
||||
#![feature(use_extern_macros, wasm_import_module, wasm_custom_section)] |
||||
extern crate wasm_bindgen; |
||||
use wasm_bindgen::prelude::*; |
||||
|
||||
#[wasm_bindgen] |
||||
extern { |
||||
fn alert(s: &str); |
||||
} |
||||
|
||||
#[wasm_bindgen] |
||||
pub fn add(a: i32, b: i32) -> i32 { |
||||
a + b |
||||
} |
||||
|
||||
#[wasm_bindgen] |
||||
pub fn alert_add(a: i32, b: i32) -> i32 { |
||||
let c = add(a, b); |
||||
alert(&format!("Hello from Rust! {} + {} = {}", a, b, c)); |
||||
c |
||||
} |
||||
|
||||
#[test] |
||||
fn it_works() { |
||||
assert_eq!(add(2, 2), 4); |
||||
} |
||||
``` |
||||
|
||||
Just to make sure that `add` works we'll run the test we wrote earlier: |
||||
|
||||
```bash |
||||
$ cargo test |
||||
``` |
||||
|
||||
You should get output that looks sort of like this: |
||||
|
||||
```bash |
||||
Compiling wasm-add v0.1.1 (file:///home/michael/Code/wasm-add) |
||||
Finished dev [unoptimized + debuginfo] target(s) in 0.54 secs |
||||
Running target/debug/deps/wasm_add-5d5676e23e39dbea |
||||
running 1 test |
||||
test it_works ... ok |
||||
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out |
||||
``` |
||||
|
||||
Yay it all works! Notice we didn't add a test for `alert_add`. This is because Rust won't know what |
||||
`alert` is unless the wasm code is running in the browser! Don't worry though. Once we package this |
||||
code up and upload it to npm we'll then test out that function to make sure everything works like we |
||||
expect it too! |
||||
|
||||
You can find all of the above code [here](https://github.com/mgattozzi/wasm-add). |
Loading…
Reference in new issue