refactor: repack external bindings into their own crates (#19)
Split the monolithic crate into a Cargo workspace with the Python and Wasm bindings as separate member crates.
- Cargo.toml: declare a `[workspace]` with members `.`/`crates/swactor-python`/`crates/swactor-wasm`, remove the `python` feature and pyo3 dependency, and change root crate-type from `["cdylib","rlib"]` to `["rlib"]`
- crates/swactor-python: new cdylib crate re-exporting the PyO3 bindings (Runtime/RuntimeConfig/RuntimeHandle/Inbox/Ctx/ActorAddress/RuntimeStats), depending on `swactor` + pyo3; pyproject.toml and uv.lock relocated here from the root
- crates/swactor-wasm: new cdylib crate moved from top-level `wasm/`, depending on `swactor` with `no_random` features
- src/actor.rs: widen `Actor::new`, `AnyActor`, `ContextInner`, and `Ctx::raw_inner` to `pub` so the separate binding crates can drive the runtime
- src/lib.rs: delete the in-tree `python` module and `#[pymodule]`, and gate the `no_random` RNG behind `all(feature = "no_random", not(feature = "getrandom"))`
- tools/: relocate package.json/package-lock.json; drop the now-duplicate `wasm/Cargo.lock`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-02-07 17:39:02 +00:00
|
|
|
[workspace]
|
2026-02-16 15:57:55 +00:00
|
|
|
members = [
|
|
|
|
|
".",
|
2026-02-24 09:12:28 +00:00
|
|
|
"crates/bindings/python",
|
|
|
|
|
"crates/bindings/wasm-runtime",
|
2026-02-23 04:44:46 +00:00
|
|
|
"crates/process",
|
2026-07-28 07:29:31 +00:00
|
|
|
"crates/provisioning",
|
2026-02-24 09:12:28 +00:00
|
|
|
"crates/transport",
|
2026-05-21 19:48:02 +00:00
|
|
|
"crates/distribution",
|
2026-06-23 20:10:41 +00:00
|
|
|
"crates/iroh-driver",
|
2026-06-09 09:29:07 +00:00
|
|
|
"crates/datastream",
|
2026-07-28 07:29:31 +00:00
|
|
|
"crates/data-plane",
|
2026-06-25 12:30:18 +00:00
|
|
|
"crates/dashboard",
|
refactor: `mvp-system` is now a standalone app, `myelin`
Promote the `mvp-system` workspace library crate to a standalone application at `apps/myelin`, rebranding the MVP system along with its binaries, node image, and spec.
- workspace `Cargo.toml`: swap member `crates/mvp-system` -> `apps/myelin` and drop `apps` from `exclude` so the app joins the workspace
- `apps/myelin/Cargo.toml`: declare package `myelin` with `autobins = false` and explicit `[[bin]]` targets `myelin-worker`, `myelin-orchestrator`, `myelin-chat`
- `apps/myelin/src`: move the whole `mvp-system` source tree and rebrand module surfaces (`chat/mod.rs`, `prompt/mod.rs`); add `bin/chat.rs` (`myelin::run_chat_from_args`) and delete the old `mvp_chat.rs`
- `apps/myelin/node-image`: relocate the worker image assets from `apps/mvp-node/` (Dockerfile, Dockerfile.base, tinygrad_worker.py, entrypoint, e2e script) and rename `MVP_SYSTEM_SPEC.md` -> `MYELIN_SPEC.md`
- `xtask`: rewrite build/reference paths for the rename (~1000-line churn); add `crates/dashboard/ACTOR_PANEL_SPEC.md`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-08-01 09:46:55 +00:00
|
|
|
"apps/myelin",
|
2026-02-16 15:57:55 +00:00
|
|
|
"xtask",
|
2026-06-23 20:10:41 +00:00
|
|
|
"tools/vastai",
|
2026-02-16 15:57:55 +00:00
|
|
|
]
|
2026-08-03 10:18:24 +00:00
|
|
|
default-members = [
|
|
|
|
|
".",
|
|
|
|
|
"crates/process",
|
|
|
|
|
"crates/provisioning",
|
|
|
|
|
"crates/transport",
|
|
|
|
|
"crates/distribution",
|
|
|
|
|
"crates/iroh-driver",
|
|
|
|
|
"crates/datastream",
|
|
|
|
|
"crates/data-plane",
|
|
|
|
|
"crates/dashboard",
|
|
|
|
|
"apps/myelin",
|
|
|
|
|
"tools/vastai",
|
|
|
|
|
]
|
|
|
|
|
# The language bindings (python, wasm) and xtask are built on demand
|
|
|
|
|
# (-p / --workspace / cargo-xtask), not during normal native iteration.
|
refactor: `mvp-system` is now a standalone app, `myelin`
Promote the `mvp-system` workspace library crate to a standalone application at `apps/myelin`, rebranding the MVP system along with its binaries, node image, and spec.
- workspace `Cargo.toml`: swap member `crates/mvp-system` -> `apps/myelin` and drop `apps` from `exclude` so the app joins the workspace
- `apps/myelin/Cargo.toml`: declare package `myelin` with `autobins = false` and explicit `[[bin]]` targets `myelin-worker`, `myelin-orchestrator`, `myelin-chat`
- `apps/myelin/src`: move the whole `mvp-system` source tree and rebrand module surfaces (`chat/mod.rs`, `prompt/mod.rs`); add `bin/chat.rs` (`myelin::run_chat_from_args`) and delete the old `mvp_chat.rs`
- `apps/myelin/node-image`: relocate the worker image assets from `apps/mvp-node/` (Dockerfile, Dockerfile.base, tinygrad_worker.py, entrypoint, e2e script) and rename `MVP_SYSTEM_SPEC.md` -> `MYELIN_SPEC.md`
- `xtask`: rewrite build/reference paths for the rename (~1000-line churn); add `crates/dashboard/ACTOR_PANEL_SPEC.md`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-08-01 09:46:55 +00:00
|
|
|
exclude = ["crates/bindings/wasm-crypto", "examples"]
|
2026-08-03 10:18:24 +00:00
|
|
|
[workspace.dependencies]
|
|
|
|
|
# Centralized so every member resolves tokio with the SAME feature set.
|
|
|
|
|
# Without this, members declared tokio with different features, so building
|
|
|
|
|
# one member vs another (or `run` vs `test`) recompiled tokio each time.
|
|
|
|
|
tokio = { version = "1", features = ["rt", "rt-multi-thread", "macros", "process", "io-util", "sync", "time", "net", "signal"] }
|
refactor: repack external bindings into their own crates (#19)
Split the monolithic crate into a Cargo workspace with the Python and Wasm bindings as separate member crates.
- Cargo.toml: declare a `[workspace]` with members `.`/`crates/swactor-python`/`crates/swactor-wasm`, remove the `python` feature and pyo3 dependency, and change root crate-type from `["cdylib","rlib"]` to `["rlib"]`
- crates/swactor-python: new cdylib crate re-exporting the PyO3 bindings (Runtime/RuntimeConfig/RuntimeHandle/Inbox/Ctx/ActorAddress/RuntimeStats), depending on `swactor` + pyo3; pyproject.toml and uv.lock relocated here from the root
- crates/swactor-wasm: new cdylib crate moved from top-level `wasm/`, depending on `swactor` with `no_random` features
- src/actor.rs: widen `Actor::new`, `AnyActor`, `ContextInner`, and `Ctx::raw_inner` to `pub` so the separate binding crates can drive the runtime
- src/lib.rs: delete the in-tree `python` module and `#[pymodule]`, and gate the `no_random` RNG behind `all(feature = "no_random", not(feature = "getrandom"))`
- tools/: relocate package.json/package-lock.json; drop the now-duplicate `wasm/Cargo.lock`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-02-07 17:39:02 +00:00
|
|
|
|
2025-11-25 00:39:17 +00:00
|
|
|
[package]
|
|
|
|
|
name = "swactor"
|
|
|
|
|
version = "0.1.0"
|
|
|
|
|
edition = "2024"
|
feat: proper `README`, `LICENSE`, and our first quick example
Add project licensing and a full README, plus a minimal WebAssembly ping-pong example that exercises the actor runtime.
- `LICENSE`: add the full GNU AGPL-3.0 text and set `license = "AGPL-3.0-only"` on every package (`swactor`, each crate, `apps/myelin`, `tools/vastai`, `xtask`)
- `README.md`: rewrite from a stub into a full project overview, covering features (actor_id routing, WASM, iroh QUIC/SWIM, OTP-style std, process manager, zero-copy objects, datastream metrics, dashboard), architecture, examples, developing, status, and license
- `examples/ping-pong`: new standalone workspace (`pingpong` cdylib) where two actors volley on a single-threaded `wasm` runtime driven by a Node host via `tick()`, demonstrating spawning, message passing, and death monitoring (`watching`)
- `examples/ping-pong`: add a host/run harness -- `run.sh` (wasm-pack build + `run.mjs`), `serve.sh` (dashboard + static demo), `index.html`, and a pinned `Cargo.lock`
- `.gitignore`: stop ignoring `.loop/`, `.deployment-notes/`, and `.omp/`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-08-05 20:29:27 +00:00
|
|
|
license = "AGPL-3.0-only"
|
feat: Stress tests, benchmarking, and non-failing queues and inboxes #3
Adds some basic benchmarking, stress tests. They still need to be properly examined to ensure they are testing the correct properties, but fit for "good enough". Implements the HybridChannel type, which features a channel buffer that can withstand overflows. It does so by providing a dequeue behind a mutex. Without overflow, will push messages into the lock free ArrayQueue implemented by crossbeam_queue; when that buffer fills, will use the locking portion provided by the Mutex<VecDequeue>.
In the future we can even further optimize this, perhaps with some linked list implementations of lock-free channels, but, like the benchmarks, this fits the "good enough" bar for now.
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-01-26 07:14:00 +00:00
|
|
|
autobenches = false
|
2025-11-25 00:39:17 +00:00
|
|
|
|
2026-02-09 14:42:25 +00:00
|
|
|
[profile.bench]
|
2026-02-16 15:57:55 +00:00
|
|
|
debug = true
|
|
|
|
|
strip = false
|
2026-02-09 14:42:25 +00:00
|
|
|
|
2025-11-25 00:39:17 +00:00
|
|
|
[lib]
|
refactor: repack external bindings into their own crates (#19)
Split the monolithic crate into a Cargo workspace with the Python and Wasm bindings as separate member crates.
- Cargo.toml: declare a `[workspace]` with members `.`/`crates/swactor-python`/`crates/swactor-wasm`, remove the `python` feature and pyo3 dependency, and change root crate-type from `["cdylib","rlib"]` to `["rlib"]`
- crates/swactor-python: new cdylib crate re-exporting the PyO3 bindings (Runtime/RuntimeConfig/RuntimeHandle/Inbox/Ctx/ActorAddress/RuntimeStats), depending on `swactor` + pyo3; pyproject.toml and uv.lock relocated here from the root
- crates/swactor-wasm: new cdylib crate moved from top-level `wasm/`, depending on `swactor` with `no_random` features
- src/actor.rs: widen `Actor::new`, `AnyActor`, `ContextInner`, and `Ctx::raw_inner` to `pub` so the separate binding crates can drive the runtime
- src/lib.rs: delete the in-tree `python` module and `#[pymodule]`, and gate the `no_random` RNG behind `all(feature = "no_random", not(feature = "getrandom"))`
- tools/: relocate package.json/package-lock.json; drop the now-duplicate `wasm/Cargo.lock`
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-02-07 17:39:02 +00:00
|
|
|
crate-type = ["rlib"]
|
2025-11-25 00:39:17 +00:00
|
|
|
|
2026-01-23 05:00:57 +00:00
|
|
|
[features]
|
2026-02-24 09:12:28 +00:00
|
|
|
default = ["getrandom", "std"]
|
|
|
|
|
std = [] # OTP patterns: supervisors, registries, timers, routers
|
2026-01-23 05:00:57 +00:00
|
|
|
getrandom = ["dep:getrandom"]
|
2026-02-08 16:18:39 +00:00
|
|
|
serde = ["dep:serde"]
|
2026-02-09 09:04:57 +00:00
|
|
|
tracing = ["dep:tracing"]
|
feat: Stress tests, benchmarking, and non-failing queues and inboxes #3
Adds some basic benchmarking, stress tests. They still need to be properly examined to ensure they are testing the correct properties, but fit for "good enough". Implements the HybridChannel type, which features a channel buffer that can withstand overflows. It does so by providing a dequeue behind a mutex. Without overflow, will push messages into the lock free ArrayQueue implemented by crossbeam_queue; when that buffer fills, will use the locking portion provided by the Mutex<VecDequeue>.
In the future we can even further optimize this, perhaps with some linked list implementations of lock-free channels, but, like the benchmarks, this fits the "good enough" bar for now.
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-01-26 07:14:00 +00:00
|
|
|
no_random = [] # compile without access to a source of randomness
|
2026-02-16 15:57:55 +00:00
|
|
|
transport = [
|
|
|
|
|
] # transport-agnostic messaging (no mandatory deps; codec is user-provided)
|
2026-02-13 13:27:34 +00:00
|
|
|
wasm = ["no_random", "dep:web-time"] # browser/wasm32 target support
|
2026-01-23 05:00:57 +00:00
|
|
|
|
2025-11-25 00:39:17 +00:00
|
|
|
[dependencies]
|
2026-01-23 05:00:57 +00:00
|
|
|
getrandom = { version = "0.2", optional = true }
|
2026-02-08 16:18:39 +00:00
|
|
|
serde = { version = "1", features = ["derive"], optional = true }
|
2026-02-09 09:04:57 +00:00
|
|
|
tracing = { version = "0.1", optional = true }
|
2026-02-13 13:27:34 +00:00
|
|
|
web-time = { version = "0.2", optional = true }
|
2026-01-23 05:00:57 +00:00
|
|
|
crossbeam-queue = "0.3.12"
|
2026-02-06 11:25:37 +00:00
|
|
|
crossbeam-utils = "0.8.21"
|
2026-06-24 11:04:39 +00:00
|
|
|
parking_lot = "0.12"
|
feat: Stress tests, benchmarking, and non-failing queues and inboxes #3
Adds some basic benchmarking, stress tests. They still need to be properly examined to ensure they are testing the correct properties, but fit for "good enough". Implements the HybridChannel type, which features a channel buffer that can withstand overflows. It does so by providing a dequeue behind a mutex. Without overflow, will push messages into the lock free ArrayQueue implemented by crossbeam_queue; when that buffer fills, will use the locking portion provided by the Mutex<VecDequeue>.
In the future we can even further optimize this, perhaps with some linked list implementations of lock-free channels, but, like the benchmarks, this fits the "good enough" bar for now.
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-01-26 07:14:00 +00:00
|
|
|
|
2026-02-06 11:25:37 +00:00
|
|
|
[dev-dependencies]
|
|
|
|
|
criterion = { version = "0.5", features = ["html_reports"] }
|
feat(std): add supervision, router, and registries
Adds the std crate on top of the core runtime: Supervisor with RestartPolicy
(Permanent/Transient/Temporary) and SupervisorStrategy (OneForOne/OneForAll/
RestForOne), Router with RoutingStrategy, name/monitor/group registries, StdExtension,
and Ctx/Runtime extension traits. Also extends core (worker, actor, delivery identity
hashing, config, stats), adds a fuzz target, a proptest suite, expands runtime_api
tests, and adds cfuzz cycle notes + benchmarks.
Signed-off-by: Zachery Aaron Shores-Chmielewski <zacheryasc@gmail.com>
2026-02-13 07:11:24 +00:00
|
|
|
proptest = "1"
|
|
|
|
|
proptest-state-machine = "0.3"
|
2026-06-23 07:12:45 +00:00
|
|
|
|