Files, Projects, Skills, and personalization
Give AI controlled access to chat files, shared Project context and Skills, and durable personal preferences.
These features have separate ownership and lifetimes.
| Feature | Scope | Use |
|---|---|---|
| Conversation files | One private chat | Inputs and generated artifacts |
| Projects | Shared through Cloud permissions | Instructions, knowledge, files, references, and defaults |
| Skills | Shared through Cloud permissions | Reusable agent instructions with optional Markdown references |
| Personalization | One user | Small durable facts, preferences, and workflow defaults |
Projects and Skills require an authenticated identity on every access path, including their HTTP APIs. Share them with users, groups, service accounts, or all authenticated identities. Public grants are not supported. Existing public grants are converted to authenticated grants at startup, preserving their permission levels. Sharing Project context does not share its users' private chats.
Use readable resource IDs
AI resources use six-character, case-sensitive readable IDs. Chat, Project, and memory IDs are globally unique. Turn and message IDs are scoped to their chat; Project access, knowledge, file, and reference IDs are scoped to their Project. Cloud generates these IDs.
URLs, Assistant capabilities, streamed chat events, and cld assistant
commands use the readable IDs. Database UUIDs are not a fallback input format.
Store conversation files
Chat routes expose a Postgres-backed file system below each conversation. Paths
are absolute in one namespace, such as /photo.jpg or /reports/summary.md,
and reject .. segments. Names are stored in Unicode NFC, so a decomposed
macOS spelling and its precomposed form address the same file (this also
applies to Project files). Each file records whether it came from the user or
the assistant; tools cannot overwrite a user upload. Default limits are 50 MB
per file and 250 MB per conversation. Forking a conversation copies its files.
The conversation owner can delete one file with
DELETE /conversations/:id/files?path=…, which also backs
cld assistant files delete and Assistant's file list. Reading or deleting a
path that does not exist in the chat returns 404 with File not found.
Code runs save validated chart, group and table views under /views/*.view.json.
These are ordinary files: visible in the chat's file list, downloadable and
counted toward its storage budget. Model write tools cannot write or append
under /views; only cloud.view.* creates views. The owner can still edit,
rename or delete them. present({path}) renders valid assistant-owned views
inline, and readers revalidate the current file before rendering.
The file-content response carries X-Cloud-Ai-File-Origin so readers can check
that the current file still has assistant origin.
Separate results from working files
The assistant keeps intermediate steps below /temp/ in the chat, one folder
per purpose, for example /temp/quarterly-report/. A result is what it hands
over: present({ path, title?, description? }) for a file or a view, and
code_open or code_present({ id }) for a Studio app. The optional
description is one sentence of at most 160 characters in the user's
language; a new delivery of the same file replaces it, also with none.
Assistant shows results first and working files one level deeper, grouped by
folder.
The platform prompt asks the agent for this split: intermediate and scratch
files go below /temp/, in one folder named after the result they serve, such
as /temp/sales-report/ for /sales-report.pdf, and deliverables go outside
/temp/. markdown_to_pdf and html_to_pdf write the PDF beside its source,
so the .md or .html source of a delivered PDF stays outside /temp/ too,
such as /sales-report.md. The folder has no special storage rules: its files
count toward the chat's limit and are forked and deleted with the chat like any
other file.
Cloud indexes every successful delivery as a conversation source of kind
result with the turn and call that made it; code_open is indexed when the
turn continues with the browser's report, and a report with an error delivers
nothing. Starting this release indexes the deliveries already stored in chat
history once, so existing chats show their results too; files deleted since are
skipped. That first start reads every stored tool result once, so it takes
longer on installations with a long chat history; meanwhile
ai.conversation_sources stays readable, and writes to it wait. Renaming
a delivered file keeps it a result. Deleting a file, also with its folder,
removes its result, so a later file at the same path is not that result. A
result counts only while its file, app, or visualization exists and the viewer
may read it.
GET /conversations/:id/sources accepts kind (comma-separated result,
web, activity, resource, file) and observed=true, which leaves out
resources indexed as Project context without a tool call, and returns total
next to the page. Each source carries sourceMessageSeq, the chat position of
the message that holds its call, for a ?message= link. Each web search query
is its own activity entry with the key web_search:<normalized query>.
GET /conversations/:id/files pages by path with limit and after;
prefix matches a folder literally, so _ and % in a folder name match only
themselves. DELETE /conversations/:id/files?path=/temp/report&recursive=true
deletes a folder with everything below it, never / itself.
loadAiConversationFileOverview(conversationId) returns the files outside
/temp/, the working folders with counts, bytes, and file types, the loose
working files directly in /temp/, and the storage used against the limit.
Load one folder's files with the files route and the folder as prefix.
The per-turn file inventory (aiConversationFileManifest) and list_files
name files outside /temp/ first, so working files never push uploads and
results out of the bounded list.
Every composer attachment is uploaded first. Messages and durable turn
configuration keep file references instead of inline binary data. For each
turn, Cloud snapshots the exact newly attached files and a bounded, newest-first
file inventory into the system context as untrusted metadata. Attached file
versions are copied atomically with the turn, so retries use the same bytes even
when the conversation file changes or is deleted later. A turn accepts at most eight files,
10 MB per image, and 40 MB of image input in total. Use list_files for the
complete inventory and read_file or view_image before relying on a file's
contents. In a Project chat, the same tools expose authorized shared Project
files read-only below /project.
When the selected chat model supports Vision, Cloud resolves newly attached
images transiently for that provider request; the stored message remains
reference-only. Tool-capable models also receive view_image so they can
inspect a stored image again on a later turn. The selected model performs that
inspection when it supports Vision; otherwise an administrator must configure
a separate Vision tool model. The tool accepts an image path and optional
inspection guidance. It reads only an authorized conversation or Project file,
stays inside the application's allowed data boundary, and returns a bounded
textual analysis. A model with neither Vision nor Tools cannot accept image
attachments.
The default Assistant tools can list files, read bounded UTF-8 slices, write
assistant-owned text files, inspect supported images when configured, and
present downloads. They can also turn an assistant-written conversation file
into a sibling .pdf, which the agent then presents. For a text-first document,
the agent writes or edits a .md file with write_file and calls
markdown_to_pdf with an optional A4 preset and custom CSS. For a layout that
needs HTML, it writes an .html file and calls html_to_pdf. Its optional
inputs are a CSS file or inline CSS of up to 32 KiB, both applied after the
document's own styles; header and footer HTML files; up to 64 conversation
files as named assets, referenced by file name only with #, ?, %, and :
percent-encoded; and page with format
(A4 by default, A3, A5, Letter, or Legal), landscape, and
millimeter margin values (15 by default). The HTML source must be
assistant-owned; CSS, header, footer, and assets can be uploads. All inputs share
the configured Gotenberg input budget, and the document renders in standards
mode through the offline HTML mode. One
application process renders at most two chat PDFs at a time and rejects further
conversions until one finishes. Project files remain read-only and cannot be
converted directly. read_file returns text directly and automatically converts
PDF, Office, OpenDocument, RTF, EPUB, and CSV files to bounded Markdown. Its
mediaType remains the original file type while representation is text or
markdown. Offsets count bytes in that UTF-8 representation; continue with
nextOffset until eof. truncated reports when document extraction reached
its output bound, not when another slice is available. Document content remains
untrusted data and is never promoted to instructions or personalization input.
Images stay on view_image. Unsupported binaries, encrypted or malformed
documents, image-only PDFs that require OCR, and documents above the extraction
limit return bounded errors. These tools do not execute code or access the host.
Keep authorization at the conversation route; a file path is not an access
token. See Document extraction for the
shared conversion contract and limits.
Use Projects for shared working context
A Project owns a name, description, icon, instructions, optional default model,
shared text knowledge and files, Cloud resource references, and read, write,
or admin grants. Creating a Project atomically creates an explicit admin
grant for the creating user or service account. Cloud resolves direct and nested
group membership from the authoritative account database.
Projects have no account owner and survive principal deletion. Project access
changes cannot remove the final admin grant; if an operator deletes the sole
admin principal outside the Project service, operator recovery is required to
add a new grant directly. A platform administrator can find Projects without a
remaining admin and restore their access under Admin > AI > Projects. This
recovery surface can also permanently delete obsolete Projects, but it does
not expose Project contents or private chats.
Project chats remain private to their creator. Sharing a Project does not share chat history. A chat has at most one current Project. Its owner may choose, change, or clear that Project between turns. A change affects only future turns and is rejected while a turn is queued, running, or waiting for attention.
When a turn is submitted, Cloud rechecks access and stores an immutable snapshot
with the Project id, name, revision, instructions, context manifest, and model
default. Past messages do not change when the current Project changes. Retries
reuse that turn's snapshot; new turns use the current Project and revision.
Workers recheck current access before execution. search_project,
read_project_knowledge, and every read below the virtual /project file mount
recheck it before returning data. search_project returns metadata only;
knowledge is read with read_project_knowledge, documents with read_file, and
images with view_image.
The mount is never writable and does not copy shared bytes into a private chat.
Only Project instructions are instruction-bearing. Knowledge, files, references, and tool results are untrusted data. References contain metadata only; the agent must use the target app's current authorized capabilities to read the source.
Knowledge and files are copies stored in the Project: they do not follow their
source, and every member with read access can read them. A reference is a
live pointer. Each member's Assistant reads the current resource with that
member's own access, so a member who cannot open the resource gets a failed
read and nothing else. Adding a reference only checks that its qualified type,
such as notebooks.note or grids.base, has a canonical reader; it does not
grant access to the resource. For agents that configure Assistant through the
CLI, cld assistant reference how-it-works.md summarizes these rules.
The Assistant Project workspace lets users with write access manage basic
metadata, knowledge, files, and Cloud resource references. Because Project
instructions and the default model change trusted agent behavior, only
admin users may edit them or manage Project access. Reference selection uses
Universal Search and can be filtered by application. The HTTP API and
cld assistant projects expose the same metadata, context, and access model.
Reuse shared Skills
A Skill gives Assistant a reusable workflow without attaching it to one person
or Project. Open Assistant settings > Skills to create one, import a
SKILL.md or Skill ZIP, edit its Markdown instructions, add Markdown files
below references/, export it, or manage its Cloud access. read access can
view and use a Skill, write can edit it, and admin can also share or delete
it. The final admin grant cannot be removed.
If the sole Skill administrator is removed outside the Skill service, a platform administrator can restore access under Administration > AI Skills. The same recovery surface can grant access to or permanently delete any Skill.
SKILL.md is the portable source of truth. It starts with YAML frontmatter
containing a lowercase, hyphenated name and a description, followed by the
Markdown instructions. Cloud keeps every other frontmatter field unchanged,
including nested JSON-representable values, up to 20,000 characters in total.
A ZIP may wrap the files in one Skill folder. Import keeps SKILL.md and
supported Markdown files directly below references/; it lists skipped files
such as scripts, assets, agent configuration, and nested references. Cloud does
not run scripts. Unsafe paths still fail. A Skill without references can also
be imported or downloaded as one bare SKILL.md.
Use cld assistant skills list, push <dir>, and pull <name-or-id> [dir]
to move Skills between Cloud and Agent Skills folders. Push refuses to overwrite
a differing Cloud Skill; pull first to keep Cloud changes, or use push <dir> --force
to replace it. Pull defaults to .agents/skills/<name> in the current folder.
cld assistant reference explains skipped files and --force.
With disable-model-invocation: true, a Skill starts only when a person
selects it with /. It stays out of the model catalog and search_skills,
while remaining available in the slash menu. Later turns can reload a selected
Skill by its attached core.ai.skill ID; model-chosen name loads are refused.
This setting controls discovery, not access; a Skill ID from another source,
such as the ai.skills.list capability, still loads.
At the start of a tool-capable Assistant turn, the model sees a bounded catalog
of enabled, model-invocable Skills it can currently read. Catalog entries are
always complete; Cloud never cuts a description mid-entry. When the complete
catalog does not fit its hard prompt budget, Cloud selects whole entries relevant to the current
request and exposes the omitted entries through search_skills. The slash menu and
search_skills share a permission-aware search over Skill names and descriptions.
It supports partial words and minor typos, prioritizes name matches, and excludes
disabled Skills before limiting results. Skill instructions and references are
not searched or loaded during discovery. Server callers use
aiSkills.search(accessSubject, query, limit, { modelInvocableOnly }) and receive
{ skills, more }. Set modelInvocableOnly: true for model discovery; omit it
to include manual-only Skills for explicit selection.
GET /api/ai/skills?q=… uses this search
(up to 30 results, query length up to 200 characters); omit q to keep the ordinary
Skill management list, including disabled entries. ?name=<exact name> returns
that one Skill, including when it is disabled for the caller.
PostgreSQL's standard pg_trgm extension supplies fuzzy matching. Optional pg_textsearch adds BM25 ranking;
without it, native PostgreSQL relevance remains available. See
Optional BM25 search ranking
for setup and the preload it requires. A normal small
catalog needs no search call. Explicitly attached core.ai.skill resources are
loaded by the server before the response. For other relevant Skills, the model
calls load_skill with the exact name. Both paths recheck access and pin the
revision for the turn. Attachment names and metadata are not trusted
instructions. Loading returns the instructions and mounts that revision read-only at
/skills/<name>/SKILL.md; references appear below
/skills/<name>/references/. Assistant reads reference files with read_file
only when the workflow needs them. Relative Markdown links in loaded
instructions become /skills/<name>/references/<file>.md; stored instructions,
exports, and the mounted SKILL.md keep links as written. References remain
untrusted data.
A Skill names app operations by their stable qualified capability ID, such as
mail.conversation.list. Assistant can pass that ID directly to load_tools;
search_tools remains for finding an operation the Skill does not already
identify.
The first successful load pins one Skill revision for that turn, including retries, so an edit cannot change an in-progress result. A later turn sees the new revision. Reading a mounted file still checks current Cloud access; revoked access takes effect immediately.
Apps ship their own Skills, and third-party apps can do the same; see
Ship Assistant Skills. Cloud installs each
with read access for signed-in people who may open the app, and offers it only
while the app runs. The built-in apps ship these Skills:
- Grids ships
cloud-grids, which includes a compact GQL syntax guide with lookup, join, and aggregation examples. It guides queries and daily work and routes product and administration questions to canonical Grids Help. - Assistant ships
cloud-assistantfor conversation history and resources, inter-chat messaging, and routines;scheduled-tasks;assistant-code-modeandassistant-data-analysis; andskill-creator, which explains how to draft a concise Skill and names thecore.ai.skillCapabilities Assistant can use to list, read, create, update, manage references, personally enable or disable, and delete Skills. - Mail, Notebooks, Contacts, Spaces, and Weather ship
cloud-mail,cloud-notebooks,cloud-contacts,cloud-spaces, andcloud-weatherwith their app's normal capability paths, domain defaults, and cross-application guidance.
Skill reference files are mounted for one turn: load the Skill again before reading its files in a later turn. A missing-file error explains this recovery; reloading still checks access. Like every readable Skill, an app Skill starts enabled and can be disabled personally. Each Skill shows its source, such as From app Grids, in Assistant settings > Skills.
Turn recurring work into a Skill
The Suggestions section of a followed turn lists the offer cases as if-then rules, and the model takes the first that applies:
- The user corrected the format or steps of a result for the second time in the chat, and the model delivered the corrected result: it offers to save the approach as a personal Skill.
- The user corrected a result that their own Skill shaped: it offers to add the correction to that Skill.
- The user corrected the tone of a result, such as a mail that is too formal, without stating a lasting rule: it offers to remember the correction as a preference. This does not depend on a Skill. Because memory saves only text the user wrote in that turn, a plain yes cannot be saved, so the model suggests a one-line rule the user can send back. A correction with "always" or "from now on" is saved directly under the memory rules. Built-in and shared Skills change for everyone, so they change only when the user asks for that.
- The user says the request recurs ("again", "every week", "like last time", "always"), pastes a long reusable instruction, or a personalization workflow default covers it: it offers a Skill or a routine.
A new Skill is offered only when no listed Skill already covers the approach.
When Skills are omitted from the bounded catalog, the model also checks
search_skills. A request that a Skill already handles can still lead to a
routine offer. Cases 1 and 2 and the Skill part of case 4 need
skill-creator; if the user disabled it or it was deleted, they are left out,
even when other Skills remain loadable. Case 3 needs the memory tool. A single
preference such as tone belongs in memory, not in a Skill. The model claims
how often something happened only when the user said it or the chat shows it,
and never searches chats only to justify an offer.
The general suggestion limits apply: at most one offer, in the last sentence of the final message, and none after a failure, while asking a clarifying question or waiting for approval, after a reply that already ended with an offer, or once the user declined or asked for no suggestions. Asking for a shorter draft is a correction, not a request for silence. Routine runs do not get these rules.
Cloud does not leave these cases to the model alone. At the start of a new followed turn, the server checks the user's message and the latest messages of the chat with fixed word lists in English and German. When one case fits, it adds one short turn instruction that starts with "Offer once at the end":
- the user corrects the format of a delivered result, such as a table or list, for the second time in a row, such as "Bitte als Tabelle" and then "Fast. Fristen bitte als TT.MM., überfällige fett": a Skill offer;
- the user corrects the tone of a mail draft in the previous reply, such as "too stiff, write casually": an offer to remember the preference;
- the user refers to earlier work by time, such as "like last week" or "wie letztes Mal": a Skill offer if the model finds and reuses that work.
The checks prefer missing a case to inventing one, because the instruction states the case as a fact. A correction is a short follow-up that names a format and points back at the result, such as "bitte als", "instead", "sort them by", or "make it bold". Questions, new tasks that name a format ("Create a sales report as a table", "Füg eine Spalte Telefon hinzu"), and edits that only got a short confirmation do not count. Messages with attached files or Cloud items start new work; the file names are not read as text. A tone correction needs a tone phrase such as "zu steif", "too formal", or "lockerer", and a request for a new mail is not one. "Wie immer" or "as usual" do not count as earlier work, because they are just as often thanks or small talk.
The server adds no instruction when the previous reply ended with a question
or an offer, after the user said no to one, when the message asks for only a
short answer, when the user's messages, memories, or the organization or
Project instructions ask for no suggestions, or when the offer needs
skill-creator or the memory tool and the turn does not have it. A Skill the
user selected for the turn suppresses Skill offers. The checks read at most
one page of the current chat, about the last few turns, and only when the
message alone could start a case; a decline or request older than that page
is not seen. Messages the user sends while a turn runs count as part of that
turn. Because word lists miss phrasings, the instruction itself repeats the
limits: the model skips the offer when it ends with a question, waits for
approval, or could not finish, when its previous reply already ended with an
offer, when the user declined one in the chat, or when the user, their
preferences, or instructions ask for no suggestions or only a short answer.
Turns that continue after an approval and routine runs get no
instruction.
After a yes to a Skill offer, the model loads skill-creator and drafts from
the conversation. Its template first picks the lightest place: memory for a
fact or preference, a workflow default for always using one mailbox or Space,
Project instructions, a Skill for a recurring procedure or format, a routine
for a set time, or a Studio App that the Skill references. A Skill draft
keeps only the procedure, the output format, the capability IDs that worked,
the user's corrections as positive rules, and inputs named by role and title.
It leaves out content from attachments, mails, and web pages, names of people
or customers, amounts, example records, and IDs of mailboxes, Spaces,
notebooks, records, or other resources copied from the chat. The exact ID of a
Studio App the Skill calls is the one exception. An existing workflow default
is referenced instead of repeated. Load triggers name the subject, such as the
team or the report, not only the output format. The core.ai.skill.create or
core.ai.skill.update review is the only confirmation. After saving, the model
says that the Skill loads for matching requests and can be selected with
/skill; later corrections update the same Skill narrowly.
Before changing an existing Skill, skill-creator checks who it affects:
core.ai.skill.read returns the user's permission, and
core.ai.skill.access.read shows who else can use a Skill the user manages. A
built-in or shared Skill changes only when the user can edit it and wants the
change for everyone. Otherwise it stays unchanged, and a correction meant only
for the user can become a personalization preference in the user's own words.
Update and override app Skills
An app Skill updates when a new release of its app changes the content. Cloud
compares a hash of the complete content; personal enabled state, access, the
Skill ID, and turns that already loaded the Skill stay as they are. App Skills
ship with read access only, so the Skill management Actions and
cld assistant cannot change them. They refuse with an error that names the
app.
A platform administrator can override an app Skill: give yourself or another
person write access under Administration > AI Skills > Permissions, then
edit the Skill. Cloud keeps the change and marks the Skill Customized, or
App update available once the app ships different content.
Compare with app version shows the differences; Reset to app version
replaces the content and lets later updates apply again. A deleted app Skill
stays deleted until an administrator restores it. When another Skill already
uses the name, Cloud does not install the app Skill and lists it as
Name in use. See
Administrators can override an app Skill
for every state and the CLI.
The platform-admin HTTP API under /api/admin/core/ai-skills returns each
Skill's source with app, status, and availability, and the app Skills that
are not installed as appSkillIssues. GET /:skillId/app-version returns both
versions as SKILL.md plus references, and the app's appVersion.
POST /:skillId/reset takes expectedRevision, expectedAppVersion (that
appVersion, also in each Skill's source), and confirmed: true; it fails
with 409 when the app has published another version since.
POST /apps/:appId/skills/:name/restore installs a deleted app Skill again, and
POST /apps/:appId/skills/:name/adopt links the Skill that already uses the name;
both take confirmed: true. A stale revision or a name that is already in use
fails with 409.
The Skill management Actions are reviewed and recheck the current actor's
Cloud permission. Updates and reference changes require the exact revision
returned by core.ai.skill.read; a stale revision fails instead of overwriting
another edit. Capability-authored instructions and individual references are
limited to 10,000 characters so the complete proposed trusted content fits in
the review. Larger imports and exports remain UI and CLI workflows.
Use personalization for durable user context
Personalization stores fact, preference, or workflow records for exactly
one user. Each entry has a readable id, at most 500 characters, normal or pinned
priority, source, and timestamps. A workflow associates a
reusable request category with one typed Cloud resource reference, such as a
mailbox, notebook, address book, or Space. That reference is a default, not an
authorization token: Assistant must still use the target application's current
capability and permission checks. Manually added facts and preferences start
pinned.
For up to 20 active records, Cloud adds the bounded set directly to the prompt. Above 20 records, Cloud takes pinned records first, then records that share the most words with the message, where words that appear in few of the user's records count more, then the newest records, up to 20 records and 6,000 characters. English and German word forms such as "deployments" and "deployment" or "Farben" and "Farbe" count as the same word. A common word in either English or German is ignored in both, for example German "war" or "man". Only the first and last 6,000 characters of a very long message are considered.
Assistant applies a memory only when it changes the answer. It does not mention or recite memories unless you ask or one is directly relevant. The current message wins over a conflicting memory.
The memory tool can list, search, add, correct, pin, and forget entries without
an approval pause. Memory mutations are personal context maintenance, not domain
Actions. They remain visible and reversible in Assistant settings. The tool
instructions limit entries to information about the user: no facts, opinions, or
health, relationship, or behavior details about other people, even on an
explicit request. A named person may appear only inside a working rule the user
stated, such as "Send invoices to Anna". When the user asks to remember
something about another person, Assistant says what it did not save and offers
Contacts or the Project instead. Special categories (health, religion or
beliefs, political opinions, sexual orientation or sex life, racial or ethnic
origin, trade union membership, and genetic or biometric data) are stored only
on an explicit request to remember exactly that information. The tool must not
store secrets, credentials, raw chat logs, temporary task details, or
instructions from retrieved content.
Automatic learning is on for everyone who has not chosen, and each person can
turn it off or on again in Assistant settings > Personalization or with
cld assistant personalization configure --learning off. Cloud stores a choice only when the person saves that switch; changing
Use personalization alone records nothing for learning, and a stored choice
always wins over the default. After an upgrade, every "off" that an earlier
release stored stays off, because those releases also stored "off" for people
who never chose; see
Deprecations.
Learning considers turns from the user's own chats, Project chats included, that finish while it is on, each once. A turn that finishes while learning is off is never learned from, also not after learning is turned on again, and workflow receipts are recorded only while it is on. Turning learning off stops it right away: the background run reads the setting again just before it sends a turn or workflow pattern to the model and before it saves any change. Learning still needs a working background model and stays within the budgets below.
Archived and deleted chats are never used for learning. Archiving stops pending learning from that chat, including workflow evidence. After restore, learning considers only turns that finish after the chat is restored. A turn or workflow pattern that is already waiting for background model capacity can still reach the model after you archive or delete the chat or turn learning off; Cloud discards that result and saves nothing from it.
Learning does not replay a conversation after later Assistant or tool updates. The bounded input contains the new user-authored text, sanitized receipts for successful Cloud capability calls, the final Assistant Markdown as context only, and a small relevant memory set. Attachments, quoted Cloud resources, raw tool output, agent messages, scheduled messages, and the rest of the Assistant loop are excluded. Facts and preferences require explicit evidence in the user text; model-written text can never establish one by itself.
The learning instructions apply the same limits: they keep only information about the user, never facts, opinions, or health, relationship, or behavior details about other people; a named person may appear only inside a working rule the user stated. They skip the special categories listed above unless the user explicitly asks to remember exactly that information. The learning input states whether the turn comes from a Project chat. In a Project chat, the Project keeps its facts, decisions, and people, and learning keeps only what the user states about themselves beyond it. The workflow-pattern instructions name the recurring category without details about other people or special categories, and return a workflow from Project-chat examples only when it clearly applies beyond that Project. These limits are instructions to the background model, not a content filter; review learned entries in Assistant settings > Personalization.
A single explicit lasting instruction can establish a workflow when the same turn also contains the matching successful typed resource receipt. Otherwise, Cloud waits for three separate successful uses of the same capability and resource, then asks the background model whether the user requests form one clear recurring category. Unrelated uses and uncertain patterns produce no memory. Standard Mail, Contacts, Notebooks, and Spaces capability results include their stable parent resource where the workflow needs one.
Background learning can add, replace, merge, or retire only normal entries that it previously created. User-created, agent-created, and pinned entries are protected. Explicit corrections can replace or retire obsolete background information, and repeated routing to a new resource can replace an older workflow; age alone never deletes a memory because it is not evidence that the information became false. Exact deleted content is not silently recreated. Every candidate, source chat, source message, run, and mutation is checked against the same user id, so another user's turns or memories cannot become learning input or mutation targets.
Each user has a conservative monthly learning budget. Cloud reserves estimated
input plus maximum output before a model call, records actual provider usage
when available, and leaves an unprocessed turn pending for a later budget
window. The operator setting ai.memory_learning_monthly_token_budget defaults
to 100,000 tokens per user per month. Turn inputs and outputs, batch size,
workflow examples, retries, and backoff are independently bounded.
When learning is enabled, Assistant settings > Personalization > Learning activity shows only the current user's paginated runs. The table includes run type, evidence chat, outcome, tokens, duration, and counts for added, updated, merged, or retired entries. Run details show the exact changed content, previous value, and typed Cloud resource where applicable. Failed and no-change runs remain visible; deleted source chats keep their title snapshot but no longer link to the chat.
Instructions for local clients
Administration > AI > Instructions for local clients sets
ai.local_client_instructions. It is plain text, without Liquid. The default
is empty: Cloud uses its shipped local client instructions, which can improve
with each release. Custom text replaces that default completely. Show
built-in text lets an administrator copy it as a starting point.
Interactive turns carrying client get a Local client section directly
after organization instructions. It identifies the terminal or ACP editor,
Cloud URL when configured, workspace, OS, shell and local tools mode, followed
by the custom or shipped text. Its description of what the user sees replaces
the web visibility guidance; other platform rules stay binding. Web and
background turns get no local section.
AGENTS.md files in localContext.instructions become Workspace instructions
after Project instructions, in the supplied order. Each retains its path;
closer files come later and win conflicts. They remain below platform,
organization, Project and the current user message. They grant no approval
and cannot authorize sending data outside the folder or Cloud.
Local Skills join the Cloud catalog with a [local] marker. A local Skill
hides a Cloud Skill with the same name, and both share the 8,000-character /
2% context budget. search_skills also searches omitted local entries and
returns source: "local". Entries with manualOnly: true hide a same-named Cloud
Skill but are not listed to the model. Load marked Skills with load_local_skill,
never load_skill. Explicitly selected local Skills appear alongside server-loaded
Skills with their local directory and instructions; read their reference files
with local_read. Only delegated Skill instructions are instruction-bearing;
reference files remain untrusted data.
Prompt order
Cloud composes the system prompt in this order:
- Platform identity, trusted runtime values including the current chat ID and
request locale, and global rules. Assistant follows the language of the
current user message when it is clear and otherwise uses that locale. It
shows dates and times in the runtime time zone, also in drafts and Skills
it writes, unless the user asks for another zone such as UTC. When the turn
offers
calculate, every amount, sum, or other number the model derives itself must come from it; numbers that a tool, file, or code result returns are stated as returned. With app tools, a reference to earlier work outside the current chat, such as "like last time", goes tocore.ai.chats.searchfirst when the turn allows it. Turns a person follows also get the visibility and suggestion rules below; - Organization instructions, followed by the Local client section for interactive local turns;
- Optional turn-specific instructions such as retry style or one offer hint;
- The bounded readable Skill catalog;
- Project instructions, followed by Workspace instructions for local turns;
- The Project context manifest as untrusted data;
- The bounded conversation file manifest as untrusted data;
- The Recent work summary as untrusted data, only when the user asks what the Assistant can do;
- Relevant personal facts, preferences, and workflow defaults;
- The Cloud resource-link output rule.
See AI resources and access for authorized domain context and Tools and approvals for tool execution boundaries.
What the model knows about the chat
Every turn except a routine run (background in the turn's run
configuration) renders two extra platform sections, controlled by the Liquid
flag interactive. cld assistant turns count as followed turns; the CLI
names each delivered file on standard error, such as
present: completed /sales-report.pdf, so the final message need not list it
there either. The preview in Assistant settings > System prompt and
cld assistant prefs system-prompt shows both sections.
- What the user sees matches the four places per turn: text between tool calls is a live status that folds away, so the model finishes every tool call before its final message, keeps results, warnings, and questions out of status text, and does not list delivered files or visuals again.
- Suggestions allows at most one offer, in the last sentence of the final message. Corrections and recurring requests lead to a Skill, preference, or routine offer, as described in Turn recurring work into a Skill; otherwise the offer is a concrete next step that saves the user real work. The model makes no offer for simple facts, while asking or waiting for approval, after a failure, after a reply that already ended with one, once the user declined, or when the user asked for no suggestions or only a short answer. A request to shorten a draft does not count as that. It never searches data only to justify an offer. Organization, Project, and user instructions about suggestions take precedence. Asked what it can do, the model leads with what the user already works with and leaves out apps without data for them, such as mail without a mailbox. When the server recognizes this question ("What can you do for me?", "Was kannst du für mich tun?"), alone or after a greeting, it adds a Recent work section: the number of the user's other active chats with up to five titles, pinned chats first, and up to eight distinct Cloud items, such as Spaces or notes, that tools used in those other chats. The titles are untrusted data. The section holds only Assistant data: it does not show which apps have data for the user, so the model still checks an unlisted app before featuring it. A question that quotes this one, such as "Translate: What can you do?", or that comes with an attached file does not get the section. Without it the model first looks, where its tools allow it, at the user's Spaces, recent chats, or files.
Routine runs keep the global rules and give their result without these sections. If the platform template fails to render, the minimal fallback prompt still states that only the final message and delivered files stay visible.
Audio attachments
Audio uses the normal conversation file picker and file lifecycle. Uploading a memo does not transcribe it or create a request. The user supplies the task. The shared file preview plays audio when the browser supports its codec.
Cloud offers transcribe_audio and its prompt hint only when an enabled audio
transcription model resolves with the required credentials and permitted data
boundary, and the user has Assistant access to it. The composer microphone
uses the same check. When the conversation contains audio files but
transcription is unavailable, the model receives the reason: no audio model,
no access, a disabled model, or missing credentials. It can tell the user that
an administrator must fix this in AI settings.
transcribe_audio reads a conversation file or an authorized /project file
and uses the configured audio profile. Attached conversation audio comes from
the exact turn snapshot; a missing required snapshot fails the call. The
operation runs inside the existing durable chat turn, without a second job.
The tool writes the full transcript to a call-owned text artifact and returns its path plus a bounded text preview. Replay of an already persisted successful tool result uses that result. A crash before result persistence can repeat the provider call; it cannot overwrite another call's artifact or a file edited since creation. Artifact collisions fail explicitly.
See Models and providers for container and provider limits. Normal file storage limits do not imply that an audio endpoint accepts the same input size.
Explicit file transfers
Assistant file references use the public AiFileLocation and AiFileReference
schemas from @k2b/cloud/ai: {scope:"chat"|"project"|"app",id,path} plus an
opaque string version. A reference names one snapshot; it grants no access.
Each owning service authorizes reads and writes, and the destination enforces
its normal byte budgets and an explicit expected version (null means absent).
Platform-owned conversation adapters are readAiConversationFile and
writeAiConversationFile. Reads require the current owner and reject archived
chats; an optional numeric file version constrains an existing manifest read.
Writes require an opaque transfer version and verify the owner and expected
content under the conversation lock before replacing a file. The returned
metadata is captured in that transaction. Project writes accept an optional
expectedVersion and serialize permission and version checks with other Project
file mutations. Existing UI callers retain their existing write behavior.
Studio owns App file storage and its transfer adapter. File imports into App
source use code_import with fromFile references in the same schema. One fresh
review covers the whole batch, since imported private bytes may become shared
or published source. Write source text with code_write using top-level path
and content, one file per call. Keep binary bytes out of tool responses and
never treat access to one chat as permission to mount all of its files into an
App.
Visual inspection of PDF pages
view_image accepts stored images and PDFs through the same authorized chat or
Project file adapter. PDF pages are one-based and distinct, default [1],
with at most three pages per call. Image calls reject pages and retain their
existing result. PDF results add sourceVersion (a hash of inspected bytes),
totalPages and pages: [{page, description}]; descriptions cover selected
pages only. Attached chat files use the immutable turn snapshot.
PDF page inspection requires the Linux Cloud runtime; other hosts reject PDF
rendering rather than run it without the memory boundary. Image inspection is
unchanged. Rendering runs in an isolated, credential-free subprocess, terminated on
cancellation or a 30-second deadline. On Linux, a 512 MiB kernel data-memory limit also bounds the decoder's heap and
native writable allocations. The decoder runs a fixed set of runtime threads, so
this limit holds regardless of how many CPU cores the host or container exposes.
Each service permits two concurrent
decoders and rejects overload without queuing. Input and aggregate PNG output
are each limited to 10 MiB; page canvases have a 2,000-pixel longest edge and
maximum 2× scale, while embedded images are limited to 16 megapixels. Damaged,
password-protected or oversized content fails explicitly rather than silently
omitting it. The normal Vision model, fallback data boundaries and usage
attribution apply. No persistent image copies are created. For normal PDF text
extraction, read_file remains the simpler path.
The standard Cloud build packages the PDF decoder, native canvas binary and font/CMap/WASM assets when the server imports this tool. Build on the target platform; no document-rendering service or browser installation is required.
Versioned file writes and generated-file exports distinguish known rejections
with AiFileWriteError: CONFLICT for an occupied export destination and
STORAGE_FULL for byte budgets. These errors retain a human-readable message and
reject the destination write. AiFileVersionConflict still identifies a stale
expected file version.