Install
$ agentstack add mcp-ferroxlabs-wayland-core ✓ scanned · ✓ verified, works with Claude Code, Cursor, and more.
Security review
✓ PassedNo issues found. Passed automated security review. · v0.1.0 How review works →
- ✓ Prompt-injection patterns
- ✓ Secret / credential exfiltration
- ✓ Dangerous shell & filesystem operations
- ✓ Untrusted network calls
- ✓ Known-malicious package signatures
What it can access
- ● Network access Used
- ● Filesystem access Used
- ● Shell / process execution Used
- ✓ Environment & secrets No
- ✓ Dynamic code execution No
From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.
Verified badge
Passed review? Show it. Paste this badge into your README, it links to the public security report.
Reliability & compatibility
Declared compatibility
Compatibility is declared by the source manifest. End-to-end runtime verification is coming, see below.
We're building live execution health for every listing: tool-call success rate, median latency, uptime, and last-checked timestamps, measured, not self-reported. It isn't live yet, so we don't show numbers we can't stand behind.
How agent discovery & health will work →About
Wayland Core
The self-evolving AI agent. Brilliant today, smarter tomorrow.
Most AI tools are as good as they'll ever be the day you install them. Wayland Core isn't — it convenes a council of rival models on your hardest problems, fuses their best answer into one, and rewrites its own prompts to get sharper every single run. Terminal-first, on your keys, in Rust.
Terminal-first · Multi-provider · Self-evolving · MCP-native · Embeddable · Apache-2.0
[](https://www.npmjs.com/package/@ferroxlabs/wayland-core) [](https://github.com/FerroxLabs/wayland-core/actions/workflows/ci.yml) [](LICENSE) [](https://www.rust-lang.org/) [](#install) [](#built-to-endure)
[Install](#install) · [Quick start](#quick-start) · [Providers](#provider-neutral-core) · [Orchestration](#orchestration--swarms) · [Crucible](#crucible--a-mixture-of-providers-council) · [Security](#security-by-default-fail-closed) · [Channels](#omni-channel-deployment--scheduled-triggers) · [Browser](#browser--computer-use) · [Memory](#memory-sessions--cost-governance) · [Evolution](#self-evolution-gepa) · [Endurance](#built-to-endure) · [Embedding](#embedding-json-lines-protocol--acp-interop) · [Docs](#documentation)
Most agents are frozen the day you install them, and married to one model. Wayland Core is neither. Hand it a hard problem and it convenes a council of rival models that cross-audit into one answer ([Crucible](#crucible--a-mixture-of-providers-council)). It rewrites and scores its own prompts between runs ([GEPA](#self-evolution-gepa)). Every tool runs in an OS-native sandbox behind a single egress gate, and it speaks MCP in both directions — all from one Rust binary, on your keys. It's the engine inside Wayland Desktop, but it stands alone: a one-shot command, a full-screen TUI, or a headless stream you embed.
> Wayland Core is the engine, on its own, open (this repo, Apache-2.0). Wayland Desktop is the GUI product built on it. Core is the engine; Desktop is one application that embeds it.
The 30-second proof
npx @ferroxlabs/wayland-core "read Cargo.toml, list the workspace crates, and explain the dependency layering"
One command. The agent reads the file, runs grep/glob across the tree, reasons, and answers, with every tool call gated and streamed. Or run wayland-core with no arguments and it detects your provider keys and drops you into the TUI:
Paste a key, get a provider. Paste an API key (or run /connect in the TUI) and the engine fingerprints the provider from the key's shape, validates it live, and stores it in your OS keyring. From there, /config exposes Essentials and Advanced editors, /doctor shows provider, key, and MCP health, and /effective prints the resolved config with secrets redacted.
What it is
- A standalone engine. The engine is the product, not a feature bolted onto an editor and not a wrapper around one vendor's API.
- Terminal-first. A one-shot command, an interactive TUI, or a headless stream. The terminal is the primary home, not an afterthought.
- Embeddable. Drive it from your own app over a typed JSON-Lines protocol. It is exactly how Wayland Desktop uses it.
- Apache-2.0. Permissive. Build on it commercially without an AGPL obligation.
Install
npm (recommended, pulls the right prebuilt binary for your platform):
npm install -g @ferroxlabs/wayland-core
wayland-core --version
# or run it once, no install
npx @ferroxlabs/wayland-core "summarize the TODOs in this repo and draft a triage plan"
Prebuilt binaries for macOS (arm64/x64), Linux (arm64/x64), and Windows (arm64/x64) are on the Releases page, each verifiable against wayland-core-checksums.txt.
From source (Rust 1.95+):
cargo install --git https://github.com/FerroxLabs/wayland-core wcore-cli
Quick start
# 1. Generate a config, then add an API key for any provider
wayland-core --init-config
wayland-core --config-path # shows where the config lives
# 2. One-shot: the agent reads files and uses tools to answer
wayland-core "Read Cargo.toml and explain the dependencies"
# 3. Interactive TUI (just run it)
wayland-core
# 4. Everything else
wayland-core --help
Provider-neutral core
The engine never knows which vendor it's talking to. It builds one neutral request type, LlmRequest, and reads one neutral event stream, LlmEvent — TextDelta, ToolUse, ThinkingDelta, Done, Error. That's the whole contract. Every provider adapter implements a single async trait, LlmProvider, whose core method is stream(&LlmRequest) -> Receiver. Wire-format translation happens inside the adapter, where it belongs. The agent loop above it stays vendor-blind.
Vendor quirks don't get hardcoded. There is no if base_url.contains("openai.com") branch anywhere. The differences — field names, message-shape rules, which API surface to hit, reasoning vs. thinking, tool-array caps, temperature support, cache markers — live in one configuration layer, ProviderCompat: 31 Option fields where None means "use the provider's default." 24 preset constructors set those defaults per vendor, and a single map binds each of the 23 built-in providers to its preset. Your config layers on top. Every field resolves as user.or(default), so anything you set wins and anything you leave alone keeps the shipped default. Adapters then read compat instead of sniffing URLs: api_path(), max_tokens_field, uses_responses_api(), supports_temperature, include_usage_in_stream, and the rest.
- 23 built-in providers, one
--providerswitch. The slug picks the wire, the base URL, and the compat preset. - Point any OpenAI-compatible backend at a built-in wire with a custom alias — set
provider,model,api_key,base_url, and you're done. No code. - Override a quirk in config, not in a fork. A self-hosted server that rejects
stream_options?include_usage_in_stream = false. - Data-driven pricing. A bundled
pricing.toml— 46 model rows across 25 provider tables — computes per-token cost in integer microcents from per-Mtok USD rates. Swap the whole catalog withWAYLAND_PRICING_PATH. - Resilience is built in. Transient failures retry automatically, with multi-key rotation on supported providers; opt into a circuit breaker plus same-provider model fallback with one
[provider_chain]block.
# Point a custom backend at the OpenAI wire, then bend one quirk
[providers.my-service]
provider = "openai"
model = "custom-model-v1"
base_url = "https://my-service.example.com/api/openai"
[providers.my-service.compat]
include_usage_in_stream = false # self-hosted server rejects stream_options
Orchestration & swarms
A single agent is the floor, not the ceiling. Wayland Core fans one task out across many workers and brings the results back, with real isolation between them. Three distinct mechanisms ship in the code, and a four-tier topology model governs all of them: Spawn (5 agents), Swarm (20), Mesh (50), Fleet (100). Each tier fixes the agent cap, how much the parent sees, and the blackboard scope — and the caps are enforced, not advisory. Ask for 51 agents on a 50-cap tier and you get TopologyError::ExceedsCap, not a quietly-truncated run.
- Sub-agents (
Spawn) fan parallel work out from one tool call. Each sub-agent gets its own conversation context and its own tool access; the count is capped by the active topology (default Spawn, 5). - Worktree swarm runs N workers as OS subprocesses, each in a fresh
git worktreeon its own branch. A dirty-checkout guard runsgit status --porcelainfirst and refuses to dispatch on an uncommitted tree — that guard exists because a contamination incident in v0.2.2 taught us why it has to. Per-worker timeouts,kill_on_dropSIGKILL on expiry, and idempotentgit worktree remove --forcecleanup. Process isolation, not threads, so one bad worker can't corrupt another. - In-process dispatchers (
MeshDispatcher,FleetDispatcher) are library primitives: they coordinate caller-supplied agent closures over a shared blackboard, enforce the tier cap, apply a timeout, and reduce the reports. Fleet partitions agents into shards (default 10) under topic prefixes likefleet//shard-/. They coordinate and reduce; spawning the agents is the orchestrator's job.
Every worker spawn goes through argv mode — Command::new(program).args(args), no shell interpreter — so worker commands are never re-parsed by a shell. Final stdout/stderr come back through collect(); opt-in heartbeats (.swarm-status.json, ~5s tick) give you liveness without consuming the result.
Roll the results up however the job needs. The wayland-core swarm CLI dispatches the worktree path and routes the collected results through one of four reducers:
# Run the test suite across 4 isolated worktrees, roll up pass/fail/total
wayland-core swarm --workers 4 --worker-command "cargo test" \
--base-branch main --branch-prefix swarm/ci --timeout 30m --reduce fleet
# Strict >50% majority over normalized worker stdout
wayland-core swarm --workers 5 --worker-command "pytest" --reduce consensus
mesh— verbatim passthrough of every worker result.fleet— succeeded / failed / total roll-up.consensus— strict majority: a bucket wins only if its votes are more than half of the successful workers, otherwise the top three are returned as disputed.debate— first round whose workers agree wins; at the CLI the batch is a single round (multi-round replay lives in the orchestrator, not the CLI path).
Topology is pure data with cap enforcement, the guards have tests behind them (58 across the swarm crate), and the live TUI labels the running tier by sub-agent count — 0-5 Spawn, 6-20 Swarm, 21-50 Mesh, 51+ Fleet. One note on reach: the standard monitored relay clamps Spawn fan-out to the Mesh cap of 50, so the 100-agent Fleet ceiling is the unmonitored library path, not the everyday Spawn call.
Crucible — a Mixture-of-Providers council
Crucible is a council of rival providers. Hand it a hard task and it fans out to N sub-agents, each pinned to its own LLM provider — Anthropic, OpenAI, DeepSeek, GLM, Kimi, Gemini, Flux-routed models — that answer in parallel; a separate, read-only judge then fuses them into one. The diversity is the whole point: cross-vendor, not one family arguing with itself. We call it Mixture-of-Providers.
Convening a council live in the TUI: two proposers pinned to different vendors, an independent judge from a third, the certified ceiling ($0.70) beside the single-model cost ($0.49), the daily envelope, and the gate's reasoning — all on the table before you approve a cent.
…and the fused output: a three-vendor council ranking the audit by severity — every proposal, provider, and cost on the table. Head-to-head benchmarks (Crucible vs. router-level mixtures vs. solo frontier models, cost-matched) are in flight.
It's off by default. List a roster in a [crucible] block:
[crucible]
enabled = true
proposers = ["anthropic:claude-opus-4-7", "openai:gpt-5", "deepseek:deepseek-v4-pro"]
aggregator = "anthropic:claude-opus-4-7" # optional; falls back to the first usable proposal
Then run it: wayland-core crucible "do a security audit of this deployment plan".
Each member pulls its own credentials from your [providers] map, so a council is genuinely keyed across vendors, not one key wearing hats. Routing prefixes don't defeat that — a Flux-pinned GPT-5 and a direct openai:gpt-5 collapse to the same vendor family, so the judge stays independent and an Auto roster stays diverse.
Then the cost discipline, because N models answering one question costs N times as much:
- A deterministic preflight gate decides whether to convene at all. A zero-LLM keyword/length classifier reads the leading instruction span and sizes the roster by stakes — low goes Direct (one call), medium pulls 3 members, high pulls 5. A high-stakes word buried in a pasted stack trace won't escalate it.
- Two roster modes. Manual: you list the providers. Auto: a deterministic Assembler picks a cost-effective, vendor-diverse roster per task, and you can
--denya vendor or force--deep. - Spend is gated before anything spawns. A judge-inclusive worst-case ceiling is certified up front. The per-run
max_cost_usdcap is strict — an unpriceable roster under a cap is refused, not run. A default-on $20/user/day envelope rides on top. - It fails closed. In a non-interactive session it refuses to spend unless you've explicitly opted in. On a TTY it prints a cost card and waits for Y/n.
- The judge can't touch your machine. The aggregator is a read-only sub-agent — no
Bash, noWrite, noEdit, by construction. Every proposal reaches it wrapped in untrusted-data fencing with forged section delimiters neutralized, so one poisoned proposer can't hijack the synthesis.
Fan-out is bounded by a per-route semaphore, and tail latency is capped: each proposer gets a hard deadline, and once quorum is met a global soft-deadline cancels the stragglers — timed-out members are kept as errored proposals so the provenance stays honest. The fused answer is either printed (Terminal mode) or injected as private guidance into the normal tool-using loop (Advisor mode, --advisor).
Shipped in v0.12.11. The council pipeline carries 84 unit tests plus 31 integration tests across the gate, resolver, roster validation, budget, fan-out, and injection-fencing paths.
Where it's honest about its edges. Some Flux-routed SKUs are unpriced today, so a Flux council can't always certify a hard ceiling — that's exactly why the per-run cap is opt-in and the daily envelope only soft-binds on Flux, accruing from actual usage instead of refusing up front. The daily envelope binds within a process, not yet across separate CLI runs. The convene-or-not gate is a deterministic heuristic, not a learned router. And the shipped invocation surface is the wayland-core crucible batch command; the slash command, natural-language tool, and full TUI/desktop approval cards are designed, not all shipped.
Security by default (fail-closed)
Security here is a posture, not a checkbox. When the safe thing and the convenient thing disagree, the engine picks safe and makes you opt out on purpose. Four mechanisms carry that, and they hold up when someone reads the source.
- No unsandboxed default. Model-driven shell and tools run inside an OS-native sandbox — bubblewrap on Linux,
sandbox-execon macOS, AppContainer on Windows, Docker if you opt in. When no real sandbox is available, execution is refused, not quietly downgraded to host permissions. Running with no isolation takes an explicitWAYLAND_ALLOW_NO_SANDBOX=1. A strayWAYLAND_SANDBOX=nonedoes nothing without it. - One egress chokepoint, enforced by a lint. Every outbound HTTP request flows through a single client, and a clippy lint bans constructing a raw
reqwestclient anywhere else — so a missed migration fails the build instead of leaking a hole. On that seam sits a fail-closed host allowlist for untrusted URLs, an exfil-shape classifier that hard-denies suspicious POSTs and high-entropy paths to non-allowlisted hosts, a hard byte-cap body reader, and a resolve-once resolver that re-checks the IP at connect time to close DNS-rebinding races. Deny stops before the socket opens. Shared multi-tenant suffixes —amazonaws.com,*.workers.dev,*.vercel.app, around 45 of them — can never be apex-allowlisted. - SSRF and metadata floor, always on. Cloud-metadata endpoints (
169.254.169.254and the GCP, AWS, Alibaba, and Oracle equivalents) and lookalike hosts are rejected outrigh
…
Source & license
This open-source MCP server is cataloged on AgentStack and links to its original source — we do not rehost the code.
- Author: FerroxLabs
- Source: FerroxLabs/wayland-core
- License: Apache-2.0
Install and usage instructions live in the source repository linked above.
Reviews
No reviews yet, be the first.
Write a review
Versions
- v0.1.0 Imported from the upstream source.