{% include "_tabler_sprite.html" %} {# Active-session row macros — reused by both the live list and the Recent group so a browser/detached row renders identically wherever it appears (live vs ended). The `filtered` flag gates the live-session-filter `x-show`: the Active zone passes the default (filtered=True) so the chips hide non-matching live rows, while the Recent zone passes filtered=False so ended rows always show — the filter is about live sessions, not ended ones, and recentCount() is filter-unaware (#421). #} {% macro hosted_row(filtered=True) %}
browser {# Unconditional, unlike a bridge row's `claude.ai` badge (x-show on bridge_session_id): a hosted session is local-only for its whole life, not a yet-to-register bridge. Don't gate this on state. #} local live-view only orphan {# `:disabled` is coerced with `!!` on every busy-state binding below. These buttons live in an x-for clone and the busy maps (hostedStopping/hostedResuming/ agentStopping) start without the row's key. Alpine 3.15.x renders a bare `:disabled="map[key]"` as DISABLED when that key is absent (an explicit false renders enabled) — so the Stop/Kill/Resume button is stuck un-clickable until the key exists. `!!` yields a concrete false for a missing key, which renders enabled. The sibling `x-text` ternaries are unaffected (undefined → 'Stop'). #} {# Forget only for an ended, non-orphan hosted session (an orphan is a live survivor — Kill it first). `!!` coercion: see the detached-row note. #}
{% endmacro %} {% macro detached_row(filtered=True) %}
detached claude.ai {# Liveness-aware action. A live worker is "Stop" (destructive red): the DELETE double-SIGINTs it for an orderly cloud-deregistering shutdown. An ENDED session has no live worker, so the deregistering SIGINT can't run — the DELETE only `claude rm`s the local record. So it reads "Forget" (neutral, not red, not "Deregister" — nothing is deregistered when the worker is gone); for an ended claude.ai session the title flags the possible cloud orphan. `!!` coercion: see the hosted-row note above — without it the button is stuck DISABLED on first paint (Alpine 3.15.x x-for missing-key `:disabled`). #} {# Resume an ENDED agent with a session UUID: `--bg --resume` continues the prior conversation in a new job (#336). `!!` coercion on :disabled — same Alpine 3.15.x x-for missing-key guard as the sibling buttons. #}
{% endmacro %} {# External (unmanaged) session row — a `claude` session in a project dir that Clauster didn't start. Observe-only: no controls, since Clauster doesn't own its lifecycle. #} {% macro external_row() %}
external unmanaged
{% endmacro %}
Lost connection to the server — data may be stale. Retrying…

Before you start a session

Active sessions

what Claude is running for you right now
No sessions match this filter.
{% if claustrum_enabled %} {% endif %}
Nothing running yet — launch one from a project below.
{% if claustrum_enabled %} {% endif %}

Projects

a folder Claude works in — launch a session from any of them

https / ssh only · private/LAN hosts blocked unless enabled in config · cloned code runs only when you launch a session.

ships — its code runs when you launch a session here. Review it before starting.
{% if projects %}
{% for p in projects %} {% set idx = loop.index0 %} {% include "_project_row.html" %} {% endfor %}
{% else %}

No projects yet

Clauster runs Claude in a project directory under {{ projects_root }}. Create one or clone a git repo to get started — or drop a directory there and it appears here.

{% endif %}
{% if reaper_ui_enabled %}

Reap ghost environments

Server-side session environments with no live session clutter the claude.ai/code "New session" selector. The cloud Default and any environment backing a live session are never reaped.

Scanning…

{% endif %}
{% include "_dashboard_script.html" %}