App Runtime

App routing, auth/session, and data access architecture.

This page describes the web application layer: routing, auth/session handling, data access, and where the main product surfaces live in src/app. It is the app-side counterpart to the native runtime docs under Clapilot-Agent — read it when you are looking for a page, an API entry point, or an app-owned behavior rather than model/agent internals.

Clapilot is a Next.js App Router app with local auth/session and a Postgres-backed supabase-compatible adapter (no hosted Supabase; the adapter mimics its client API against the local database).

Routing layout

  • root shell: src/app/layout.tsx
  • installable web app: src/app/manifest.ts publishes /manifest.webmanifest with standalone display mode, root start URL/scope, Clapilot theme/background colors, and dedicated regular/maskable icons. The root metadata links the manifest and declares the matching browser theme color, so a browser-installed Clapilot uses the same Next.js routes and rendering code as the normal web surface.
  • authenticated app shell: src/app/(app)/layout.tsx
  • docs routes: src/app/docs/**
  • proxy/session gates: src/proxy.ts, src/lib/supabase/middleware.ts

Auth and session model

  • session cookie: clapilot_session
  • session validation: src/lib/auth/server.ts
  • login/logout: /api/auth/login, /api/auth/logout
  • admin role guards: src/lib/auth/roles.ts

Protected UI routes redirect to /login. Protected API routes return 401.

Data access layer

  • DB pool: src/lib/db/index.ts
  • local supabase server client: src/lib/local-supabase/server-client.ts
  • query executor and policy checks: src/lib/local-supabase/query-executor.ts
  • route helper: src/lib/supabase/server.ts

Core product routes

Business UI

  • dashboard/clients/tasks/calendar: src/app/(app)/*
  • settings area: /settings/*, /admin/*, and /profil/* live in the shared route group src/app/(app)/(einstellungen)/; its layout.tsx owns the settings sidebar (SettingsSidebar) so navigating between settings pages swaps only the content column client-side — the sidebar stays mounted and keeps its search text, expansion state, and fetched admin/module/build-info data. SettingsPageShell (src/components/settings-top-tabs.tsx) renders only the per-page title/description header inside that layout.
  • the Kalender server page preloads the focused week for authenticated users and resolves every entry color before the client hydrates. The API and browser-installed web app use the same resolveCalendarEntryDisplayColor helper; valid stored hex colors are preserved exactly, while invalid and historical default values retain the documented fallback behavior.
  • the web Kalender now uses anchored side-by-side floating cards for both event creation and event editing, without dimming the rest of the page; its timed grid also supports direct desktop interactions similar to Google Calendar: drag on empty space to prefill and immediately create a new timed event, drag timed events to move them, drag their top/bottom edges to resize duration in place, left-click an existing event to open it directly in edit mode, right-click an existing event for a small edit/delete menu, and right-click empty all-day or timed cells to open a prefilled create popup at the clicked position: src/app/(app)/calendar/page.tsx
  • contacts settings: src/app/(app)/(einstellungen)/settings/contacts exposes import source slots and a VCF upload flow backed by /api/contacts/import/vcf; imported contacts are stored as mandanten so existing client search, call-agent lookup, and agent read tools see them through the established client model
  • documents: src/app/(app)/dokumente
  • proactive AI inbox: src/app/(app)/emails
    • top-header segmented controls instead of the old left sidebar; one folder switcher for Posteingang / Archiv / Gesendet / Papierkorb plus custom IMAP folders and nested Outlook folders when connected; a separate Personal / Assistenz toggle
    • a Smart dropdown for Fristen / Antwort erforderlich / Wichtig / Unbearbeitet, and a single compact list-header row with the Default / Smart segmented switch on the left and the search field with inline magnifier on the right
    • lighter inbox rows with preview text plus compact AI state icons in the meta line, icon-only delete, a three-dot archive/trash menu, checkbox-based multi-select with long-press activation on touch devices, desktop batch action surfaces for read/unread/move/delete, a mobile sticky bulk-action tray, and move targets sourced from the same custom IMAP / nested Outlook folder inventory as the folder switcher
    • persistent case-insensitive sender/keyword filters managed under Profile → E-Mail; matches from Gmail and IMAP are moved into the on-demand Nicht relevante mails label/folder and marked read during recurring inbox synchronization
    • no Focus Mode or reply/priority badges in the list; default-mode day-grouped sections for Heute/Gestern/Diese Woche/Älter, and a smart-mode flat priority list where one message expands inline at a time with the prepared draft and send action inside the row while the original email stays in the full detail view
    • email detail places the prepared answer workflow after the current message plus the immediately previous quoted reply when long plaintext threads are detected, moving older quoted history into a bounded section below the AI suggestion
    • email detail also exposes a direct Reply action that opens a dedicated reply composer, prefilled from the prepared suggestion when available and still available as an empty manual reply when the workflow decided no reply was needed
  • native iOS/macOS client: clients/apple/ClapilotApple — sections for dashboard/chat/team chat/mail/notizen/documents/calendar/tasks/automations/issue reporter/settings with compact native layouts
    • boots into a simple native dashboard with summary cards and a bottom chat handoff composer
    • runs the same proactive AI e-mail reply workflow as the web inbox in the native Mail detail view: opening an inbox message ensures and polls /api/emails/:id/automation; a pale AI reply-decision surface shows the progressive context/analysis/draft stages, the prepared reply draft with subject/recipient/body preview, and a no-reply/failed/sent state; users can send the prepared draft directly via POST /api/drafts/:id/send, switch the reply between sender language and UI language through PATCH /api/drafts/:id regeneration, or open the draft in the native composer bound to the server draft so edits are persisted before sending
    • supports checkbox/long-press multi-select in the native Mail list with a bottom bulk-action tray for read/unread/move/delete and a folder picker backed by /api/emails/folders
    • keeps the native mail list fresh while the app is active (staleness-based live refresh when the Mail section opens or the app returns to foreground, plus periodic polling while the mailbox stays visible; forced pull-to-refresh always performs a live mailbox fetch) and renders native pull-to-refresh on iOS with the branded Clapilot loading indicator in a floating circular surface instead of the system spinner
    • exposes list/kanban switching for Aufgaben and lets users attach images/files to new tasks and task comments in the native task detail flow
    • ships a native day/week calendar board with arrow-based period navigation where tapping an event opens the styleguide-styled edit form directly (title, location, note, all-day flag, start/end, color — the same form as event creation) backed by PATCH /api/calendar/:id, with circular save/delete toolbar icon buttons, a delete confirmation dialog, and a read-only info view instead of the editor for imported iCal entries
    • shows /geplante-aufgaben as a native Automationen & Agenten workspace that mirrors the web tabs with a top-bar segmented control (Automationen | Agenten) instead of a page title, one shared drawer entry for both, compact single-line web-style rows (avatar, title, prompt preview, inline run/pause/delete actions) without per-row status/schedule/skills/tools badges, search with an inline filter menu, create/edit sheets for time-based automations, run-now, pause/resume, delete, and runtime log inspection
    • keeps profile settings as the profile-avatar modal, opens the drawer settings row as a full-screen native settings section, and shows the ClapilotAICore provider/model settings entry only to admins
    • lets admins add/edit/delete OpenAI API, OpenAI-Codex OAuth, Anthropic API, and Anthropic-Claude subscription providers with encrypted backend storage through the shared /api/agent-runtime/config contract, loads provider model catalogs via /api/agent-runtime/provider-models, edits the global provider/model priority list, and starts Codex OAuth from the native provider form by opening the OpenAI authorization URL and accepting the pasted callback URL through /api/admin/openai-codex/oauth/complete
    • the native settings menu now renders real content for every section instead of placeholders, mirroring the web settings against the same HTTP contracts (clients/apple/ClapilotApple/Sources/Clapilot/Views/AppSettings*.swift):
      • Allgemein: quick links into the other native sections, onboarding restart via POST /api/onboarding {action:"restart"}, and an admin-only backup card that exports the settings ZIP from POST /api/admin/backup/export (native file exporter) and imports one via multipart POST /api/admin/backup/import with the literal IMPORTIEREN confirmation
      • App-Verbindungen: read-only connection status tiles for Apple iCloud, Google Workspace, Microsoft 365, reMarkable, and X from the /api/integrations/*/status endpoints plus full admin CRUD for GitHub (/api/app-connections/github) and GitLab (/api/app-connections/gitlab) token integrations; OAuth-based connecting itself stays in the web app and is signposted as such
      • Kalender: full iCal subscription management against /api/calendar/ical/subscriptions (add with name/context/URL/interval, enable/disable, per-subscription and force-all sync, delete with confirmation)
      • Agent-Orchestrator (admin + developer mode): runtime status pill and metric tiles, poll-interval/max-concurrent/task-board form, Codex and Claude runtime model selection, start/stop/trigger-poll, remote-runner list, per-repository automation toggles (PR review, issues, mentions, main-CI fix) with trigger mode and webhook URL copy, and the three automation cards (provider, forge integration, prompt) via the agent-orchestrator module API with a 4s status refresh loop
      • Issue-Reporter (admin): target and GitHub-integration selection stored through /api/app-settings, hub status display, and — when the instance is the local hub — the reported-issues queue from /api/hub/issues with approve/deny actions
      • News (admin): RSS import settings and source CRUD plus manual sync through the news module API
      • Profil: the full profile settings (avatar, display name, language, speech-to-text, agent pet) embedded inline as a settings section in addition to the existing sheet
      • Menü anpassen: reorder/hide/rename the shared sidebar menu groups; preferences persist per user via /api/user/menu-preferences and therefore also apply to the web sidebar
      • Admin: the /admin/general public-base-URL form (with derived Google redirect URI) through /api/app-settings, plus a shortcut that opens the full web admin area in the browser for the remaining admin subpages
      • Benutzer (admin): user management against /api/admin/users — create with temp password, inline role changes, password reset with one-time display, expanded editor for display name/login email/avatar (2 MB, JPEG/PNG/GIF/WebP data URL) and manual password set, and delete with self-delete protection
    • opens PDF detail natively on iPad for PencilKit-based signing directly on top of the original file
    • accepts iOS Share Sheet imports for images and document files into the personal chat composer, and can turn a shared screenshot plus user text directly into an Issue Reporter submission
    • on macOS also exposes a menu bar extra that can switch between the active personal chat session and native Team Chat in the same status-item popup; closing the main window keeps the app and status item running, and the popup's top-left Clapilot control reopens the full app window. Finder files can be dropped anywhere on a personal or Team Chat surface to attach them to that composer; dropping files on another native module uploads them through /api/documents/inbox, refreshes Documents, and confirms the import with an in-app toast.
  • native Documents folder navigation: the iOS/macOS Documents screen mirrors the web documents sidebar. On regular layouts (macOS, iPad) a left folder rail lists Alle Dokumente, Ohne Ordner, Google Drive / Microsoft 365 (only when those sources have documents), and the shared/private document folder hierarchy with indented subfolders and subtree document counts; on compact iPhone layouts the same scopes are exposed through a folder dropdown under the search field. Selecting a scope reloads the list server-side through the existing /api/documents folder_view/folder_id/include_facets parameters (clients/apple/ClapilotApple/Sources/Clapilot/Views/DocumentsView.swift, AppModel.selectDocumentsFolderView), so per-folder contents are complete instead of being cut off by the flat list page size, and the Documents screen force-refreshes on every appearance so files just synced from the Mac folder sync show up without an app restart. Labels are localized in de/en/it; no new endpoints or agent tools are involved.
  • native document download: iOS/macOS document detail screens expose a compact download action when the document has a stored file. It retrieves the original file through the authenticated /api/documents/[id] path, preserves a safe title and file extension, and opens the native share sheet so iPhone and iPad users can choose “Save to Files” or another installed app. The preparation state and errors stay visible, and all labels are localized in de/en/it. This reuses the existing document API and does not add an agent tool.
  • macOS Documents folder sync ("Mac-Ordner-Synchronisierung"): the native macOS client can mirror the Clapilot Documents workspace into ~/Documents/Clapilot, Dropbox-style in both directions. The Settings profile screen exposes a macOS-only card to grant Documents-folder access (a direct TCC prompt via NSDocumentsFolderUsageDescription on unsandboxed builds, or an NSOpenPanel pick with a security-scoped bookmark on sandboxed builds), create the Clapilot folder, toggle syncing, trigger a manual sync, and open the folder in Finder. The engine (MacFolderSyncEngine + pure MacFolderSyncPlanner, controller MacFolderSyncController) reconciles every 5 minutes and on app activation against the existing documents APIs: remote folders become local subfolders, remote documents download as titel-named files, new local files upload through /api/documents/upload (auto-creating remote folders), local edits push through PUT /api/documents/[id], deletions propagate in both directions (local deletions go to the Trash), and concurrent edits produce a localized "conflicted copy" file that is kept and re-uploaded. Per-instance sync state lives under ~/Library/Application Support/Clapilot/FolderSync/. The Documents screen toolbar has a macOS-only sync button that opens the same sync options as a compact popover (MacFolderSyncPopoverView) without the full profile settings. Sync scope is selectable: either the entire Documents workspace, or a checkbox tree of the document folder hierarchy where selecting a folder implicitly includes its subfolders (selection persists per instance; deselecting a folder removes its unmodified local copies, keeps locally modified files untouched, and files outside the selected folders are ignored in both directions). Safety guards: files over 100 MB are skipped, and if a sync run would delete more than 25 remote documents at once, the remote deletions are deferred and the settings card shows a warning instead. Folders are never deleted by sync, only files. No new agent tools are involved — the sync reuses the existing documents endpoints that chat/live agents already cover.
  • The macOS GitHub-release Apple client variant is built with CLAPILOT_GITHUB_RELEASE. That variant is intentionally unsandboxed, embeds the bundled host runtime, exposes local host server controls in native Settings, adds a local-server start action to the instance setup screen, installs ~/.clapilot from the bundled runtime on first launch when needed, starts the managed local services, and signs in automatically against http://127.0.0.1:<PORT> with ADMIN_EMAIL / ADMIN_PASSWORD from the local runtime env. The normal Apple scheme remains sandboxed and keeps the instance/login flow for TestFlight, App Store, and Xcode Cloud builds.
  • Apple Watch companion app: clients/apple/ClapilotApple/ClapilotWatch Watch App receives the active iOS login over WatchConnectivity, stores the instance/session in its own secure store, and keeps manual login only as a fallback. It presents a voice-only chat surface with iOS-aligned transcript bubbles, streaming assistant text, an animated agent state indicator, a tap-to-record/tap-to-send microphone control, and a Live Mode control; it starts watchOS Live Mode through /api/chat/live/session and offers Walkie Talkie mode by sending recorded audio attachments to /api/chat, discarding accidental recordings shorter than one second, and replaying the persisted assistant audio reply from /api/chat/audio/:id.
  • Ollama provider: the web provider catalog and native clapilot-agent runtime support local Ollama and Ollama Cloud through the native /api/tags, /api/chat, and /api/embed endpoints. Local rows require only a reachable base URL; Cloud rows use an API key. The provider's optional encrypted browser session supplies Ollama Cloud quota data without being sent to inference endpoints.
  • iOS Subscription Usage: native Settings renders every provider returned by /api/subscription-usage, including Codex, Claude Code, Grok, and Ollama. Window names are localized from semantic keys and reported durations, including the Claude Fable 5 weekly limit; Codex primary_window and secondary_window are never assumed to mean fixed five-hour/seven-day periods. clients/apple/ClapilotApple/ClapilotUsageWidget provides compact small, medium, and large WidgetKit layouts for the first two provider cards in the stable snapshot order and applies the same window-label rules. The extension reads the selected instance from the existing App Group and the signed-in session from the shared Keychain access group, strips the session cookie on cross-origin redirects, caches the last successful instance-scoped snapshot in the App Group, and asks WidgetKit for another timeline after 30 minutes. It does not use or expose a developer API key.
  • Apple Watch complications / Smart Stack widgets: clients/apple/ClapilotApple/ClapilotWatchWidget is a watchOS WidgetKit extension embedded in the watch app that ships three accessory-family widgets (circular, corner, rectangular, inline) for watch faces and the Smart Stack: subscription-usage meters from /api/subscription-usage, upcoming calendar events from /api/calendar?from&to, and an unread-email count derived from the read flags of /api/emails?limit=50&prefer_cache=1. The watch app publishes the active instance, UI language, and session cookie into the shared App Group and Keychain access group via WatchWidgetStateWriter on login, phone-session sync, and bootstrap, and clears them on logout; each timeline provider fetches with the mirrored session cookie (stripping it on cross-origin redirects, persisting rotated cookies), caches the last instance-scoped snapshot in the App Group, and refreshes after 30 minutes (usage) or 15 minutes (calendar, email). Widget titles, descriptions, states, and accessibility labels are localized in German, English, and Italian.

