# How Remote Hosts Sync Their Sessions to a Central agentsview Instance

> Learn how remote hosts sync sessions to a central agentsview instance via authenticated HTTP pull. Discover session ID namespacing and shared database writes for seamless synchronization.

- Repository: [Kenn Software/agentsview](https://github.com/kenn-io/agentsview)
- Tags: how-to-guide
- Published: 2026-07-04

---

**Remote hosts synchronize sessions to a central agentsview instance through an authenticated HTTP pull mechanism where the central daemon POSTs to remote endpoints, triggering local sync engines that namespace session IDs with host-specific prefixes before writing to a shared database.**

The kenn-io/agentsview repository implements a distributed synchronization architecture that allows a central agentsview deployment to aggregate session data from multiple remote agentsview instances. This design uses token-authenticated HTTP requests and configurable ID prefixing to ensure secure, collision-free data aggregation across your infrastructure.

## Configuring Remote Hosts in the Central Instance

Before initiating synchronization, the central instance must define which remote hosts to pull from. Remote hosts are configured via the `RemoteHost` struct in [`internal/config/config.go`](https://github.com/kenn-io/agentsview/blob/main/internal/config/config.go).

Each entry specifies the daemon address, authentication token, and transport protocol:

```go
type RemoteHost struct {
    Host      string // e.g., "devbox:8080"
    URL       string // http://devbox:8080 (daemon address)
    Token     string // secret shared with the central instance
    Transport string // "http" (currently the only supported transport)
}

```

Remote hosts are typically defined in the user-supplied configuration file (TOML or YAML). The central instance validates these entries via `config.RemoteHost.Validate` before attempting to connect. This configuration decouples the central orchestrator from the remote filesystems, ensuring all communication occurs over HTTP.

## Initiating Remote Sync from the Central Instance

When an operator runs `agentsview sync --remote` on the central host, the CLI driver in [`cmd/agentsview/sync.go`](https://github.com/kenn-io/agentsview/blob/main/cmd/agentsview/sync.go) iterates over the configured `remoteHosts` and initiates a pull for each target.

The core function `runRemoteSyncOnce` constructs a JSON payload and POSTs it to the remote daemon's endpoint:

```go
type remoteSyncRequest struct {
    Token         string `json:"token"`   // authentication token
    Full          bool   `json:"full"`    // force a full remote resync
    IncludeLocal  bool   `json:"include_local"` // also pull local sessions (rare)
}

```

The request targets `http://<host>/api/v1/sync/remotes`. If the remote daemon returns an error, the CLI wraps it as a `remotesync.StatusError` but continues processing remaining hosts. This ensures that one unavailable remote does not block synchronization from other hosts in the fleet.

## Handling Sync Requests on Remote Hosts

The remote daemon registers the synchronization endpoint in [`internal/server/server.go`](https://github.com/kenn-io/agentsview/blob/main/internal/server/server.go). When the central instance POSTs to `/api/v1/sync/remotes`, the remote handler performs three critical operations:

1. **Token validation**: The handler compares `req.Token` against the daemon's configured `cfg.RemoteAuthToken`. A mismatch returns HTTP 401 Unauthorized.
2. **Engine initialization**: A new sync engine is created with an `IDPrefix` derived from the machine name:

```go
engine := sync.NewEngine(db, sync.EngineConfig{
    IDPrefix: fmt.Sprintf("%s~", cfg.Machine), // e.g., "devbox~"
    PathRewriter: func(p string) string {
        // Transform local paths like /tmp/foo into "devbox:/tmp/foo"
        return fmt.Sprintf("%s:%s", cfg.Machine, p)
    },
    // additional configuration omitted
})

```

3. **Synchronization execution**: The handler calls `engine.SyncAll(req.Full)` to process the remote host's local session files.

As implemented in [`internal/sync/engine.go`](https://github.com/kenn-io/agentsview/blob/main/internal/sync/engine.go), the `IDPrefix` field ensures all generated session IDs are automatically prefixed via `applyIDPrefixToID`. This prevents collisions when the same session ID exists on multiple hosts. The `PathRewriter` function similarly namespaces temporary file paths, preserving attribution when aggregating data from diverse filesystems.

## Database Persistence and Central Aggregation

After the remote engine completes its local synchronization, the remote daemon pushes the newly imported sessions to the central database if PostgreSQL is configured. This occurs via `backend.PGPush` in [`internal/postgres/push.go`](https://github.com/kenn-io/agentsview/blob/main/internal/postgres/push.go).

The push logic respects the same ID-prefixing rules established during the sync phase. When the central PostgreSQL instance receives the data, sessions from different hosts remain distinct due to their prefixed identifiers (e.g., `devbox~session123` versus `webserver~session123`). This allows the central agentsview UI to display and query aggregated sessions without ambiguity.

The end-to-end flow ensures that remote hosts never directly access the central database; instead, they expose a controlled HTTP endpoint, and the central instance orchestrates the data collection while the remote handles its own local persistence and upstream push.

## Summary

- Remote hosts are defined in [`internal/config/config.go`](https://github.com/kenn-io/agentsview/blob/main/internal/config/config.go) with URL, token, and transport settings
- The central CLI uses `runRemoteSyncOnce` in [`cmd/agentsview/sync.go`](https://github.com/kenn-io/agentsview/blob/main/cmd/agentsview/sync.go) to POST `remoteSyncRequest` payloads to each remote
- The endpoint `/api/v1/sync/remotes` is registered in [`internal/server/server.go`](https://github.com/kenn-io/agentsview/blob/main/internal/server/server.go) and validates tokens before executing sync
- Remote sync engines use `IDPrefix` and `PathRewriter` from [`internal/sync/engine.go`](https://github.com/kenn-io/agentsview/blob/main/internal/sync/engine.go) to namespace session IDs and paths
- Remote hosts push prefixed data to PostgreSQL via [`internal/postgres/push.go`](https://github.com/kenn-io/agentsview/blob/main/internal/postgres/push.go), enabling collision-free central aggregation

## Frequently Asked Questions

### How does authentication work between the central and remote agentsview instances?

The central instance includes a secret token in the JSON payload of each POST request to `/api/v1/sync/remotes`. The remote daemon validates this token against its local `cfg.RemoteAuthToken` configuration. If the tokens do not match, the remote returns HTTP 401 Unauthorized and the sync attempt fails for that specific host.

### How does agentsview prevent session ID collisions when aggregating from multiple remote hosts?

The `EngineConfig.IDPrefix` field in [`internal/sync/engine.go`](https://github.com/kenn-io/agentsview/blob/main/internal/sync/engine.go) automatically prepends a host-specific string (e.g., `"devbox~"`) to every session ID generated during the remote sync. This occurs in the `applyIDPrefixToID` helper function, ensuring that `session123` from one host becomes `devbox~session123` in the central database, eliminating collisions across the fleet.

### Can remote hosts push data to the central instance instead of the central instance pulling?

Currently, agentsview implements a pull-only architecture. The central instance must initiate the HTTP request to the remote daemon's `/api/v1/sync/remotes` endpoint. The remote daemon does not establish outbound connections to the central instance; it only responds to incoming synchronization requests and optionally pushes to a shared PostgreSQL database that both instances can access.

### What transport protocols are supported for remote synchronization?

As defined in the `RemoteHost` struct in [`internal/config/config.go`](https://github.com/kenn-io/agentsview/blob/main/internal/config/config.go), only HTTP is currently supported. The `Transport` field accepts `"http"` as its value, and all communication between the central CLI and remote daemons occurs over HTTP POST requests with JSON payloads.