Prompt fragments
A prompt fragment is a block of instructions saved once in your workspace that any of your agents can use. An agent carries one line that names the fragment and reads the fragment's current text in its place, so change the fragment and every agent that uses it reads the new text from its next run.
What a fragment is
An agent’s instructions are what you write in What should it do? when you create it. A fragment
is a named part of those instructions that lives in your workspace instead of inside one agent: a
house style, a risk checklist, the way every report should be laid out. An agent uses a fragment
through one line in its instructions, such as {{include "tenant/house-style"}}.
Before any run starts, that line has already been replaced by the fragment’s text, word for word.
With this fragment, named house-style:
## House style
Lead with the decision, then why. these instructions:
Summarize the portfolio each morning.
{{include "tenant/house-style"}} reach the agent as:
Summarize the portfolio each morning.
## House style
Lead with the decision, then why. So a fragment is linked, not copied. The agent keeps the line, not the text:
- Change the fragment, and every agent that uses it reads the new text from its next run. A run that’s already going keeps the text it started with.
- While any agent uses a fragment, it can’t be deleted.
Built-in fragments and your own
Built-in fragments are written and kept up to date by Spooky Labs. Every workspace has the same two:
- Working with other agents,
platform/a2a-communication: how handing a run to another agent works. The other agent takes over the rest of the run, and nothing comes back to the agent that handed it over. Only useful for agents that hand work to others. - Using skills,
platform/skills-usage: tells the agent to check its skills at the start of every run and follow the one that fits to the end. Only useful for agents that have skills.
You can add a built-in fragment to any agent and read its exact text with Preview, but you can’t
edit or delete it. To change one, use Make a copy: it opens the text as a new fragment of your
own, named like skills-usage-copy, and agents that use the built-in keep using it. When Spooky Labs
updates a built-in fragment, the agents that use it read the new text from their next run, just as
they do when you edit one of yours.
Your fragments are saved in your workspace, and any of its agents can use them. Their paths
start with tenant/. In the Prompt fragments row:
- New fragment opens an editor for a name and the text.
- Upload a file fills the same editor from one
.mdor.txtfile. Nothing is saved until you save it, so you can read and change the text first. - Each of your fragments has Edit…, Make a copy and Delete… in its More actions menu.
Before you save a change to a fragment that agents use, the editor names those agents.
Add a fragment to an agent
On New agent, open the Prompt fragments row. The help text under What should it do? links to it, and the row’s value says how many fragments the instructions add: None, 1 in use, and so on. Each fragment shows its path, its size and how many agents use it, and Preview shows its exact text and about how many tokens it adds.
Add puts the fragment’s line at the end of What should it do?, as a paragraph of its own, and Remove takes it out again. You can move the line anywhere in the instructions: the text appears wherever the line is. You can also type a line yourself. The console checks fragment lines as you type and won’t create the agent while one names a fragment that doesn’t exist, and the platform refuses it too.
A fragment line works only in What should it do?. In a schedule’s Prompt for each run it is sent to the agent exactly as typed, and the console warns you when you type one there.
The console can’t change an agent’s instructions after the agent is created, but you can change a fragment’s text at any time. So put anything you may want to change later in a fragment of your own.
When a change takes effect
When you save a fragment, every agent that uses it reads the new text from its next run: the next time one of its schedules comes due, you choose Run now, or a wake it booked for itself comes due. Each of those agents first has an update prepared, which usually takes a few seconds, and a run that starts before then still uses the previous text. A run that’s already going keeps the text it started with.
Deleting a fragment
A fragment can’t be deleted while any agent uses it, because an agent whose fragment is missing can’t take any further update: it would keep running on the text it last had. Delete… on a fragment in use names those agents instead of deleting it, and the platform refuses the delete whichever client asks. An agent that is being deleted doesn’t count.
- To change what those agents read, edit the fragment.
- To stop using it, delete those agents first. The console can’t take the line out of an existing agent’s instructions.
A fragment no agent uses is deleted once you confirm, and that can’t be undone. Built-in fragments can’t be deleted.
Limits
| What | Limit |
|---|---|
| One fragment’s text | Up to 8 KB, and not empty |
| All your fragments together | Up to 32 KB, counting each name as well as its text |
| Built-in fragments | Count toward neither limit |
| A name | Letters, numbers, dashes (-), underscores (_) and dots (.), up to 253 characters. It can’t be . or start with .. |
| An upload | One .md or .txt file at a time, 8 KB or smaller |
Sizes are in bytes, and 1 KB is 1,024 bytes. Most English letters take one byte each; accented
letters and symbols such as € take two or three. The Prompt fragments row shows how much of
the 32 KB you’ve used.
A name can’t be changed once it’s saved. To rename a fragment, make a copy with the new name, then delete the old one once no agent uses it. When you upload a file, its name without the extension becomes the fragment’s name, with spaces and other characters changed to dashes, and you can change it before you save.
Writing a fragment
Write a fragment the way you write instructions: plain text or Markdown, addressed to the agent. The agent reads it exactly as written.
- Leave out passwords and API keys. Nothing filters them out, and the text is sent to the model on every run.
- Write placeholders with angle brackets, like
<ticker>, not curly braces.
Curly braces need care. A single word in them is reserved for values filled in at run time, and Spooky Labs fills in none, so the console and the platform refuse these, in a fragment and in an agent’s instructions:
| You wrote | Why it’s refused |
|---|---|
{ticker}, {{ticker}}, { ticker } or {user:ticker} | A single word in curly braces would make every run of an agent that reads it fail |
{ticker?} | It would be removed before the agent reads it |
{artifact.notes} | It asks for a file agents can’t load, so every run would fail |
Write <ticker> instead, or reword it. Curly braces around anything that isn’t a single word are
fine: JSON such as {"action": "buy"} and formats such as {price:.2f} reach the agent as written.
Inside a fragment, nothing in double curly braces is filled in. A fragment can’t add another fragment
or fill in values, so {{include "tenant/other"}} or {{.Description}} inside a fragment reaches
the agent as those characters. Only an agent’s own instructions can add fragments and use the template
values described in How it works.
What it costs
A fragment’s text is part of the instructions of every agent that uses it, and the instructions are sent to the model with every model call, not once per run: a run calls the model at each step, including after every tool call. So a fragment adds its tokens to every model call of every agent that uses it, billed as input tokens like the rest of the instructions; see How you are billed. A token is about four characters of English text, so a full 8 KB fragment is about 2,000 tokens on every call. Preview shows each fragment’s estimate, and the create page’s token estimate for the instructions includes the text of the fragments they add.
How it works
Agents on Spooky Labs run on kagent, an open-source framework for running AI agents on Kubernetes. Fragments are built on kagent’s prompt templates, which Spooky Labs sets up for you, so you never write the template configuration yourself.
Where fragments live
Your workspace’s Kubernetes namespace holds two fragment libraries: platform, the built-ins, which
Spooky Labs rewrites whenever it sets up or repairs the workspace, and tenant, your own. A
fragment’s path is its library and its name.
When the text is spliced in
When an agent is created, Spooky Labs finds every fragment line in its instructions, checks that each names a fragment that exists, and fills in the template once to check it, the same way kagent will. Instructions that add no fragment get no template at all: nothing in them is filled in.
kagent then compiles the agent into a revision, a fixed snapshot of everything the agent runs with, and splices in each fragment’s current text at that point, word for word. Every run starts from the agent’s latest revision that compiled. kagent watches both libraries, so saving or deleting any of your fragments compiles a new revision of every agent that adds any of your fragments, even one whose text didn’t change; runs keep starting from the previous revision until the new one is ready. A fragment that’s missing stops the compile, and the agent stays on its last revision with the old text, which is why a fragment in use can’t be deleted.
Template values
When the instructions add at least one fragment, kagent treats them as a Go template and fills in four values:
{{.AgentTemplateName}}: the agent’s name, such asmarket-watcher.{{.AgentTemplateNamespace}}: an internal id for your workspace,tenant-and 20 hexadecimal characters, not its name.{{.Description}}: the agent’s description, or nothing when it has none.{{.ToolNames}}: the tools the agent calls through its MCP servers, which are its scheduling tools, plus its trading tools when it has markets.
{{.ToolNames}} is written in Go’s list format, not as a comma-separated list. For an agent with no
markets it becomes:
[schedule_wake list_wakes cancel_wake] The values work only in an agent’s own instructions, never inside a fragment, and only when those
instructions add a fragment; without one, they stay exactly as typed. In instructions that add a
fragment, any other value, such as {{.AgentName}} or {{.SkillNames}} from earlier kagent
versions, is refused when you create the agent, because kagent 1.0 doesn’t have it and the agent
would never start. If the instructions use {{.Description}}, the description has to follow the
curly-brace rules too, because it becomes part of the instructions. Template actions such as {{if}} and {{range}} can’t be used: the {{end}} that closes them is a single word in curly
braces.
Curly braces at run time
The agent runtime, Google’s Agent Development Kit for Go, reads the compiled
instructions again before every model call and treats a single word in curly braces as a value to
look up in the run’s session state. A value that isn’t there fails the run, and a trailing ? makes
it silently disappear instead. Agents here have no session state you can set, so Spooky Labs refuses
those braces when it saves instructions and fragments, and checks the instructions again once their
fragments and values are filled in.