AI and admin UI

  • chat: src/app/(app)/chat
  • team chat: src/app/(app)/team-chat
  • Live Stream Studio: src/app/(app)/livestream with admin-only /api/livestream/studio; the separate clapilot-streamer process owns FFmpeg/RTMPS, triggers media/chat polling, and reports health into Postgres
  • shared group chat API: src/app/api/chat/group/messages/route.ts
  • native iOS/macOS team chat view/menu: clients/apple/ClapilotApple/Sources/Clapilot/Views/TeamChatView.swift
  • Apple push-device registration API: src/app/api/push/devices/route.ts
  • live voice APIs: src/app/api/chat/live/session/route.ts, src/app/api/chat/live/tools/route.ts
  • Team Chat renders human and assistant messages as one Slack-style left-aligned timeline with a fixed avatar column, inline sender name plus timestamp, and plain own-message text instead of a separate accent bubble.
  • Team Chat channels are either public or private. Public channels are discoverable by every signed-in user and auto-join that user on first open; private channels stay limited to active members. Channel creators, room admins, and app admins can switch visibility at any time. #general is public by default; admins may make it private, which suspends auto-join and enables member exclusion, while switching it back to public resumes auto-join for everyone including previously removed users. App admins can discover, open, and manage any private channel without being inserted into its membership, while direct and group_dm privacy is unchanged. Web creation defaults to public and both web and Apple channel-settings surfaces expose the current visibility; private membership continues to use the existing member editor.
  • pending personal, floating, and Team Chat agent replies use the signed-in user's shared chat activity selection. The compact three-dot typing bubble is the default; explicitly selecting a Pet replaces the bubble across those surfaces
  • web and native chat surfaces render assistant Markdown inline, including links, lists, code blocks, and emitted Clapilot Canvas blocks. During a streamed assistant turn, reasoning from <think>...</think> (including supported reasoning-tag aliases and malformed repeated </think> boundaries from local templates) appears only as an unboxed text line using a left-to-right animated AI gradient. The line keeps its natural height so multiline reasoning is not clipped, respects Reduce Motion on Apple platforms, disappears as soon as final answer or Canvas output starts, and is never retained as a completed-message section or completion-notification preview. The parser and presentation are shared by /chat plus the floating right-side web chat and by personal plus Team Chat in the iOS/macOS client
  • user-sent messages render as Markdown too (src/components/chat-user-message-content.tsx, used in /chat, /team-chat, and the floating right-side chat): lists, tables, fenced/inline code, links, and workspace-file/entity detection work like in assistant messages, single newlines stay hard line breaks, pasted raw HTML markup is converted into fenced html code blocks instead of being parsed or dropped (small inline fragments stay literal text), team-chat @mentions of valid member/agent handles keep their navy highlight inside the Markdown flow, and long messages (over ~1400 characters or ~20 lines) collapse to a faded preview with a localized inline Mehr anzeigen/Weniger anzeigen toggle (chat.message.showMore/chat.message.showLess in de/en/it)
  • inline code spans in assistant messages use a quiet Clapilot-tint bordered pill (soft blue hairline + pale blue fill, navy text) instead of the legacy grey background, and ISO-8601 timestamps written inside inline code are reformatted to a short, locale-aware, user-facing string that preserves the written wall-clock (e.g. 2026-06-12T08:00:08+02:0012.06.2026, 08:00); the formatter lives in src/lib/chat-inline-code-format.ts (web) and clients/apple/ClapilotApple/Sources/Clapilot/Views/ChatInlineTimestampFormat.swift (native, applied in ChatDetectedEntityText). The native client renders inline code as plain monospaced text (no grey background to restyle), so only the timestamp reformatting is mirrored there
  • assistant messages auto-convert detected workspace file references (/app/workspace/... in plain text, inline code, Markdown links, file:// URLs, and file-explorer download URLs) into compact clickable document chips showing a type-specific icon (PDF, Word, sheet, slides, text, Markdown, HTML, code, data, archive, e-mail, image, video, audio, generic) plus the file name; clicking a chip opens the file inline in a new tab through the bundled file-explorer download endpoint, the detection/classification helpers live in src/lib/chat-workspace-file-chips.ts, the chip UI in src/components/chat-workspace-file-chip.tsx, and the same chips render during answer streaming and in every surface using ChatAssistantMessageContent/AssistantMarkdownText (main /chat, floating right-side chat, embedded assistant Markdown). The native iOS/macOS client mirrors this: detected workspace file references in assistant messages render as inline FDS-styled document chips (SF Symbol type icon + file name, navy accent, hairline border) that open the file via the same /api/modules/file-explorer/api/download endpoint; the Swift detection/classification/flow-rendering lives in clients/apple/ClapilotApple/Sources/Clapilot/Views/ChatWorkspaceFileChips.swift and is wired into ChatDetectedEntityText, so it covers every native chat surface (personal chat, team chat, news) with chat.workspaceFile.open localized in de/en/it
  • the floating right-side chat now uses an inline collapsible session tray instead of a header dropdown: the tray opens inside the top section of the widget, shows up to 10 personal sessions with scroll, keeps Hauptchat effectively pinned, and exposes direct Neuer Chat and Session leeren actions plus per-session pin toggles. Clearing a session removes its visible history and rotates the runtime session binding so stale agent context is not reused.
  • while a personal assistant turn is still pending in /chat or the floating right-side chat, the UI now renders one inline working bubble that animates through short status text, switches to the active tool label before streamed response text starts, and keeps the most recent tool label visible briefly after fast tool calls complete so quick backend runs do not immediately fall back to the generic preparing state
  • expanded web chat tool timelines show the five most recent calls by default, in chronological order, with a localized disclosure for revealing earlier calls and returning to the compact recent view. The same bounded list behavior covers the main personal/team chat surface and the floating chat, while completed replies still keep the entire tool section behind their existing summary disclosure
  • detached backend specialist runs now persist the same live assistantToolStatuses metadata into personal and team-chat pending bubbles, so Codex-bridge and embedded-Pi specialist executions can surface their current tool labels while still running
  • web chat accepts image, document, video, and audio attachments through the picker and via drag/drop directly onto the composer. WAV, MP3, M4A, and OGG uploads are classified as audio, accepted up to 25 MB, and sent through the configured server-side STT provider before the agent turn; the iOS/macOS personal and Team Chat importers mirror that behavior. Sent image thumbnails persist in history and can be opened in a larger preview in /chat and /team-chat; Team Chat keeps generated image and media-link previews compact in the message timeline, opens image/video media in the same larger preview dialog on click, and persists owned automation/agent audio from the shared agent-media workspace as playable metadata after removing the private local path. History polls return an authenticated media URL instead of embedded audio bytes, and playback loads the bytes on demand. The native iOS/macOS Team Chat timeline provides the same audio playback control and large-preview attachment behavior, while the iOS app exposes a Share Extension for HTTP(S) web links, PNG/JPEG images, PDF, Word, Excel, PowerPoint, text, CSV, JSON, and common OpenDocument/iWork files
  • both personal web chat composers also support @-triggered document autocomplete; selected results become persistent document-reference chips in the composer/history and are forwarded to /api/chat as structured documentReferences metadata for prompt enrichment
  • legacy agent mailbox routes redirect into the unified mailbox UI: src/app/(app)/angela/*
  • legacy compatibility admin/editor: src/app/(app)/(einstellungen)/settings/opencore

RAG in runtime path

  • Chat route (/api/chat) can inject retrieved document context from document_chunks before native runtime streaming.
  • Retrieval logic is implemented in src/lib/rag/retrieve.ts.
  • Background indexing is performed by scripts/document-rag-indexer.mjs started by entrypoint.sh when RAG_INDEXER_ENABLED=true.
  • Admin diagnostics and reindex controls are exposed via /api/admin/rag/status and /api/admin/rag/reindex.

Detailed implementation:

Group chat persistence

  • shared room data is stored in chat_group_messages (migration db/migrations/021_chat_group_messages.sql)
  • each row stores sender identity (sender_user_id, sender_display_name) plus nachricht/antwort
  • room-scoped direct messages in /team-chat reuse the same table via room_id naming (clapilot-members for the shared room, dm:<user-a>:<user-b> for user direct threads, and agent-dm:<user-id>:<specialized-agent-handle> for direct specialist rooms)
  • chat_member_presence stores lightweight /team-chat heartbeat presence used by the right sidebar online/offline indicators
  • chat_room_typing_state stores short-lived room typing heartbeats used for team-chat ... indicators in the transcript and sidebar
  • user_push_devices stores Apple APNs device tokens for signed-in users so team chat and personal KI-Assistent replies can deliver remote notifications to Apple clients. Before APNs delivery, the same message event is written idempotently to user_notifications; this keeps GET /api/v1/notifications polling payloads aligned with Apple title/body and chat-routing metadata even when no Apple device is registered or APNs is temporarily unavailable
  • chat API tags shared-room turns as group-chat context for KI-Assistent and supports silent NO_REPLY behavior
  • the native Apple app mirrors the same team chat contract with a dedicated Team Chat menu entry, a unified Mitglieder & Direktnachrichten rail/sheet for both the shared Clapilot Team Chat room and member DMs, an Agenten section and @ suggestions filtered by actual room invitations (including the removable main agent), native channel controls for invite/remove plus mention_only / all_messages, remote APNs registration so tapped iOS team-chat notifications open the matching room while personal KI-Assistent reply pushes open the matching chat session, and the same inline typing / working indicators for both human room members and pending agent replies without a separate sidebar progress card
  • Spezial-Agenten is also exposed natively, grouped with Automationen in the shared /geplante-aufgaben workspace behind the Agenten segment (mirroring the web tabs, one drawer entry for both) and backed by /api/specialized-agents/overview, with searchable compact specialist rows (avatar, name, @handle · description), a running-sessions strip under the search field, automatic refresh while specialists are running, and a detail drill-down for recent visible specialist runs.
  • personal /chat, the floating web chat, Team Chat, and the native Apple chat clients smooth live assistant streaming client-side by queueing incoming delta text, typing it out letter by letter, and appending the selected activity suffix until the stream finalizes and normal markdown rendering takes over. The suffix uses user_profiles.agent_pet_key: bubbles is the default compact animated three-dot bubble, while explicit Pet selections render their activity asset. Other loading animations remain unchanged. Built-in Pet animations render per platform: the web working indicator eager-loads the selected asset, iOS plays bundled Pet GIFs through the embedded animation web view, and macOS plays them natively through an NSImageView-backed view; the bubble itself is native UI on every client.
  • personal /chat and the floating web chat gate active runs per chat session: a running turn queues additional messages only in that same session, while other sessions can start concurrent requests. The backend already serializes turns per chat-session runtime key, so client-side cross-session concurrency preserves per-session ordering. Composer busy state, stop controls, and history-poll pausing follow only the active session.
  • the native Apple markdown chat renderer now formats markdown tables as real horizontally scrollable tables instead of raw pipe-delimited text
  • personal /chat and the floating web chat render assistant responses against a wider content column with reduced horizontal viewport padding so larger markdown blocks such as tables can use almost the full available width, while markdown tables keep natural column widths and fall back to horizontal scrolling instead of compressing every column into narrow wrapped cells