A Bytecode Alliance project
A tool for composing WebAssembly components together.
wac
is a tool for composing WebAssembly Components
together.
The tool uses the WAC (pronounced "whack") language to define how components composed together.
The wac
language is a declarative superset of wit
for describing how components are composed together.
As an example, imagine two components name.wasm and greeter.wasm.
The wit for name.wasm is:
package example:name;
world name {
/// Exporting a 'name' function that returns a name to greet.
export name: func() -> string;
}
And the wit for greeter.wasm is:
package example:greeter;
world greeter {
/// Importing a 'name' function that returns the name to greet.
import name: func() -> string;
/// Exporting a 'greet' function that returns a greeting using the name.
export greet: func() -> string;
}
The following is an example of a wac file that composes these two components together by plugging name.wasm's "name" export into greeter.wasm's "name" import.
package example:composition;
// Instantiate the `name` component
let n = new example:name {};
// Instantiate the `greeter` component by plugging its `name`
// import with the `name` export of the `name` component.
let greeter = new example:greeter {
name: n.name,
};
// Export the greet function from the greeter component
export greeter.greet;
The result of encoding this composition is a single component that does not import anything and only exports the "greet" function.
For a full description of the wac
language see the language guide.
cargo install wac-cli
To enable support Warg component registries, specify the registry
feature:
cargo install wac-cli --features registry
The wac
CLI tool has three commands:
wac parse
- Parses a composition into a JSON representation of the AST.wac resolve
- Resolves a composition into a JSON representation.wac encode
- Encodes a WAC source file as a WebAssembly component.
To encode a composition, use the wac encode
command:
wac encode -t input.wac
This will encode input.wac
as a WebAssembly component and write the text
representation of the component to stdout.
wac encode -o output.wasm input.wac
This will encode input.wac
as a WebAssembly component named output.wasm
.
By default, wac
will create a component that embeds its dependencies (i.e. packages
referenced in a WAC source file) inside of itself rather than importing those dependencies;
to cause dependencies to be imported in the output component, use the
--import-dependencies
flag:
wac encode --import-dependencies -o output.wasm input.wac
Dependencies may be located within a deps
subdirectory, with an expected structure of:
deps/
├─ <namespace>/
│ ├─ <package>.wasm
The dependency may be also be a WIT file or a directory containing a WIT package:
deps/
├─ <namespace>/
│ ├─ <package>/
│ │ ├─ a.wit
│ │ ├─ ...
The --deps-dir
CLI option may be used to specify a different directory to
search for dependencies.
The location of specific dependencies may also be specified with the --dep
CLI option:
wac encode --dep foo:bar=./baz.wasm -o output.wasm input.wac
By default, dependencies must be binary-encoded WebAssembly components; to
enable support for WAT files, use the wat
build-time feature.
If the registry
build-time feature is enabled, then dependencies may be
automatically resolved from a Warg registry and do not need to exist in the
deps
subdirectory or specified via the --dep
CLI option.