Private Accounts and Service Publishing

Sign in at deek.loca.zone with your own Authelia account. A provisioned account reaches its own Deek process, sessions, workspace, settings, and plugin selection. An account without an instance receives 403: no instance provisioned instead of somebody else’s workspace.

For operator-only user provisioning, see the existing private operations runbook: Operate or disable one account (sign-in required). It documents the separate deek-user add USER --index N --subscriptions own path and its root/Authelia prerequisites; this page does not authorize a provisioning command or change the already shared pxl/otto accounts.

Private data and shared subscriptions

Accounts do not receive copies of other owners’ conversations, files, browser-cookie secrets, or provider grants. Use a separate browser profile or normal Authelia logout/login to switch identity; a stale Harness cookie is not another user’s authority.

Published owner deployment history records explicitly authorized shared ChatGPT/Codex, Claude, and xAI subscription access for pxl and otto, with provider-terms and shared-quota risks accepted for that earlier scope. This is not a new provider permission or an expansion of approved onboarding. Shared Models access does not share conversations, workspaces, or delegated command-line credentials. Choose Configure later rather than adding a paid API key. Subscription Provider Sign-in owns the release-qualified visible catalog, restrictive onboarding policy, no-extra-login guidance, custody, and historical recovery references.

Features depend on the selected owner’s release. The expanded sharing tool schema is available from rc.2-r9. The corrected theme/sidebar and keyboard-accessible session list are available from rc.2-r11; see Releases.

Publish an app

  1. Start your own server bound to 127.0.0.1, using your assigned port block and an allowed app name.
  2. Ask the agent to call the native deploy_service tool, not to write nginx configuration or invoke sudo. A minimal request is {"name":"my-app","port":47150,"action":"deploy"}; the port is an example, not permission to use another owner’s allocation.
  3. Read the broker result and keep its request UUID. PENDING after the tool’s 90-second wait means queued, not published or refused; inspect status before repeating.
  4. Open the returned owner-visit URL through normal sign-in. PUBLISHED_NEEDS_OWNER_VISIT does not mean an owner visit has succeeded. Inspect status afterwards.

The URL is https://<owner>.deek.loca.zone/<app>/, for example:

AppOwner URL
Theme Parkhttps://loca.deek.loca.zone/theme-park/
Neon Arcadehttps://loca.deek.loca.zone/neon-arcade/
Batch Studiohttps://pxl.deek.loca.zone/batch-studio/

These examples identify routes, not public-access or working-backend guarantees. Visibility and app health still apply. An owner-app origin is not the Deek chat UI.

Build browser asset URLs for /<app>/. The fixed sanitizing proxy strips exactly one app prefix before forwarding: the upstream serves / and /assets/..., while browser URLs retain /<app>/. Publishing updates the route map; it does not create a per-app nginx location or reload nginx.

Durable snapshot deployments

The broker deek-nginx-location-deploy supports operator-approved pinned apps. For a managed app, deploy refreshes an immutable snapshot under /opt/deek/apps/releases/ and runs it in its deek-app@ service, separate from the Deek conversation’s tool scope. Source selection is allowlisted: the owner’s workspace and /var/lib/deek/apps/<name> are supported, with the private-state alias deduplicated. An arbitrary filesystem path is not accepted.

The operator approves the exact snapshot limits and managed-app grants. The limits require a maximum release size no greater than 1 GiB, a root free-space reserve of at least 1.5 GiB, at least two retained releases, and mandatory secret exclusions. A deploy request cannot waive those checks. The agent-facing schema does not expose the broker’s operator pin/handover flags.

Before commit, the broker checks HTML and referenced assets twice: first through a candidate proxy socket before the route write, then through the real proxy socket before committing. Asset bytes and MIME types must match the snapshot. REFUSED_PREFIX_ASSET_BROKEN means fix the app’s source/base handling, not the proxy.

Pruning removes only classified old snapshots of the same owner/app after commit; live managed references and the actual previous rollback release are protected. Unclassified legacy/shared directories are retained. Remove also handles an orphan route whose owner entry is absent, while checking its port. Removing a broker-managed app unpublishes it and stops its app unit but retains its snapshot; it is not a private-data deletion.

Agent listener durability limitation

As shipped through rc.2-r14, an agent-published listener (deploy_service) runs inside the owner’s Deek process and is not pin-durable: it dies with the owner restart. Publishing a route is not a transfer to a durable service. The broker refuses to pin a layout that serves assets only under /<name>/ with REFUSED_PREFIX_ASSET_BROKEN. To be pinnable, the upstream must serve / and /assets at its root; browser-facing URLs still retain the app prefix. Correct the app’s source/base handling, not the proxy, and obtain separate operator approval for a managed pin.

The D-541 proof app has been retired after the listener-lifetime and prefix/asset pin refusals (D-541p-e; backend follow-up D-590). Its earlier successful share render is historical proof, not a currently available demo or durable deployment.

Sharing and the owner page

Open https://<owner>.deek.loca.zone/_apps/ while signed in as that owner to inspect apps, change access, switch off/on, and copy or replace a share link. This owner page is independent of whether an older Deek release exposes the expanded agent schema.

SettingAccess
privateOwner-only; anonymous visitors are sent to sign-in. New apps default private.
linkA valid app-scoped share token permits access. Treat the link as a bearer permission.
grantedThe owner and explicitly named, exact Authelia usernames; not groups.
publicAnyone can open the enabled app.
Off (enabled:false)Hidden from everyone, including the owner; the selected visibility is retained for re-enabling.

The link format is https://<owner>.deek.loca.zone/<name>/?share=<43-character-url-safe-token>. The proxy strips share before forwarding to the app and establishes an app-scoped HttpOnly, Secure, SameSite=Lax cookie. Tokens are stored as hashes in route data, not plaintext in tool results. Copy the link on the owner page; Replace link / share:"rotate" invalidates previous links and share cookies. Do not confuse a share link with the single-use __deek_visit owner confirmation.

From rc.2-r9, action:"access" changes only an existing app’s access, not its deployment. Optional fields are visibility, granted_users, share:"rotate", and enabled; name, port, and action remain required. See Images and Self-publishing for examples and the exact tool inputs.

Limits and recovery

The broker enforces the requesting owner’s UID/cgroup, granted loopback port, reserved/denied names, and app-count policy. It accepts no shell command, nginx text, arbitrary owner, or arbitrary path. A vhost/policy pin mismatch requires operator review; do not bypass it. NO_LISTENER requires a running server; an ownership refusal requires correcting that server’s UID and Deek service/tool scope.

Accounts keep separate kernel UIDs and private state but share host loopback and an aggregate memory cap; this is not a VM or per-user network namespace. App snapshots do not grant access to Deek credentials or state. A rendered app shell is not proof that a credential-dependent backend works. Account removal retains private data.

See Themes and Sidebar, Configuration and Data, and the private service runbook.