Sherlock-Holo opened issue #6074:
Thanks for filing a bug report! Please fill out the TODOs below.
Note: if you want to report a security issue, please read our security policy!
Test Case
wit file
default world http { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
rust wasm code
wit_bindgen::generate!("world"); struct Runner; impl Http for Runner { fn run(url: String) -> Result<String, String> { let resp = get(&url)?; Ok(format!("wasm response: {resp}")) // Ok("wasm response: ".to_string() + &resp) // Ok(resp) } } export_http!(Runner);
rust normal codes
use async_trait::async_trait; use wasmtime::component::{bindgen, Component, Linker}; use wasmtime::{Config, Engine, Store}; bindgen!({ path: "../wit", async: true, }); struct Function; impl Function { async fn inner_get(&mut self, url: &str) -> Result<String, String> { let resp = reqwest::get(url).await.map_err(|err| err.to_string())?; Ok(resp.status().to_string()) } } #[async_trait] impl HttpImports for Function { async fn get(&mut self, url: String) -> wasmtime::Result<Result<String, String>> { Ok(self.inner_get(&url).await) } } #[tokio::main(flavor = "current_thread")] async fn main() { let mut config = Config::new(); config.wasm_component_model(true).async_support(true); let engine = Engine::new(&config).unwrap(); let component = Component::from_file(&engine, "../target/component.wasm").unwrap(); let mut linker = Linker::new(&engine); Http::add_to_linker(&mut linker, |state: &mut Function| state).unwrap(); let mut store = Store::new(&engine, Function); let (http, _instance) = Http::instantiate_async(&mut store, &component, &linker) .await .unwrap(); let result = http .call_run(&mut store, "http://www.example.com") .await .unwrap(); println!("{:?}", result); }
Steps to Reproduce
I build the rust wasm codes with
cargo b -r
, the target is set on .cargo/config.toml[build] target = "wasm32-wasi"
then I download the https://github.com/bytecodealliance/preview2-prototyping/releases/download/latest/wasi_snapshot_preview1.reactor.wasm and rename it to
wasi_snapshot_preview1.wasm
then run
wasm-tools component new ../target/wasm32-wasi/release/wasm.wasm -o ../target/component.wasm --adapt ../wasi_snapshot_preview1.wasm
to compile the wasm file, no errorthen I run the normal codes, it report error
thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: import `streams` has the wrong type Caused by: 0: instance export `drop-input-stream` has the wrong type 1: expected func found nothing', runtime/src/main.rs:39:10 note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
I run
wasm-tools component wit ../target/component.wasm
to dump the wit file, it showsinterface streams { type input-stream = u32 type output-stream = u32 record stream-error { } drop-input-stream: func(this: input-stream) write: func(this: output-stream, buf: list<u8>) -> result<u64, stream-error> drop-output-stream: func(this: output-stream) } interface filesystem { use self.streams.{output-stream} type descriptor = u32 type filesize = u64 write-via-stream: func(this: descriptor, offset: filesize) -> output-stream append-via-stream: func(this: descriptor) -> output-stream drop-descriptor: func(this: descriptor) } interface environment { get-environment: func() -> list<tuple<string, string>> } interface exit { exit: func(status: result) } interface stderr { print: func(message: string) } default world component { import streams: self.streams import filesystem: self.filesystem import environment: self.environment import exit: self.exit import stderr: self.stderr import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
a lot of things, but if I remove the
Ok(format!("wasm response: {resp}"))
in the rust wasm codes, replace withOk(resp)
, dump again and it will showsdefault world component { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
it looks like normal
Expected Results
works well
Versions and Environment
Wasmtime version or commit: wasmtime crate 7.0.0
Operating system: Archlinux
Architecture: x64
Sherlock-Holo labeled issue #6074:
Thanks for filing a bug report! Please fill out the TODOs below.
Note: if you want to report a security issue, please read our security policy!
Test Case
wit file
default world http { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
rust wasm code
wit_bindgen::generate!("world"); struct Runner; impl Http for Runner { fn run(url: String) -> Result<String, String> { let resp = get(&url)?; Ok(format!("wasm response: {resp}")) // Ok("wasm response: ".to_string() + &resp) // Ok(resp) } } export_http!(Runner);
rust normal codes
use async_trait::async_trait; use wasmtime::component::{bindgen, Component, Linker}; use wasmtime::{Config, Engine, Store}; bindgen!({ path: "../wit", async: true, }); struct Function; impl Function { async fn inner_get(&mut self, url: &str) -> Result<String, String> { let resp = reqwest::get(url).await.map_err(|err| err.to_string())?; Ok(resp.status().to_string()) } } #[async_trait] impl HttpImports for Function { async fn get(&mut self, url: String) -> wasmtime::Result<Result<String, String>> { Ok(self.inner_get(&url).await) } } #[tokio::main(flavor = "current_thread")] async fn main() { let mut config = Config::new(); config.wasm_component_model(true).async_support(true); let engine = Engine::new(&config).unwrap(); let component = Component::from_file(&engine, "../target/component.wasm").unwrap(); let mut linker = Linker::new(&engine); Http::add_to_linker(&mut linker, |state: &mut Function| state).unwrap(); let mut store = Store::new(&engine, Function); let (http, _instance) = Http::instantiate_async(&mut store, &component, &linker) .await .unwrap(); let result = http .call_run(&mut store, "http://www.example.com") .await .unwrap(); println!("{:?}", result); }
Steps to Reproduce
I build the rust wasm codes with
cargo b -r
, the target is set on .cargo/config.toml[build] target = "wasm32-wasi"
then I download the https://github.com/bytecodealliance/preview2-prototyping/releases/download/latest/wasi_snapshot_preview1.reactor.wasm and rename it to
wasi_snapshot_preview1.wasm
then run
wasm-tools component new ../target/wasm32-wasi/release/wasm.wasm -o ../target/component.wasm --adapt ../wasi_snapshot_preview1.wasm
to compile the wasm file, no errorthen I run the normal codes, it report error
thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: import `streams` has the wrong type Caused by: 0: instance export `drop-input-stream` has the wrong type 1: expected func found nothing', runtime/src/main.rs:39:10 note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
I run
wasm-tools component wit ../target/component.wasm
to dump the wit file, it showsinterface streams { type input-stream = u32 type output-stream = u32 record stream-error { } drop-input-stream: func(this: input-stream) write: func(this: output-stream, buf: list<u8>) -> result<u64, stream-error> drop-output-stream: func(this: output-stream) } interface filesystem { use self.streams.{output-stream} type descriptor = u32 type filesize = u64 write-via-stream: func(this: descriptor, offset: filesize) -> output-stream append-via-stream: func(this: descriptor) -> output-stream drop-descriptor: func(this: descriptor) } interface environment { get-environment: func() -> list<tuple<string, string>> } interface exit { exit: func(status: result) } interface stderr { print: func(message: string) } default world component { import streams: self.streams import filesystem: self.filesystem import environment: self.environment import exit: self.exit import stderr: self.stderr import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
a lot of things, but if I remove the
Ok(format!("wasm response: {resp}"))
in the rust wasm codes, replace withOk(resp)
, dump again and it will showsdefault world component { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
it looks like normal
Expected Results
works well
Versions and Environment
Wasmtime version or commit: wasmtime crate 7.0.0
Operating system: Archlinux
Architecture: x64
bjorn3 commented on issue #6074:
I think if you use wasi_snapshot_preview1.wasm you will need to provide an implementation of wasi_snapshot_preview2 on the host side. Wasmtime doesn't have an implementation of this yet afaik.
Sherlock-Holo commented on issue #6074:
@bjorn3 could you tell me how to add the
implementation of wasi_snapshot_preview2
I try to use the
wasmtime::Linker
let mut linker = Linker::new(&engine); let wasi_ctx = WasiCtxBuilder::new() .inherit_stdio() .inherit_args() .unwrap() .inherit_env() .unwrap() .build(); wasmtime_wasi::add_to_linker(&mut linker, |state: &mut Function| &mut state.wasi_ctx).unwrap();
but run still report same error
bjorn3 commented on issue #6074:
wasmtime_wasi is an implementation of wasi_snapshot_preview1, not the wasi_snapshot_preview2 you need.
Sherlock-Holo commented on issue #6074:
so i can't use the component model feature to write normal rust wasm codes, until wasmtime support preview2 ?
Sherlock-Holo commented on issue #6074:
but why if i return the resp directly, ot can works on wasmtime?
bjorn3 commented on issue #6074:
so i can't use the component model feature to write normal rust wasm codes, until wasmtime support preview2 ?
Yeah, using wasi with wasm components requires wasi preview2. I just found that https://github.com/bytecodealliance/preview2-prototyping has host support for wasi preview2 in the host/ directory. Be aware that it depends on a specific commit of wasmtime, so you will need to specify the exact same version of wasmtime: https://github.com/bytecodealliance/preview2-prototyping/blob/b4eb2043b165971820e60f077076c9484de283ed/host/Cargo.toml#L14
but why if i return the resp directly, ot can works on wasmtime?
The wasi_snapshot_preview1.wasm adapter probably got skipped due to the inner wasm module not needing any of the wasi methods when directly returning the response. Printing the response requires wasi and thus the wasi_snapshot_preview1 -> wasi_snapshot_preview2 adapter and in turn means the final wasm component needs wasi_snapshot_preview2.
Sherlock-Holo commented on issue #6074:
I change to
wasmtime = { git = "https://github.com/bytecodealliance/wasmtime", rev = "5ae8575296d5b524cde42ad10badf8c89945105a", features = ["component-model"] }
but still report errorthread 'main' panicked at 'called
Result::unwrap()
on anErr
value: importstreams
has the wrong typeCaused by:
0: instance exportdrop-input-stream
has the wrong type
1: expected func found nothing', runtime/src/main.rs:42:10
note: run withRUST_BACKTRACE=1
environment variable to display a backtraceanything I miss?
pchickey commented on issue #6074:
are you using the preview1.wasm adapter and host crate from the same revision of preview2-prototyping? use the host crate's
command::add_to_linker
on yourwasmtime::component::Linker
in order to provide thedrop-import-stream
export func that is reported missing there
Sherlock-Holo commented on issue #6074:
I change the Cargo.toml to
[package] name = "runtime" version = "0.1.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] clap = { version = "4", features = ["derive"] } tokio = { version = "1", features = ["rt", "macros", "time"] } reqwest = "0.11" wasmtime = { version = "7", features = ["component-model"] } #wasmtime = { git = "https://github.com/bytecodealliance/wasmtime", rev = "5ae8575296d5b524cde42ad10badf8c89945105a", features = ["component-model"] } #wasmtime = { git = "https://github.com/bytecodealliance/wasmtime", branch = "main", features = ["component-model"] } host = { git = "https://github.com/bytecodealliance/preview2-prototyping", branch = "main" } wasi-cap-std-sync = { git = "https://github.com/bytecodealliance/preview2-prototyping", branch = "main" } async-trait = "0.1"
and add
command::add_to_linker(&mut linker, |state: &mut Function| &mut state.wasi_ctx).unwrap();
, it works!thanks for your help~
Sherlock-Holo closed issue #6074:
Thanks for filing a bug report! Please fill out the TODOs below.
Note: if you want to report a security issue, please read our security policy!
Test Case
wit file
default world http { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
rust wasm code
wit_bindgen::generate!("world"); struct Runner; impl Http for Runner { fn run(url: String) -> Result<String, String> { let resp = get(&url)?; Ok(format!("wasm response: {resp}")) // Ok("wasm response: ".to_string() + &resp) // Ok(resp) } } export_http!(Runner);
rust normal codes
use async_trait::async_trait; use wasmtime::component::{bindgen, Component, Linker}; use wasmtime::{Config, Engine, Store}; bindgen!({ path: "../wit", async: true, }); struct Function; impl Function { async fn inner_get(&mut self, url: &str) -> Result<String, String> { let resp = reqwest::get(url).await.map_err(|err| err.to_string())?; Ok(resp.status().to_string()) } } #[async_trait] impl HttpImports for Function { async fn get(&mut self, url: String) -> wasmtime::Result<Result<String, String>> { Ok(self.inner_get(&url).await) } } #[tokio::main(flavor = "current_thread")] async fn main() { let mut config = Config::new(); config.wasm_component_model(true).async_support(true); let engine = Engine::new(&config).unwrap(); let component = Component::from_file(&engine, "../target/component.wasm").unwrap(); let mut linker = Linker::new(&engine); Http::add_to_linker(&mut linker, |state: &mut Function| state).unwrap(); let mut store = Store::new(&engine, Function); let (http, _instance) = Http::instantiate_async(&mut store, &component, &linker) .await .unwrap(); let result = http .call_run(&mut store, "http://www.example.com") .await .unwrap(); println!("{:?}", result); }
Steps to Reproduce
I build the rust wasm codes with
cargo b -r
, the target is set on .cargo/config.toml[build] target = "wasm32-wasi"
then I download the https://github.com/bytecodealliance/preview2-prototyping/releases/download/latest/wasi_snapshot_preview1.reactor.wasm and rename it to
wasi_snapshot_preview1.wasm
then run
wasm-tools component new ../target/wasm32-wasi/release/wasm.wasm -o ../target/component.wasm --adapt ../wasi_snapshot_preview1.wasm
to compile the wasm file, no errorthen I run the normal codes, it report error
thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: import `streams` has the wrong type Caused by: 0: instance export `drop-input-stream` has the wrong type 1: expected func found nothing', runtime/src/main.rs:39:10 note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
I run
wasm-tools component wit ../target/component.wasm
to dump the wit file, it showsinterface streams { type input-stream = u32 type output-stream = u32 record stream-error { } drop-input-stream: func(this: input-stream) write: func(this: output-stream, buf: list<u8>) -> result<u64, stream-error> drop-output-stream: func(this: output-stream) } interface filesystem { use self.streams.{output-stream} type descriptor = u32 type filesize = u64 write-via-stream: func(this: descriptor, offset: filesize) -> output-stream append-via-stream: func(this: descriptor) -> output-stream drop-descriptor: func(this: descriptor) } interface environment { get-environment: func() -> list<tuple<string, string>> } interface exit { exit: func(status: result) } interface stderr { print: func(message: string) } default world component { import streams: self.streams import filesystem: self.filesystem import environment: self.environment import exit: self.exit import stderr: self.stderr import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
a lot of things, but if I remove the
Ok(format!("wasm response: {resp}"))
in the rust wasm codes, replace withOk(resp)
, dump again and it will showsdefault world component { import get: func(url: string) -> result<string, string> export run: func(url: string) -> result<string, string> }
it looks like normal
Expected Results
works well
Versions and Environment
Wasmtime version or commit: wasmtime crate 7.0.0
Operating system: Archlinux
Architecture: x64
DougAnderson444 commented on issue #6074:
I am still seeing this error, noting that a few things have changed since March
Error: import `wasi:io/streams` has the wrong type Caused by: 0: instance export `drop-input-stream` has the wrong type 1: expected func found nothing
1) First I used
--adapt
as per the instructions2) Next I also see that
preview2-prototyping
moved tocrates/wasi-preview1-component-adapter
so I also tried# Cargo.toml [dev-dependencies] wasi-preview1-component-adapter = { git = "https://github.com/bytecodealliance/wasmtime", default-features = false, features = [ "command", ] }
...in order to use the
command::add_to_linker
move, but thefeature
selection doesn't seem to be working ascommand
isn't available?
Last updated: Dec 23 2024 at 12:05 UTC