> ## Documentation Index
> Fetch the complete documentation index at: https://docs.doconda.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Artifacts

> One more format: a web page that stores data (a poll, a team list, a calculator).

An **artifact** is a document with `format: "artifact"`: instead of a Word file or a PDF, Doconda delivers a web page that
stores data. What it stores persists between visits.

It is created, listed, tracked and billed like any other document. It is private to your project: you decide who gets
the link (for example, inside your product, in an `iframe`).

## Create one

With a sentence, and Doconda writes the page:

```bash theme={null}
curl https://api.eu.doconda.com/v1/documents \
  -H "Authorization: Bearer $DOCONDA_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "format": "artifact", "prompt": "A poll to choose the Friday menu, with live results" }'
```

Or with your content in Markdown, and Doconda turns it into the page (keeping your text):

```json theme={null}
{ "format": "artifact", "content": { "markdown": "# Friday menu\n\nVote for:\n- Paella\n- Pizza\n- Sushi" }, "style": "warm colors, big buttons" }
```

It costs like any created document, by its [quality level](/en/guides/create#quality-levels).

How it's made: first a short design plan (what it's for, sections, colours and fonts, interaction) that checks what the
page can do: store in `doconda.db` and use Tailwind, Chart.js, d3 or dayjs, nothing else (no external APIs, email,
payments or sign-in; if you ask for them, it proposes how to solve it inside the page). Then it writes a single HTML
with everything inside (pictures too), looks at it on desktop and phone and fixes what looks wrong: once at `fast` and
`standard`, twice at `best`. The `artifact.planned` event carries the plan.

All three [modes](/en/guides/modes) work: direct, `stream` and `background`. The [style](/en/guides/style), in your own words,
describes how the page looks. An artifact takes no `sources`.

## Where it stores its data

You pick one of two modes with `artifact.storage`:

| | `shared` (default) | `local` |
| - | - | - |
| Who sees the data | Everyone who opens the link sees the same | Each visitor sees only their own |
| Where it is stored | In Doconda | In each person's browser (it never leaves it) |
| For | Polls, team lists, sign-ups, dashboards | Calculators, drafts, personal lists |
| Your program can read it | Yes (`GET /documents/{id}/data`) | No: Doconda never receives it |

```json theme={null}
{ "format": "artifact", "prompt": "A mortgage calculator that remembers my simulations", "artifact": { "storage": "local" } }
```

The page is the same in both modes: it uses `doconda.db` and Doconda decides where to store.

## The link

When it is ready, `outputs` includes an `html` whose `url` is the page. That link expires in 1 hour; ask for another one
with the duration you need (up to 7 days):

```bash theme={null}
curl "https://api.eu.doconda.com/v1/documents/doc_…/outputs?expires_in=86400" \
  -H "Authorization: Bearer $DOCONDA_API_KEY"
```

```html theme={null}
<iframe src="ARTIFACT_URL" sandbox="allow-scripts allow-same-origin allow-forms" style="width:100%;height:600px;border:0"></iframe>
```

Each artifact is served on its own subdomain, isolated from your website, from Doconda and from other artifacts
(`allow-same-origin` refers to that subdomain, which is its own).

<Warning>Anyone with the link can see the page (and, in `shared`, save data to it) until it expires. Give it only to those who should use it.</Warning>

## Save data from the page

Doconda adds `window.doconda.db` to the page. It stores JSON by **collection** and **key**:

```js theme={null}
await doconda.db.set("votes", crypto.randomUUID(), { option: "A" }) // creates or replaces
await doconda.db.get("votes", "abc")        // → the data, or null
await doconda.db.list("votes")              // → [{ key, data, updated_at }], most recent first
await doconda.db.delete("votes", "abc")

// Right away and every time someone changes something (other people too):
const stop = doconda.db.subscribe("votes", (votes) => render(votes))
```

* Collection and key names: letters, numbers, `_`, `-` or `.` (up to 64).
* Each record, up to 16 KB of JSON; each artifact, up to 5,000 records.
* Per artifact and minute: up to 1,200 reads and 120 writes. Above that, `429 rate_limited`.
* The page opens isolated: it has no cookies or `localStorage`, and it cannot read anything from your website or Doconda.
  To save, use `doconda.db`.

## Read the data from your program

```bash theme={null}
curl https://api.eu.doconda.com/v1/documents/doc_…/data \
  -H "Authorization: Bearer $DOCONDA_API_KEY"
# { "data": [{ "collection": "votes", "records": 42 }] }

curl https://api.eu.doconda.com/v1/documents/doc_…/data/votes \
  -H "Authorization: Bearer $DOCONDA_API_KEY"
```

## Projects that don't store content

If the project has storage turned off (or the request has `store: false`), an artifact can only be
`local`, and Doconda doesn't host it: it is delivered as an **`artifact.html`** file for you to upload to your website (we
delete it after 15 minutes). Its data stays in each visitor's browser.

## Region

An artifact lives in its project's region, like any other document: its page and its data never leave it.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.