Crabrix blog
Crabrix SDK: share a Rust Playground from JavaScript, Rust and Go
Integrate temporary Rust workspaces into agents with the crabrix npm library, Rust and Go bindings, exact revisions and permission-gated local Run/Debug.
· 10 min read
Crabrix blog
Integrate temporary Rust workspaces into agents with the crabrix npm library, Rust and Go bindings, exact revisions and permission-gated local Run/Debug.
· 10 min read
The JavaScript implementation supplies the shared protocol core. The Rust and Go libraries embed that same local bridge and communicate with it over bounded stdio. All three require Node.js 22 or newer. This is an intentional implementation boundary: the Rust and Go packages provide language-appropriate APIs and process ownership, rather than pretending to offer separately implemented cryptographic stacks or native on-host Rust compilation.
The bindings do not need a global npm installation because the bridge is included with them. Their local process handles room encryption, collaborative document updates, selections and signed runtime messages. It does not expose a shell tool or an API for reading arbitrary host files. A language binding can therefore share the same edit and permission rules without inventing its own interpretation of a room capability.
For maintainers, a common core also makes evidence easier to compare. The embedded bridge bytes can be checked against the release manifest, and the same browser can participate in a room opened by any binding. That does not eliminate bugs in process management or language APIs, so those transports still need their own tests. In this release, the public browser and JavaScript, Rust and Go clients were checked together rather than relying only on disconnected unit tests.

