AIplane Dots: product and architecture specification¶
Status: implementation in progress; personal Dot ownership, active lifecycle,
the first web management page, manually managed Dot memory, recent activity,
owner-scoped memory/activity APIs, private Dot chat sessions, and personal
tool selection with durable approvals, per-action rules for browse_page and browser_control, Dot-bound schedules and webhooks, and same-owner directed delegation with durable child approvals are implemented. Organization ownership, group-derived membership, independent active limits and configuration through the existing agent builder are implemented; current member writers can authorize and explicitly select each organization Dot’s own OAuth credential. Active organization Dots support private saved-draft and published conversations for current member writers, including durable approvals, selected own credentials, isolated Dot notes and shared organization knowledge. Published private conversations retain their original version and use current member Write access for history and Inbox decisions. Organization schedules and asynchronous webhooks run pinned published versions in fresh private principal conversations. Personal Dots can delegate bounded tasks to consented organization Dots. Organization conversation reuse, outgoing organization delegation and public agent channels remain unavailable.
The current implementation branch has the personal-Dot owner and active
state table, transactional active-slot enforcement, and session-authenticated
GET/POST /api/v0/dots plus PUT /api/v0/dots/{id}/active endpoints. The
active cap is an operator setting at /admin/settings → Access, defaulting to
four. The /dots page lists, creates, activates and deactivates personal Dots.
Lifecycle endpoints require the independent can_manage_dots group
permission; administrators hold it and other groups default to disabled. Each
Dot card shows its name, active state and optional purpose description. Its
Details button opens tabs for memory, activity, access, communication,
workspace and automation. The workspace tab links to the Dot's file manager;
automation links to the existing Dot-scoped schedule and webhook pages. Tabs
keep their loaded state while switching so unsaved access edits are preserved.
The short description appears on the card and to other Dots; it is not sent to
the model as an instruction. Conversational setup saves separate work
instructions that the personal Dot uses in its runs. The manual creation
dialog leaves those instructions unset; give that Dot its task in chat. See
the setup walkthrough.
The memory tab has
separate preference, project and fact entries. Owners can add, edit and delete
those notes; they remain separate from user-wide memory. The activity tab
shows the Dot's recent audited events and can page through older ones.
Starting a Dot chat adds a session-start event without copying conversation
text. Personal Dot tool decisions and outcomes appear in the same feed with
the acting user and Dot attribution; their activity detail contains the tool,
decision and status, but not arguments or tool results.
Dot memory has a separate store and owner-scoped API, but automatic memory
curation is not implemented. A personal Dot can start a private chat that
reads bounded Dot memory and the user's existing profile context. Its chat
uses the tools selected in its Access and approvals panel, intersected with
the user's current grants, enabled settings and connected MCP tools. Existing
memory tools are selected at creation when granted and enabled; their writes
remain isolated to the Dot. Schedules and webhooks can run with the same personal Dot context and durable approvals.
| Endpoint | Behavior |
|---|---|
GET /api/v0/dots |
Lists only the signed-in user's personal Dots, including inactive ones, and returns the active limit. |
POST /api/v0/dots |
Creates a named personal Dot if the user has an active slot. |
PUT /api/v0/dots/{id}/active |
Activates or deactivates an owned Dot; activation rechecks capacity transactionally. |
GET /api/v0/dots/{id}/access |
Returns the owned Dot's tool selection and approval rules together with the user's current available catalog. |
PUT /api/v0/dots/{id}/access |
Replaces the owned Dot's selected tools and their approval rules, retaining other agent spec fields. |
GET /api/v0/dots/{id}/communication |
Returns actual same-owner peers and separate directed outgoing/incoming consent. |
PUT /api/v0/dots/{id}/communication |
Saves one directed consent under current management permission and generation checks. |
GET /api/v0/dots/{id}/memories |
Lists at most 500 notes with actual scopes/names/current writable flags; organization access requires current membership and relevant Read/Write share. |
POST /api/v0/dots/{id}/memories |
Creates or reclassifies a memory (preference, project, fact); requires explicit scope and at most 2,000 UTF-8 bytes. |
PUT /api/v0/dots/{id}/memories/{memory_id} |
Updates a note under explicit scope and the same byte bound and current write rights. |
DELETE /api/v0/dots/{id}/memories/{memory_id} |
Deletes an authorized note under explicit ?scope=dot or ?scope=organization. |
GET /api/v0/dots/{id}/activity |
Lists the owned Dot's audited activity, newest first; accepts cursor and limit. |
POST /api/v0/dots/{id}/sessions |
Creates a private chat session owned by the user and associated with the active Dot. |
Lifecycle routes require can_manage_dots. Administrators configure it in the
existing group form; agent management does not imply Dot management. Revoking
it blocks list, creation and active-state changes after RBAC reload. It does
not deactivate existing Dots, revoke tool grants or stop existing runs;
owner-scoped access and execution retain their existing checks. Creation and active-state
changes are recorded through the existing agent activity chain. The Dot
principal starts without independent grants; personal execution uses the
owner's effective authority. Lowering the configured active cap does not deactivate existing
Dots; creation and reactivation remain blocked until the owner is below the
new cap. Dot memories are separate from user_memories, reuse its kinds and
duplicate handling, and can be managed under /api/v0/dots/{id}/memories.
A Dot chat session reads bounded Dot memory and the user's existing profile
context. The memory tools remember, recall, update_memory and forget
follow the selected Dot rules and the user's memory grant and setting. Writes go to that
Dot's own store; recall returns both Dot and user memories with explicit
scopes, and user-wide memory is read-only from a Dot chat. Selected core and
MCP tools act under the owner account and existing connector mode. Deactivating
a Dot preserves its existing sessions but blocks new sessions and new turns;
ordinary pending Dot turns remain paused while the Dot is inactive. Affected
delegation trees are cancelled when a participating Dot is deactivated. The /dots
page displays active usage against the operator limit, creates a personal Dot
with a friendly name, starts a private chat, and lets the owner deactivate or
reactivate it. A deactivated Dot stays in the list and can be reactivated when
a slot is available. The Access tab offers selected tools
with Allow or Ask before each call; unselected tools are denied. Connector
identity labels identify the selected user, Dot or shared connection. Supported
personal OAuth connectors may use a separately authorized Dot connection;
connecting and selecting it are separate operations. Organization Dots have
explicit organization ownership, own-account management and private draft or published
test chat for current member writers. Their Setup memory panel exposes isolated
Dot notes and shared organization knowledge. Member writers change own notes;
shared-note changes also require current gateway administration. Runtime memory
reads both scopes under its Recall grant; writes remain Dot-specific and no
employee profile is read. Organization schedules and webhooks use the selected published
version and independent principal. They can receive consented personal Dot
requests; outgoing organization delegation and public agent channels remain
unavailable. An owned local credential remains visible
for explicit
disconnect after catalogue access is lost, including credentials never selected
for execution. Restricted catalogue and user-account details stay hidden.
Active
Dot cards link to the existing schedule and webhook creation forms with that
Dot selected.
Access changes reuse the agent's draft spec, revisions and audited save path.
The API accepts {"tools":[{"id":"browse_page","permission":"always_ask","actions":[{"id":"read","rule":"allow"},{"id":"fill","rule":"deny"}]}]};
an empty list denies every tool. Duplicate IDs, unavailable tools and unknown
permissions are rejected. Only the owner can read or update these settings,
including while the Dot is inactive. Tool labels and descriptions use the
existing catalog and live tool schemas; actual IDs distinguish actions within
a grouped capability. A read-only declaration defaults to Allow; writes and
unknown effects default to Ask before each call. Explicit rules may narrow or
permit an action within the owner's existing authority. A connector's own
Ask mode continues to require approval even when the Dot rule is Allow.
Tools with a declared action catalogue expose an Actions disclosure. Each
actual action can inherit the tool rule or use Allow, Ask or Deny. The implementation supports browse_page and batched browser_control; connector tools without that contract
retain their existing tool rules. Action IDs and descriptions come from the
tool implementation. Unavailable saved actions remain visible and must be
removed before saving. Current overrides and grants are checked before any
execution, including after approval; action Allow cannot bypass connector Ask.
The saved pending call carries ordered action IDs, and incompatible changes
to its classification refuse execution. See action rules
for the runtime and wire contract.
AskFirst persists a suspended call in the existing chat approval system. The owner can approve once or deny in chat or Inbox. Approval refers to the original arguments; resumption reloads Dot selection, current user grants, enabled settings and connected tools. Revoked selections and disabled tools cannot execute on an old approval. Dot deactivation leaves ordinary pending calls paused and cancels affected delegation trees.
Personal Dot files¶
Choose Workspace on a personal Dot card to open its files. The page uses that Dot’s actual name and storage state. Open folders, download files, upload files of at most 50 MiB, create folders, or delete files and empty folders after confirmation. Missing file metadata is shown as unavailable. Directory results are paginated; reload after changes from a running Dot. Files are downloaded, not executed or previewed in the web page.
The owner can inspect an inactive Dot. Upload, folder creation and deletion are
blocked while any of the Dot’s computer containers are active or waiting for
confirmed teardown. Owner rights are checked again after storage requests.
Files remain across turns and container expiry. In verified personal Dot
run_in_sandbox and browse_page calls, /workspace is the shared persistent
file directory; /work remains scratch and attachment output. Copy a selected
output into /work to deliver it in the conversation.
Persistent storage is available only with a configured persistent runner volume and a successful local rootful Linux/gVisor mount proof at runner startup. An unverified runner shows unavailability; it does not substitute scratch storage. The workspace API supports personal ownership. Browser logins persist in the Dot's server-side browser profile; a self-service browser-profile reset is not implemented. See the complete workspace design and runner requirements.
Deactivation preserves files. Dot and account deletion create durable cleanup work. The runner seals the deleted Dot, confirms container removal, then removes its files in bounded passes. Failed cleanup retries after restart. A private minimal owner/Dot tombstone remains to reject delayed requests; it contains no workspace contents and is not exposed to users or models.
Personal Dot communication consent¶
The Communication disclosure configures separate Can ask and Accepts
requests from decisions for actual owned Dots. Both decisions are required
for a directed relationship; reverse communication needs its own choices.
Inactive peers remain visible. New enabling requires both Dots active, while
revocation remains possible. Each row saves separately and a stale edit must
be reloaded explicitly. Mutations require current can_manage_dots permission.
The Both consents enabled indicator describes stored consent. Personal chats with selected and authorized forward_request can send an
explicit bounded task to a consenting receiver. The receiver uses its own
selected tools, rules and memories under current owner permissions. Child
approvals propagate to the root conversation and Inbox; receiver histories
are private and read-only. Revoking consent or deactivating a participating
Dot cancels affected delegation trees. See Dot communication.
Implemented personal Dot background execution¶
The existing schedule and webhook forms expose Run as, using the owner's actual Dots and the ordinary assistant option. Creating or changing a binding requires an active owned Dot. An unchanged inactive or unavailable binding remains visible and may be retained while editing unrelated configuration; it cannot execute until the binding is available and active. There is no independent Dot model selector: the existing model catalogue, cron/timezone, tools switch, synchronous mode and reuse settings remain the controls.
Conversation reuse requires a private user-owned session with exactly the
same Dot binding, or an ordinary private session for an ordinary automation.
The linked-chat picker uses the existing chat listing with dot_id filtering:
an absent filter lists all, an empty filter selects ordinary sessions, and a
concrete ID selects that user's Dot sessions. Changing Run as clears the
form's linked conversation; server validation repeats the ownership and
binding checks. Webhook reruns replay an actual stored payload into a fresh
conversation carrying the webhook's current binding.
headless::open_session uses session-core's atomic idle turn-pair creation:
it inserts the user prompt and assistant turn together only if the conversation
has no running or suspended assistant turn. Background execution registers
with the same worker registry as chat, so streaming and stopping use the shared
session mechanisms. The substrate remains unaware of Dot ownership.
Each run records the exact assistant turn ID, original tools switch and history window before model execution. Resume reloads that durable run context and checks its owner, private session and unchanged Dot binding. The tools ceiling is the original switch intersected with the current automation switch, owner grants, enabled settings and Dot rules. Enabling tools later cannot grant them to a turn that started without them. The recorded history window is restored on resume; later settings cannot broaden that turn's history. Usage retains its scheduled/webhook source and existing owner billing and limits. A separate per-Dot usage dashboard or billing budget is not implemented.
Approval-required calls enter waiting, appear in Inbox and the linked chat,
and release the execution worker. Approval applies only to the stored call
arguments, with current access checked before execution. Resumed completion,
denial or cancellation updates the exact run; an older continuation cannot
overwrite the summary of a newer run. Synchronous webhook fires and reruns
return HTTP 202 with status: waiting and the session ID when a decision is
needed; waiting is distinct from a failed run.
Pausing a schedule or webhook prevents future triggers and permits resolution of its existing pending turn. Deactivating the Dot preserves conversations and keeps ordinary pending Dot calls paused; affected delegation trees are cancelled. Deletion of an automation returns a conflict while its run is executing or awaiting a decision: disable future triggers, then finish or stop the turn before deleting. The existing Dot UI provides deactivation, not a Dot-delete action.
Personal Dot files and persistent browser profiles are implemented for supported runner deployments; owner browser handover is described in dots-browser-handover.md. Automatic memory curation remains planned. Organization conversation reuse remains unavailable. The user workflow is in Schedules, webhooks and inbox.
Organization schedules and private run history¶
Current organization member writers open Scheduled actions from the Dot's
existing agent editor. The same list and create/edit forms use the actual
principal_id scope. Back, Cancel and successful saves retain that scope;
personal schedules retain their existing user scope and optional Dot binding.
An organization schedule explicitly selects an available positive published version and timezone. The form displays the selected version's authored model; an omitted model is shown as missing. It offers no employee model override, user identity or linked personal conversation. Each fire opens a fresh private conversation owned by the Dot's principal. The selected version remains pinned after a newer publish. Current principal model/tool grants and explicitly selected own MCP credentials remain execution ceilings; no employee profile, credential or model grant is substituted.
Schedule edits and toggles compare the returned configuration generation. Authored execution edits invalidate older runs for further execution. Disable prevents future fires while leaving an admitted pending run answerable. Run history retains its original version and generation. Structural cancellation and reconciliation preserve the original owner, private session, assistant turn and run/session version; changed configuration or deactivation does not prevent an authorized writer from stopping that exact turn. Reconciliation updates the exact run and cannot replace a newer or different-generation schedule summary.
Open chat opens the existing editor at
/agents/{principal_id}?tab=try&test_session={session_id}. Test chat reads the
actual private transcript over its existing events endpoint. Its source and
version remain unknown until the stopped-turn debug response supplies them;
source selection and submission remain disabled during that load. No Draft
label is inferred for a scheduled conversation. Stop cancels the actual
running or suspended turn through
POST /api/v0/agents/{id}/test/{session_id}/cancel with its turn_id.
A cancelled turn is recorded as a failed run with its cancellation reason.
New conversation clears the history query without cancelling existing work.
Navigation invalidates outstanding component operations so an older response
cannot reopen a previous session or overwrite the current URL.
Organization schedule conversation reuse, Dot delegation and public agent channels are unavailable. Organization webhooks use the same private history and exact-turn Stop; see their admission contract. Personal Dot computers and browser handover are implemented for supported runner deployments; automatic memory curation remains planned. See organization Dots and Schedules, webhooks and inbox.
Product goal¶
AIplane Dots are named, persistent AI coworkers that a person or an organisation can reach through AIplane's web interface. A Dot keeps useful context across runs, can work from chat, schedules and incoming events, and uses only the identities, connectors and actions its owner has authorised. The implementation uses AIplane's own runtime and configured model upstreams. It does not install or depend on OpenDots, CopilotKit Intelligence, AG-UI, OpenBot or OpenAI Dots.
The product adopts the user-facing capabilities described by OpenAI Dots and OpenDots, not their code or hosted services. OpenAI describes scheduled work, read-only background research, long-term preferences and action review. The OpenDots repository describes a persistent agent workspace, per-Dot connections and approvals, and explicitly notes that its schedules are not a complete goal or event-trigger system. These references inform the product requirements; they do not determine AIplane's implementation.
Confirmed requirements¶
Dot ownership and identity¶
- A personal Dot belongs to one user, has its own display name, and runs with that user's effective permissions.
- A personal Dot may use a connector with the user's connected identity or a connector identity attached specifically to that Dot. The user chooses per connector.
- An organisation Dot belongs to an organisation, has its own system identity, and must use an organisation/Dot-owned connector identity. It must not silently inherit an employee's identity.
- The Dot name is the named agent identity shown to people. For a personal Dot, the acting user remains the security principal for permission checks; the activity record also identifies the Dot.
- Users may create Dots when the operator enables that capability. The operator controls the maximum number of active personal Dots per user.
- The initial default active-Dot limit is four. Deactivating a Dot frees an active slot; the requirement limits active Dots, not the historical number of disabled Dots.
- Deleting a user removes that user's personal Dot principals, definitions, memories, grants and tokens through the existing principal cascade.
Work and channels¶
-
Dots must be able to communicate with one another under explicit permissions in both directions. The first planned slice permits bounded internal delegation between personal Dots with the same owner; receivers retain their own tools and approval rules, and only explicit task data is shared. This is not executable yet; directed consent configuration is implemented and the reusable dispatch and privacy design is in Dot communication.
-
The initial user interface is AIplane's web application only. Slack is out of scope. Voice and other channels are later work unless separately approved.
- Dots are reachable when idle and can continue work through scheduled or event-triggered runs. "Always on" does not require a model process to run continuously.
- Events should reuse AIplane's existing webhook and tool/MCP mechanisms. A ticket-monitoring example is handled through the configured ticket-system MCP; it does not justify a Gira/Jira-specific integration.
- Dots use AIplane's configured model catalogue and existing upstream routing.
- Existing sandbox and browser capabilities should be reused or extended to give a Dot a suitably isolated computer. The browser extension that acts in a user's live browser is not sufficient for unattended work.
Permissions and actions¶
- A personal Dot's effective permissions are the intersection of the user's effective permissions and the Dot's own allowed tools/actions. The Dot may narrow user rights but never expand them.
- An organisation Dot uses its own principal and explicit grants.
- Owners choose connectors and configure rules by tool and action.
- Actions outside read-only research and chat require an explicit policy. External writes and critical actions must be reviewable and can require a human approval before execution.
- Approval checks are enforced in the gateway/tool path, not only in prompts or the browser.
- The activity record must show the acting user (for personal Dots), the Dot, the selected connector identity, action, decision and outcome.
Memory and Dot workspace¶
- A personal Dot can use both its own memory and the user's general knowledge and preferences. Organisation Dots must not acquire an employee's personal memories by default.
- Memory persists across runs. A background process should consolidate useful user knowledge and Dot-specific lessons, including pitfalls, so they can prevent repeated mistakes.
- Each Dot has a persistent, isolated data area that it can reuse across runs for project work and its own structured information.
- The implementation should reuse user memories, document/canvas storage, agent state, and existing tool APIs where they fit. It must not expose arbitrary application database access to a model.
Existing mechanisms to reuse¶
| Need | Existing AIplane mechanism | Gap to resolve |
|---|---|---|
| Agent definition and display name | agents, AgentSpec, drafts and published versions |
Represent Dot ownership and personal-vs-organisation execution mode |
| Identity and organization grants | system principals, principal_grants, agent shares |
Personal Dot must act with the user's authority while retaining Dot attribution |
| Chat, runs and streaming | chat_sessions, chat_turns, SessionDriver, JSON-SSE |
Associate a personal Dot with user-owned sessions without turning it into a second chat engine |
| Durable pause and approval | chat_turn_suspensions, agents::approval, Inbox |
Interactive chat and user-owned scheduled/webhook turns can persist a pause and resume through the user's Inbox. Dot execution must retain its attribution and re-evaluate current owner grants and Dot rules when a paused turn resumes. |
| Schedules | scheduled_actions and scheduled worker |
Personal Dot binding and organization principal-owned, pinned-version execution are implemented; organization runs open fresh private sessions |
| Event triggers | Webhooks and headless execution | Personal Dot binding and organization-owned asynchronous webhooks use durable assistant-turn correlation and current execution authority |
| MCP catalogue and execution | connector catalog, McpConnectionManager, UserMcpLayer |
Personal delegated and Dot-owned credentials; organisation/Dot OAuth identity |
| Per-user memory | user_memories, memory tools, dot_memories |
Runtime reads/writes and background curation for isolated Dot memory |
| Agent conversation state | agent_state |
Session-scoped today; Dot workspace must persist independently across sessions |
| Browser and code execution | sandbox-runner, sandbox browser tools, browser-control | Persistent isolated computer/profile/storage per Dot, suitable for background runs |
| Operator settings | declarative settings API and SPA | Dot creation permission and active-Dot limit (default 4); define organization scope |
| Usage controls | user/agent spend and usage limits | Attribute background usage to its owner and Dot; no separate parallel-run cap is requested |
Shared mechanisms: personal Dot access and approvals¶
The current code establishes these reuse points and the remaining runtime seam:
| Need | Existing mechanism | Dot-specific work |
|---|---|---|
| Resolve the signed-in user's current tool ceiling | AppState::allowed_tools_for_session, UserMcpLayer, and CompositeToolSource |
Resolve the ceiling on each Dot turn and compose only the connectors selected for that Dot. Do not treat a tool name from the model as a grant. |
| Store a Dot's tool allowlist and approval settings | The Dot already has an agents.draft_spec; AgentSpec.main.tools and main.tool_resources represent tool selection and per-tool permission |
Add an owner-scoped update/read path that validates against the user's current grants. The ordinary agent spec validator assumes grants belong to the agent principal, so it cannot be called with the Dot's empty principal grants unchanged. Do not add a parallel action-policy table. |
| Enforce tool rules before execution | RunToolSource, GrantedToolSource, Permissions and AskFirst |
ChatPersona::with_tool_access narrows the dynamic user/MCP source. LivePersonalDotTool reloads active ownership, current user roles, selected rules, enabled settings and the actual connected tool before each invocation, then applies the existing approval wrapper. Current access also intersects the turn's initial grant ceiling. |
| Pause and resume a decision | chat_turn_suspensions, AskFirst, the user Inbox, and resume_turn |
The chat resume path reloads the session's personal_dot_sessions link before constructing the driver. Keep that resolution and re-check the live owner grant and Dot rule when resuming. |
| Attribute tool activity | agent_audit and the personal-Dot attribution on ToolContext |
Records the acting user, Dot, tool, decision and outcome. Personal MCP admission records the currently selected typed connection and generations as the identity of the attempted call; outcomes remain correlated by the existing call ID. |
Tool::changes_state() is the existing default for agent approval and an MCP
tool reports a state change from its server's destructive and read-only
annotations. A personal Dot needs a stricter default: missing or incomplete
read-only metadata must not silently turn an external action into an
unreviewed write. This stricter resolution belongs in the Dot policy seam; it
must not change permission defaults for ordinary chat or existing agents.
The connector store represents mutually exclusive user/principal owners.
Personal Dots can explicitly select the owner’s current connection or their
own authorized OAuth credential. Current organization member writers can
configure a Dot’s own credential and run its saved draft or published version in a private principal
conversation. Organization schedules and asynchronous webhooks use retained
published versions and the same own-principal credentials. Public agent channels
remain unavailable. Ordinary principal runs use
explicitly granted shared-identity connectors. Existing agent-scope
connectors accept none or static_bearer. See Dot identities
for the OAuth selection and generation fences.
Gateway groups resolve identity-provider claims and resource rights. Actual
organization ownership is stored in organizations, group-derived membership
in organization_groups, and canonical dots records carry exactly one User
or Organization owner. A group name is not an owner.
Personal Dot execution retains the user principal and user-owned session for authority, metering and private chat, while carrying the Dot’s AgentRun for its spec, own memory, activity chain and tool/action rules. Tools and models use the intersection of those sources. Organization execution requires the separate current principal authority bridge described in organization Dots.
Dot workspace files and browser profiles live outside per-turn containers in
the runner's validated persistent workspace. A SandboxLease still lives in
a turn's ToolContext and is released at turn end; the runner's lease table
has a configured TTL and capacity cap. The filesystem and browser profile are
mounted only for their typed Dot workspace purpose, and browser handover keeps
the exact scoped container alive while its owner controls it.
The MCP manager’s ordinary overlays are: layer_for_user resolves
the user's allowed per-user OAuth connections plus allowed global connectors;
layer_for_principal resolves only granted connectors with a shared gateway
identity. The personal Dot resolver applies its persisted identity selection, owner
grants and Dot policy. Organization calls require their own selected-principal
resolver before execution is enabled. Exposing both
overlays wholesale and relying on the prompt to choose would exceed the
confirmed permission boundary.
Personal schedules and webhooks retain user ownership and optionally bind to a
personal Dot through dot_id. Organization schedules and asynchronous
webhooks use the owning principal and pinned published version. Their headless
workers open private conversations and resolve the same Dot execution policy
as interactive runs. tools_enabled is an additional ceiling, not approval
for external writes. Webhook payloads retain their untrusted-input framing.
Personal memory has this split in the current code. user_memories is keyed only
by user_id; the four existing memory tools use the acting user's identity
and personal Dot context to route writes into dot_memories. Dot
chats expose them only when the user's existing memory capability is granted
and enabled. recall combines both scopes and marks each result; correction
and deletion operate only on Dot-scoped memories from a Dot chat. The driver
injects the user's preferences only when the shared recall tool is granted
and enabled. Agent agent_state is a different store keyed by
conversation session and is used for typed orchestration slots, so it cannot
serve as persistent Dot memory. A personal Dot turn must get user-profile
memory under the user's existing memory grant and switch, plus a distinct
Dot-owned memory scope for lessons and project context. The default write
target must not silently turn every Dot lesson into a user-wide preference.
Organization Dot memory uses the same typed dot_memories accessors and
existing editor with exclusive Dot/organization scopes. Its initialized principal
run reads own and shared knowledge; writes affect only its own notes. Current
run authority is checked in the same transaction as each note operation.
Proposed architecture¶
flowchart TD
UI[AIplane web: Dots, chat, activity, approvals, workspace]
API[/api/v0 JSON API]
Domain[Dot ownership and policy]
Runtime[Existing agent run and chat runtime]
MCP[Existing MCP catalog and connection manager]
Jobs[Existing scheduler and webhook workers]
Memory[User memories plus Dot memory]
Computer[Sandbox runner and isolated Dot workspace]
Audit[Existing agent activity log]
UI --> API --> Domain --> Runtime
Jobs --> Domain
Runtime --> MCP
Runtime --> Memory
Runtime --> Computer
Runtime --> Audit
The Dot is a user-facing mode of AIplane's existing agent, not a replacement for the agent runner. The execution context is explicit:
PersonalDot { user_id, dot_id }: tool access is resolved from the user's grants and connector identities, then narrowed by the Dot's own policy.OrganizationDot { organization_id, principal_id }: tool access is resolved only from the Dot principal's grants and its own connector identities.
The concrete Rust type and schema are implementation choices. They must keep
the crate dependency direction intact and must not make session-core aware
of Dot ownership.
The canonical dots table stores the user-facing name and active state,
keyed by the existing agent principal with exactly one immutable user or
organization owner. User-facing names
are unique per owner, while the system principal retains a generated unique
internal name; two users can therefore each name a Dot "Harald". Explicit
organizations metadata and selected organization_groups provide the
organization ownership and membership boundary. See organization
Dots for the implemented configuration foundation and
remaining credential and execution requirements.
Identity and authorization flow¶
request from signed-in user
-> load Dot and verify owner/share access
-> establish explicit Dot execution context
-> resolve owner permissions and chosen connector identity
-> intersect owner permissions with Dot tool/action policy
-> apply hard safety rules and approval policy
-> run the existing tool loop
-> append activity as {actor user, Dot, connector identity, action, result}
For personal Dots, user authority is resolved at execution time so a revoked user grant or disconnected connector takes effect without republishing the Dot. For organisation Dots, principal grants remain explicit. A Dot cannot use its model-visible instructions to change these decisions.
Persistence concepts¶
These are logical responsibilities; table names and exact encoding are still subject to migration design review.
- Dot metadata: existing agent definition plus owner type/id, active state, execution mode and Dot-specific policy.
- Connector identity selection: per-Dot connector choice of user identity, Dot-owned identity or organisation-owned identity. Credentials remain encrypted and unavailable to model context.
- User memory: existing user-wide memory, readable by the user's personal Dots only under the user's configured permission.
- Dot memory: separate scope for lessons and context owned by that Dot.
- Dot workspace: persistent Dot-owned project artifacts and structured
data, separate from chat transcript and short-lived
agent_state. - Work item/run correlation: schedule or event source, Dot, session, status, attempts, decisions and outcomes must be traceable through current runs and activity records. Avoid a new task table unless existing schedule/webhook records cannot represent a confirmed lifecycle requirement.
Action policy¶
Policy is configured by a Dot owner and evaluated for every tool call. It has three outcomes: allow, require approval, or deny. Resolution must include the owner's authority, Dot policy, connector/tool policy and mandatory platform rules. The most restrictive applicable result wins. Approval is durable and uses the existing suspension and inbox flow.
Interactive chat and the existing user-owned scheduler/webhook workers can
persist a suspension in chat_turn_suspensions, release the worker and resume
the same tool call through the user's Inbox. Dot execution can reuse this
continuation when it keeps the Dot context attached to the user-owned session
and verifies permissions again on resume. A tool that requires a decision
must still refuse to run on a path where nobody can resume it; enabling tools
on a schedule or webhook is not itself approval. Organization-owned runs need
an explicitly authorized approval owner and continuation path.
Action categories come from each tool's actual declared action catalogue. Personal tool policies and approvals are implemented as described above. Private organization decisions require current membership and Write access. Responses preserve the original source, version, authored snapshot, model and grant ceiling across restart. Published private decisions also appear in the existing Inbox for current member writers. Publication does not admit automation or external callers.
Background work and memory curation¶
AIplane schedules and webhooks use the existing workers with an optional personal Dot binding. MCP calls may be used as event-driven work inputs where the connected system supports them; the Dot feature itself does not implement ticket-system specific code.
OpenAI publicly describes background research as read-only and separately describes scheduled tasks. OpenDots documents scheduled turns and says its schedules are not a complete goal/event system. Neither source exposes a general-purpose internal trigger implementation. AIplane will therefore use its own scheduler and webhooks, with polling frequency, connector event delivery and retry policy defined per supported deployment capability.
Memory curation should operate on existing conversations, user memory and Dot memory through a bounded background run using the configured model upstreams. It must not become model training. The curation cadence, evidence retention, approval behavior and conflict resolution remain open decisions.
User experience¶
The initial channel is the web SPA:
- A user creates a named personal Dot when the operator allows it and an active slot is available.
- The user chooses model, tools, MCP connector identity and action rules.
- The user chats with the Dot, starts or edits ongoing work, and reviews activity and pending approvals.
- The user can inspect and manage user-wide memory, Dot memory and the Dot's workspace.
- The user can deactivate a Dot to free an active slot.
- An authorized organization manager creates an organization Dot, gives it its own identity and grants only the required resources.
UI implementation requires a reviewed mockup/walkthrough before Svelte changes, per the repository working agreement.
First web slice walkthrough for review¶
The management surface for the lifecycle API above uses only fields currently returned by that API:
Sidebar: Dots
My Dots 1 of 4 active
Named assistants available to you [Create Dot]
Name Status Actions
Harald Active [Deactivate]
Create Dot dialog
Name [Harald________________]
Display name [Harald________________]
Description [Optional________________________]
[Cancel] [Create Dot]
The count comes from active rows and active_limit; name, display name,
description and active state come from each returned Dot. The view does not
invent a run status, last activity, or capabilities before those are backed by
the execution and activity APIs. Creation validates the name server-side. The
active row action calls the state endpoint and the count updates from a fresh
list response. The personal execution slice adds a conversation action to each
active Dot:
Name Status Actions
Harald Active [Chat] [Deactivate] [Memory] [Activity]
Selecting Chat creates a private session owned by the signed-in user, associates
it with Harald, and opens the existing /chat/{session_id} experience. Inactive
Dots have no Chat action. Sessions remain private to their user and Dot, and
deactivation prevents new messages from starting. This first execution slice
loads Dot and user memory and applies the selected tool and approval rules.
Approved tool access and approvals walkthrough¶
The next personal-Dot settings surface extends each existing Dot card with an
Access and approvals disclosure. It uses the signed-in user's currently
available tools and connectors as the ceiling; it does not show tools the user
cannot use. The tool list comes from the runtime registry after user RBAC and
per-user tool settings are applied. MCP rows come from the existing connector
tool inventory, including each server's read-only annotation and the user's
current connector mode.
Harald Active
[Chat] [Memory] [Activity] [Access and approvals]
Access and approvals
Only tools already available to you can be enabled for Harald.
Tool label and description from catalog Dot rule Identity
AIplane read-only tool from the user's catalog Allow AIplane
Read-only tool from connected Gira MCP Allow My account
Write tool from connected Workspace MCP Ask before each call My account
Changes to these rules apply to new calls. Approval applies only to the pending
arguments. Current permissions and Dot availability are checked again on resume.
The list contains only tool IDs returned by the user's allowed-tool resolution
and connected MCP layers; display names and descriptions come from their
existing catalogs. Allow and Ask before each call map to the existing
AgentSpec.main.tools and main.tool_resources[tool].permission fields.
Omitting a tool from main.tools denies it to that Dot. The personal Dot's
effective set remains the intersection of this Dot selection and the user's
current grants and enabled settings. MCP readOnlyHint supplies the default
for read calls; a write or a tool without a read-only annotation defaults to
approval. The owner may change that default per tool within the user's grants.
The selected connector identity is resolved separately from this action rule;
a Dot-owned identity is offered only after that connector has a Dot-owned
credential.
An approval pauses the interactive Dot turn through the existing
AskFirst/chat_turn_suspensions/Inbox path. Approve-once resumes the pending
call; a saved Allow rule changes future calls. Scheduled and webhook runs
persist approval-required calls and resume through the same Inbox path. The walkthrough does not add a parallel policy table or
approval mechanism. On resume, current ownership, active state and tool access
are checked again even when the call was approved once.
Delivery plan¶
Slice 1: Dot ownership and active lifecycle¶
- Establish user- and organization-owned Dot records on top of existing agent definitions and principals.
- Let users create personal Dots when their configured group permission
allows it through the independent
can_manage_dotsgroup flag. - Enforce the configurable active personal Dot cap (default 4) transactionally at creation/activation; deactivation frees capacity.
- Preserve current agent-manager workflows for visitor-facing and other principal-owned agents.
- Add the initial Dot list/create/deactivate API and state-based tests.
Slice 2: Delegated personal execution¶
- Carry explicit
PersonalDot { user_id, dot_id }attribution from the chat actor intoToolContext, while keeping the effective principal as the user. This establishes a scope for Dot-owned data; it does not yet grant tools or enforce a Dot action policy. - Enforce user grants intersected with Dot policy before offering or executing a tool.
- Attribute every action to user and Dot in usage and audit.
- Keep sessions owner-scoped and private.
Slice 3: MCP identity selection and action approval¶
- Reuse the MCP catalog, manager, OAuth refresh and secret sealing.
- Support selected user identity or Dot-owned identity for personal Dots.
- Support only Dot-/organization-owned identity for organization Dots.
- Add per-tool/action policy using the durable approval path.
Slice 4: Persistent memory and workspace¶
- Use existing user memories for shared personal context.
- Add Dot-specific memory scope and bounded background curation.
- Reuse document/canvas and sandbox storage where they meet workspace isolation and persistence requirements; otherwise design one narrowly scoped Dot workspace store.
Slice 5: Background work and isolated computer¶
- Extend scheduled and webhook execution to use Dot context and activity.
- Establish safe retries, cancellation, concurrency and usage bounds.
- Extend sandbox-runner for a persistent isolated browser/filesystem per Dot only after confirming the required lifecycle and deployment constraints.
Slice 6: Organization management and operations¶
- Add organization ownership, manager access and organization/Dot connector provisioning.
- Add operator settings, limits, run visibility, retention and deployment documentation for the complete product.
Slices that change rights, personal-data access, credentials or external writes need their policy and UI approved before those behaviors ship. Build one vertical slice at a time; keep each feature's code, tests, translations, documentation and generated artifacts together.
Non-functional requirements¶
- No dependency on an external agent runtime, hosted thread store or hosted computer service.
- Existing AIplane model upstreams, Rust/Rama stack, SQLite migrations, JSON API, JSON-SSE, Fluent catalogs and daisyUI remain the platform conventions.
- Personal and organization data must be isolated in database queries and tool access, not merely filtered in the UI.
- Model/tool output remains untrusted. Existing injection defenses and outbound URL guard apply to background runs as well as interactive runs.
- Runs must respect configured model grants, cost limits, tool rules, suspension expiry, retention and audit requirements.
- The confirmed default of four limits active personal Dots, whether they are currently working or idle. The user has not requested a separate cap on simultaneous runs.
Remaining implementation¶
The following adopted designs define the remaining implementation work:
- Conversational setup and chat participation records the requested natural-language Dot creation and reconfiguration, guided prerequisites, organization peer delegation and ordinary-chat Dot mentions. Its complex interaction mockup requires approval before UI work.
- Organization Dots defines an independent active cap, member/share approval standing and isolated principal execution.
- Dot identities defines the reused user OAuth account and explicitly selected own OAuth account. Personal selection and current organization member-writer credential management are implemented.
- Memory curation defines source selection and reviewed optimization; its background job remains to be implemented.
- Persistent workspace provides durable personal Dot files and browser profiles on supported runner deployments. Browser handover lets the owner control a suspended personal Dot browser; organization handover and runner-replica coordination remain outside the implemented scope.
- Existing worker, run-budget and spend limits bound execution. The active Dot cap counts enabled Dots and does not impose a global parallel-run cap.
Deactivation is reversible and frees an active slot; this is the confirmed product behavior and is implemented by the lifecycle API.
Research references¶
- Grok Bot feature comparison and additional product gaps
- xAI: Introducing Grok Bot
- xAI: Grok Bot product page and FAQ
- OpenAI: Wir stellen dots vor
- OpenAI: How we build safety, security, and privacy into dots
- OpenAI Help Center: Getting started with your dot
- OpenAI Help Center: Dots privacy, security, and safety FAQs
- CopilotKit OpenDots repository README
Documentation build: 2610.1.108 · commit b774e1f9e2c2