---
title: Events
description: Bidirectional host-guest communication
icon: "tower-broadcast"
---

<Note>
  Events are coming soon and not yet available in the current SDK.
</Note>

The events API is for structured communication between host and guest beyond stdin/stdout. The host can subscribe to named events from the guest and emit events back, all through the same channel used by `exec`.

On the guest side, processes just write JSON to `/run/agent.sock`, which is a standard Unix domain socket. No special library needed. Any language that can open a socket and write a newline-delimited JSON message will work.

## Basic example

<CodeGroup>
```rust Rust
use microsandbox::{Sandbox, EventData};
use serde::Deserialize;

let sb = Sandbox::get("worker").await?.start().await?;

let _sub = sb.on_event("task.progress", |event: EventData| {
    #[derive(Deserialize)]
    struct Progress { percent: u32, message: String }

    if let Some(data) = event.data {
        if let Ok(p) = data.deserialized::<Progress>() {
            println!("[{}%] {}", p.percent, p.message);
        }
    }
});
```

```typescript TypeScript
import { Sandbox, EventData } from 'microsandbox'

const sb = await Sandbox.get("worker")

const sub = sb.onEvent("task.progress", (event: EventData) => {
    const { percent, message } = event.data as { percent: number; message: string }
    console.log(`[${percent}%] ${message}`)
})
```

```python Python
from microsandbox import Sandbox

sb = await (await Sandbox.get("worker")).start()

sub = sb.on_event("task.progress", lambda event: (
    print(f"[{event.data['percent']}%] {event.data['message']}")
))
```

```go Go
// Bidirectional events are not available in the current SDKs yet.
```

</CodeGroup>

## Send events to guest

Emit a named event with typed data into the guest. Any process listening on the agent socket receives it.

<CodeGroup>
```rust Rust
use microsandbox::Sandbox;
use serde::Serialize;

#[derive(Serialize)]
struct TaskConfig { input_file: String, output_dir: String }

sb.emit("task.start", TaskConfig {
    input_file: "/data/input.txt".into(),
    output_dir: "/data/output".into(),
}).await?;
```

```typescript TypeScript
await sb.emit("task.start", {
    inputFile: "/data/input.txt",
    options: ["--verbose"],
})
```

```python Python
await sb.emit("task.start", {
    "input_file": "/data/input.txt",
    "output_dir": "/data/output",
})
```

```go Go
// Bidirectional events are not available in the current SDKs yet.
```

</CodeGroup>

## Guest-side emitting

Inside the guest, any process can emit events by writing JSON to the Unix domain socket at `/run/agent.sock`. No SDK required.

```python
# Inside the guest, plain Python, no SDK
import json, socket

sock = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
sock.connect("/run/agent.sock")
sock.sendall(json.dumps({
    "event": "task.progress",
    "data": {"percent": 50, "message": "Halfway done"},
}).encode() + b"\n")
sock.close()
```

The host subscription registered with `on_event("task.progress", ...)` receives this message automatically.