Sources: MCP stdio transport
Install crabrix when you want to call a library from your own program. ESM, CommonJS and TypeScript declarations are included. The npm release is bundled without runtime npm dependencies or installation hooks. That describes the SDK distribution; it does not mean live collaboration works without a network connection, and it does not include an AI model subscription, provider credential or browser compiler download.
Create one client per room and give it a useful participant name. The name is visible to collaborators and is a label, not identity verification. A structured source snapshot contains validated text and a revision; status exposes file paths, byte counts, expiry, participants and selections without returning a secret link. Requesting a share link is a separate, explicit operation, which keeps access out of routine status polling.
The following example makes a small source change and obtains an intended handoff. The surrounding application must decide where to deliver the secret link. It deliberately does not log it. Closing the client leaves other participants and the room available until their existing deadline; if the creator wants to close the room for everyone, it must invoke the separate end-room operation before disconnecting.
import { Crabrix } from "crabrix";
const agent = new Crabrix({ name: "Review agent" });
try {
await agent.create({
name: "Small Rust example",
lifetimeMinutes: 60,
files: { "main.rs": 'fn main() { println!("hello"); }
' },
});
const file = await agent.read("main.rs");
await agent.apply({
expectedRevision: file.revision,
changes: [{
path: file.path,
text: file.text.replace("hello", "hello from an agent"),
}],
});
const handoff = await agent.share("edit");
// Deliver handoff.link only to an intended participant.
// Display handoff.expiresAt next to your explicit share action.
} finally {
agent.close();
}Sources: Crabrix npm package · Public SDK source
The Rust binding exposes a client that owns its local bridge process. Its typed options cover room creation, file changes, selections and handoff results. Source fields and capability links are not placed in process arguments. Normal debug formatting of a handoff redacts its link, although an application can still expose the field deliberately when the user requests sharing. Callers should keep that distinction in their own logging and telemetry.
The Rust library is published as crabrix version 0.3.0 on crates.io. Add it to a project with cargo add crabrix@0.3.0, or install the optional MCP executable with cargo install crabrix --version 0.3.0 --locked. The registry archive checksum matches the prepared release, and a fresh registry installation reports the expected version. Node.js 22 or newer remains a prerequisite because the crate embeds the common JavaScript protocol core.
The code below shows the library’s shape. A successful start of the bridge only establishes a local protocol connection. Creating a room performs the separate encrypted sharing operation. For an existing room, use its authorized complete link instead. Dropping the client releases its own bridge; ending a room for all participants is an explicit creator action. Do not silently reconstruct a client and replay a possibly committed edit after a timeout.
use crabrix::{ApplyOptions, Change, Client, CreateOptions};
fn main() -> Result<(), Box<dyn std::error::Error>> {
let mut client = Client::new()?;
client.create(&CreateOptions::new("Rust agent example"))?;
let file = client.read("main.rs")?;
client.apply(&ApplyOptions {
expected_revision: file.revision,
changes: vec![Change {
path: file.path,
text: Some(file.text + "// reviewed in Rust
"),
}],
entry_file: None,
name: None,
})?;
let handoff = client.share("edit")?;
assert_eq!(handoff.mode, "edit");
Ok(())
}Sources: Crabrix Rust package on crates.io · Cargo publishing process · Crabrix Rust API documentation
The Go module provides corresponding creation, source, edit, selection and runtime methods. Use a context that represents the integration’s lifetime, then close the client when the room interaction is finished. A canceled request should not become an excuse for blindly repeating a write. The transport reports cancellation and ambiguous outcomes so the caller can reconcile the actual room state before deciding what to do next.
The source module lives under the public SDK repository’s Go path. A tagged module version identifies immutable source for Go tooling; it is not a separate centrally reserved package name. The installed executable can be named crabrix, while imports use the complete module path. Node.js 22 or newer is still required because this binding embeds the shared JavaScript bridge rather than a different room implementation.
When integrating into a long-running agent, distinguish its normal request context from a process-wide shutdown. Avoid passing a context that is already canceled, and give each operation a bounded lifetime. The SDK caps transport frames and queues; your application should also avoid creating a new room for every token or launching an unbounded number of clients. One deliberate shared workspace is usually more useful than many anonymous temporary connections.
package main
import (
"context"
"github.com/sergii-ziborov/crabrix-sdk/go/crabrix"
)
func main() {
ctx := context.Background()
client, err := crabrix.New(ctx, crabrix.Options{})
if err != nil { panic(err) }
defer client.Close()
_, err = client.Create(ctx, crabrix.CreateOptions{Name: "Go agent example"})
if err != nil { panic(err) }
file, err := client.Read(ctx, "main.rs")
if err != nil { panic(err) }
updated := file.Text + "// reviewed in Go
"
_, err = client.Apply(ctx, crabrix.ApplyOptions{
ExpectedRevision: file.Revision,
Changes: []crabrix.Change{{Path: file.Path, Text: &updated}},
})
if err != nil { panic(err) }
}Sources: Go SDK source · Publishing Go modules
A handoff includes a link, its access mode, expiry and current revision. That is enough for another authorized agent to join the same work surface without an application-specific account. It is also enough to grant the link’s permitted source access, so keep it out of public issues, generated code comments and routine diagnostics. Passing a link between agents is an explicit action, not an incidental side effect of asking for status.
The creator retains a separate view capability and can request a view handoff. A participant that merely joined with an edit link does not possess that separate capability, so it cannot manufacture a weaker link by changing a display field. Similarly, a view participant cannot escalate to editing. These details matter when one agent is allowed to review but another is expected to make the requested change.
A useful handoff message describes the task, the last inspected revision, the deadline and what was actually verified. The link itself can travel through the recipient’s authorized private channel. Avoid implying that a revision is permanent repository history: another participant may edit the room immediately afterward. The receiving agent should read current status and relevant source before proposing its own change.
Explore in Crabrix: Shared interview workflow · Sharing guide
The source revision is a content identity, while the relay’s sequence identifies the update order. A conditional edit checks its expected base before committing encrypted change data. This protects against replacing a human’s or another agent’s intervening work. It does not mean concurrent participants are unable to edit; it means an agent’s proposed replacement must be reconsidered when its basis is no longer current.
Read the relevant files, build one bounded proposal and apply it with the returned revision. When a conflict occurs, inspect the newer source. Sometimes the correct response is to merge the requested change; sometimes another participant has already made it unnecessary. Do not create a loop that fetches a new revision and resends the exact old replacement unchanged. That would turn a useful guard into a decorative extra request.
A lost HTTP acknowledgement is different from a known rejection. The shared core uses a stable message identifier and ciphertext for a safe retry of the same conditional commit. If the final outcome remains uncertain, it asks the caller to read state before deciding on a new action. The language transports likewise avoid claiming success from a disconnected response stream. This is a practical reliability contract, not a promise that networks never fail.

Explore in Crabrix: Explicit state machines in Rust
Room source is capped at 16 supported text files, 64 KiB per file and 128 KiB in total. Package archives, images, compiler caches, credentials and private configuration are outside the shared document. Keep larger project machinery in its original environment and extract a small reproducible source example when that is what collaborators need. A small workspace with an honest boundary is easier to inspect than a partially imported project presented as complete.
The default room lifetime is one hour, with a maximum of 24 hours. The relay holds bounded ciphertext in process memory, without a permanent account project, database source record or backup. A restart can end a room before its advertised expiry. Your integration should display the deadline and offer a clear path to an ordinary local source copy. Rejoining is not a keepalive mechanism for extending the original lifetime.
Close clients and unused tabs when they are no longer participants. Keep creator-only room closure separate from a single participant leaving. If a user presses Stop, do not quietly choose another runtime and start the same program again. Cancellation and loss of permission are meaningful state changes. An agent that explains them clearly is more dependable than one that hides them behind an unlimited retry policy.
Explore in Crabrix: Project recovery and export · Typed data boundaries
Use a pinned package version in a reproducible MCP configuration, and use normal semantic versioning when updating the SDK in an application. The public repository contains the JavaScript source, Rust and Go bindings, license notices and qualification records. The brand images and real app screenshots make the project recognizable, but they are not evidence that a specific code path ran. Look for the actual test and release results.
The release was checked with an official MCP client, an actual browser compiler and a four-participant room containing JavaScript, Rust, Go and the browser. Source edits, Unicode, named selections and stale-revision rejection were observed. Build, Run, structured Debug locals, stepping and Stop were checked separately in the browser. The language bindings also have their own transport tests. These checks describe those exact profiles; they do not claim that every arbitrary Rust repository can run in the web Playground.
For durable work, take the reviewed source back to your own repository and normal review process. Crabrix provides a small shared place to explain, edit, test and hand off that source. It does not replace Git hosting, a production runtime or an organization’s access system. Keeping that purpose clear makes the SDK useful to ordinary agents as well as people using the Crabrix app, and leaves a straightforward path for improving it through public, testable releases.
Sources: SDK source and qualification records · npm release
Explore in Crabrix: All Rust courses · Full Crabrix guide