Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "componentize-py"
version = "0.22.1"
version = "0.23.0"
edition = "2024"
exclude = ["cpython"]

Expand Down
4 changes: 2 additions & 2 deletions examples/cli-p3/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,15 +11,15 @@ run a Python-based component targetting version `0.3.0-rc-2026-03-15` of the
## Prerequisites

* `Wasmtime` 43.0.0
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v43.0.0.

```
cargo install --version 43.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/cli/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,15 @@ run a Python-based component targetting the [wasi-cli] `command` world.
## Prerequisites

* `Wasmtime` 38.0.0 or later
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v38.0.0.

```
cargo install --version 38.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/http-p3/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,15 +11,15 @@ run a Python-based component targetting version `0.3.0-rc-2026-03-15` of the
## Prerequisites

* `Wasmtime` 43.0.0
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v43.0.0.

```
cargo install --version 43.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/http/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,15 @@ run a Python-based component targetting the [wasi-http] `proxy` world.
## Prerequisites

* `Wasmtime` 38.0.0 or later
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v38.0.0.

```
cargo install --version 38.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/matrix-math/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ within a guest component.
## Prerequisites

* `wasmtime` 38.0.0 or later
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0
* `NumPy`, built for WASI

Note that we use an unofficial build of NumPy since the upstream project does
Expand All @@ -23,7 +23,7 @@ https://github.com/bytecodealliance/wasmtime/releases/tag/v38.0.0.

```
cargo install --version 38.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
curl -OL https://github.com/dicej/wasi-wheels/releases/download/v0.0.2/numpy-wasi.tar.gz
tar xf numpy-wasi.tar.gz
```
Expand Down
4 changes: 2 additions & 2 deletions examples/sandbox/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@ versions have a different API for working with components, and this example has
not yet been updated to use it.

* `wasmtime-py` 38.0.0
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

```
pip install componentize-py==0.22.1 wasmtime==38.0.0
pip install componentize-py==0.23.0 wasmtime==38.0.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/tcp-p3/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,15 +12,15 @@ run a Python-based component targetting version `0.3.0-rc-2026-03-15` of the
## Prerequisites

* `Wasmtime` 43.0.0
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v43.0.0.

```
cargo install --version 43.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
4 changes: 2 additions & 2 deletions examples/tcp/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,15 +11,15 @@ making an outbound TCP request using `wasi-sockets`.
## Prerequisites

* `Wasmtime` 38.0.0 or later
* `componentize-py` 0.22.1
* `componentize-py` 0.23.0

Below, we use [Rust](https://rustup.rs/)'s `cargo` to install `Wasmtime`. If
you don't have `cargo`, you can download and install from
https://github.com/bytecodealliance/wasmtime/releases/tag/v38.0.0.

```
cargo install --version 38.0.0 wasmtime-cli
pip install componentize-py==0.22.1
pip install componentize-py==0.23.0
```

## Running the demo
Expand Down
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ features = ["pyo3/extension-module"]

[project]
name = "componentize-py"
version = "0.22.1"
version = "0.23.0"
description = "Tool to package Python applications as WebAssembly components"
readme = "README.md"
license = { file = "LICENSE" }
Expand Down
125 changes: 123 additions & 2 deletions src/command.rs
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,14 @@ pub enum Command {

/// Generate Python bindings for the world and write them to the specified
/// directory.
///
/// Note that bindings generated using this command are only stubs which
/// unconditionally raise `NotImplementedError`s. They are meant for use by
/// e.g. IDEs, type checkers, and document generators. The `componentize`
/// subcommand will generate the real code (i.e. code connected to the
/// components actual imports and exports) on-the-fly as necessary. The
/// bindings generated by this command need not and should not be used by an
/// actual component produced using the `componentize` command.
Bindings(Bindings),
}

Expand Down Expand Up @@ -183,7 +191,7 @@ pub fn run<T: Into<OsString> + Clone, I: IntoIterator<Item = T>>(args: I) -> Res

fn generate_bindings(common: Common, bindings: Bindings) -> Result<()> {
BindingsGenerator {
wit_path: &common
wit_paths: &common
.wit_path
.iter()
.map(|v| v.as_path())
Expand Down Expand Up @@ -226,7 +234,7 @@ fn componentize(common: Common, componentize: Componentize) -> Result<()> {

Runtime::new()?.block_on(
ComponentGenerator {
wit_path: &common
wit_paths: &common
.wit_path
.iter()
.map(|v| v.as_path())
Expand Down Expand Up @@ -521,4 +529,117 @@ class Bindings(bindings.Bindings):
};
componentize(common, componentize_opts)
}

#[test]
fn mix_of_cli_and_dependency_wits_and_worlds() -> Result<()> {
let dir = tempfile::tempdir()?;

let cli_wit_file = dir.path().join("cli.wit");
fs::write(
&cli_wit_file,
br#"
package test:cli;

interface cli-interface {
foo: func();
}

world cli-world {
import cli-interface;
export cli-interface;
export foo: func();
}
"#,
)?;

let app_file = dir.path().join("app.py");
fs::write(
&app_file,
br#"
import cli_world
from cli_world import exports
from cli_world.imports import cli_interface
from lib.wit.imports import lib_interface

class CliWorld(cli_world.CliWorld):
def foo(self) -> None:
pass

class CliInterface(exports.CliInterface):
def foo(self) -> None:
lib_interface.foo()
cli_interface.foo()
"#,
)?;

let lib_dir = dir.path().join("lib");
let lib_wit_dir = lib_dir.join("wit");
fs::create_dir_all(&lib_wit_dir)?;

fs::write(
lib_dir.join("componentize-py.toml"),
br#"
wit_directory = "wit"
bindings = "wit"
"#,
)?;

fs::write(
lib_wit_dir.join("lib.wit"),
br#"
package test:lib;

interface lib-interface {
foo: func();
}

world lib-world {
import lib-interface;
}
"#,
)?;

generate_bindings(
Common {
wit_path: vec![lib_wit_dir.clone()],
world: vec!["test:lib/lib-world".into()],
world_module: Some("lib.wit".into()),
quiet: false,
features: Vec::new(),
all_features: false,
import_interface_name: Vec::new(),
export_interface_name: Vec::new(),
full_names: false,
},
Bindings {
output_dir: lib_wit_dir,
},
)?;

componentize(
Common {
wit_path: vec![cli_wit_file],
world: vec!["test:cli/cli-world".into(), "test:lib/lib-world".into()],
world_module: Some("cli_world".into()),
quiet: false,
features: Vec::new(),
all_features: false,
import_interface_name: Vec::new(),
export_interface_name: Vec::new(),
full_names: false,
},
Componentize {
app_name: "app".into(),
python_path: vec![
dir.path()
.to_str()
.ok_or_else(|| anyhow::anyhow!("non-UTF8 path"))?
.into(),
],
module_worlds: vec![],
output: dir.path().join("app.wasm"),
stub_wasi: false,
},
)
}
}
Loading
Loading