API pipeline: Create and edit your project page
Index: API pipelines — index
Goal: create your project page and keep it current: text, place, photos, contacts, translations and who can see it.
Steps
- Create.
POST /v0/my/projects
Idempotency-Key: proj-bikes-1
{"title": "Bike repair in Lisbon", "content": "What I offer, prices, hours…",
"language": "en", "handle": "example-bikes",
"rubrics": ["<rubric nonce>"], "location": "<place nonce>",
"translate_mode": "auto"}
→ {"nonce": "470000000000000001", "card_type": "project", "visibility": "Private", "handle": "example-bikes", …}
titlerequired;languagedefaults toen(en,ru,es).handle: a-z, 0-9,_ . -, up to 64 characters, unique; the page is thenhttps://cabi.chat/@example-bikes.rubrics: topic rubric nonces;location: one place nonce (city, region or country). Finding them: API pipeline: Search the graph, API pipeline: Find projects by place and on the map.translate_mode:auto(machine translation) orllm(through your translation agenda; its cost shows in your AI spend: API pipeline: See your AI spend);translate_langslimits the target languages. Translations arrive a little later.- A new project is always Private.
- Photos. Upload, then attach:
POST /v0/my/media/upload (multipart/form-data, up to 10 images, 10 MB each)
→ {"files": [{"hash": "<sha256>", "format": "webp", "width": 1200, "height": 800, …}]}
PATCH /v0/my/projects/470000000000000001
{"avatar": "media:<sha256>.webp", "media_add": ["media:<sha256>.webp"]}
media replaces the whole gallery (ordered, up to 20; [] clears it); media_add appends; avatar sets the round picture. Keep images out of content.
- Contacts.
POST /v0/my/projects/470000000000000001/contacts
Idempotency-Key: proj-bikes-contact-1
{"kind": "Telegram", "value": "@example", "is_primary": true,
"publicity": "Everyone", "requires_reveal": true}
→ {"nonce": "470000000000000011", "kind": "Telegram", "value": "@example", …}
kind: Phone, Email, Website, Telegram, WhatsApp, Instagram, Facebook, TikTok, LinkedIn, Discord, X, YouTube, Other.publicity:Ecosystem(default, signed-in people only) orEveryone.requires_reveal: truehides the value until a visitor asks for it: API pipeline: Reveal a project's contact- One primary contact: setting
is_primaryclears it on the others. - List:
GET /v0/my/projects/{nonce}/contacts; edit:PATCH /v0/my/contacts/{nonce}; remove:DELETE /v0/my/contacts/{nonce}.
Edit text, place, rubrics:
PATCH /v0/my/projects/{nonce}with any oftitle,content,language(which language you are writing),handle,rubrics,location,canonical_lang(the original language),translate_mode+translate_langs. Fields you leave out stay as they are.Publish.
PATCH /v0/my/projects/470000000000000001
{"visibility": "Public", "publicity": "Everyone",
"permissions": {"read": true, "write": false, "execute": false}}
visibility:Public(listed: landing, search, map),Unlisted(only people you share it with by a link or grant) orPrivate(only you).publicity(required for Public):Everyone(anyone, also signed out) orEcosystem(signed-in people only).permissions(required with Public or Unlisted): what the audience may do —read;writeonly on Unlisted; neverexecuteon a Public project.
- Check it:
GET /v0/graph/projects/{nonce | @handle}shows the page as others see it;GET /v0/my/projects/{nonce}as its owner.
Behind
- Lowering a project's visibility also lowers the cards anchored to it: Private makes them Private, Unlisted makes Public ones Unlisted.
- Version history, if you switch it on: API pipeline: Keep a card's version history. Archive or delete: API pipeline: Archive, restore or delete your cards.
Rules
- 400
title is required;handle may contain only a-z, 0-9, _ . -;handle is too long (max 64). - 400
Public visibility requires explicit publicity,Public/Unlisted visibility requires explicit permissions,Public cards cannot grant write,Public projects cannot grant execute; share x by grants or links,Private cards carry no permissions. - 400
media: at most 20 items,media_add: the gallery would have N photos, at most 20; …,avatar must be a media:<sha256>.<ext> ref …; upload:no image files in upload,at most 10 files per upload. - 400
unknown contact kind: …,publicity must be Everyone or Ecosystem, got …. - 400 without
Idempotency-Keyon the two creates.
API surface
| Endpoint | Purpose | FE | AI / oracle |
|---|---|---|---|
POST /v0/my/projects |
Create (Private) | yes | yes |
PATCH /v0/my/projects/{nonce} |
Edit text, place, photos, visibility | yes | yes |
GET /v0/my/projects, /v0/my/projects/{nonce} |
Your projects | yes | yes |
POST /v0/my/media/upload |
Upload images | yes | yes |
POST / GET /v0/my/projects/{ident}/contacts |
Add / list contacts | yes | yes |
PATCH / DELETE /v0/my/contacts/{nonce} |
Edit / remove a contact | yes | yes |
GET /v0/graph/projects/{ident} |
The public page | yes | yes |