Available on crate feature
runtime
and crate feature component-model
and docsrs
and crate feature component-model-async
only.Expand description
Example of using StoreContextMut
in imported functions.
This is an example of using the store
option to the imports
configuration of the bindgen!
macro. Like
seen in previous examples a
MyWorldImports
trait is generated
for my-world
, but imports that have access to the store get added to a
separate trait with a *WithStore
suffix, in this case
MyWorldImportsWithStore
.
This second trait provides access to a StoreContextMut
.
use wasmtime::component::{bindgen, HasData, Access, Accessor};
use wasmtime::{StoreContextMut, AsContextMut};
bindgen!({
inline: r#"
package example:store-in-imports;
world my-world {
import sync-with-store: func();
import async-with-store: async func();
import sync-without-store: func();
import async-without-store: func();
export run: async func();
}
"#,
imports: {
"sync-with-store": store,
// note that this isn't required because WIT-level `async` functions
// always have access to the store.
// "async-with-store": store,
"async-without-store": async,
},
});
struct MyState {
// ...
}
impl HasData for MyState {
type Data<'a> = &'a mut MyState;
}
impl MyWorldImportsWithStore for MyState {
/// Synchronous functions that have access to the store are defined in
/// Rust as a normal `fn` with an `Access` as the first parameter.
fn sync_with_store<T>(mut host: Access<'_, T, Self>) {
// The `Access` type implements `AsContextMut` to manipulate and
// operate on the store.
let mut store: StoreContextMut<'_, T> = host.as_context_mut();
// The `Access` type can be used to get the `Data` projection of
// the `HasData` trait implementation above, in this case
// ourselves.
let my_state: &mut MyState = host.get();
}
/// Asynchronous functions that have access to the store are defined in
/// Rust as an `async fn` with an `Accessor` as the first parameter.
async fn async_with_store<T>(accessor: &Accessor<T, Self>) {
// The `Accessor` type does not implement `AsContextMut` directly
// and instead represents the ability to, synchronously, work with
// the store. Notably borrows into the store or `Self` cannot be
// persisted across await points
accessor.with(|mut access| {
// same as `sync_with_store` above
let mut store: StoreContextMut<'_, T> = access.as_context_mut();
let my_state: &mut MyState = access.get();
// ...
});
some_function().await;
accessor.with(|mut access| {
// ...
});
}
}
// Functions that don't have access to the store are defined with
// `&mut self` indicating that they can only access data in `self`, not the
// entire store.
impl MyWorldImports for MyState {
fn sync_without_store(&mut self) { /* ... */ }
async fn async_without_store(&mut self) { /* ... */ }
}
Structs§
- MyWorld
- Auto-generated bindings for an instance a component which
implements the world
my-world
. - MyWorld
Indices - Auto-generated bindings for index of the exports of
my-world
. - MyWorld
Pre - Auto-generated bindings for a pre-instantiated version of a
component which implements the world
my-world
.