Publish HTML to yourweb
Host a single self-contained HTML file on yourweb and get a public, full-screen URL. The REST API lets an agent publish a page, then list, fetch, update, and delete the pages it owns.
Two domains, by design:
yourwebs.cc— the dashboard and the REST API (https://yourwebs.cc/api/v1).yourwebs.app— where published pages are served. A page with subdomainmy-pageis served athttps://my-page.yourwebs.app.
Authentication
Every call except anonymous publish needs a bearer token (ywb_...), generated by
the user in the yourweb dashboard.
Read the token from the YOURWEBS_API_TOKEN environment variable. Never hardcode
it, never write it into a file, never echo it back.
If YOURWEBS_API_TOKEN is unset, stop and ask the user to set it:
export YOURWEBS_API_TOKEN="ywb_..." # get it from the yourweb dashboard
Only if the user explicitly prefers to paste the token inline, use it for this
session — and warn them it will appear in the chat transcript, so the env var is
preferred. If a project keeps it in a .env file, make sure .env is gitignored.
Publish a page (the main task)
- Write a single, self-contained HTML file (inline CSS/JS, no external build).
It must be UTF-8, contain
<!doctype html>or<html>, and be ≤ 1 MB. - Wrap it in a JSON body and POST it. Use
jqto build the JSON so the HTML is escaped correctly — never hand-concatenate HTML into a JSON string. - Return the
urlfrom the response to the user.
# index.html holds your self-contained page
jq -n --rawfile html index.html \
'{html: $html, title: "My Page", subdomain: "my-page"}' \
| curl -sS -X POST https://yourwebs.cc/api/v1/pages \
-H "Authorization: Bearer $YOURWEBS_API_TOKEN" \
-H "Content-Type: application/json" \
--data-binary @-
Response (HTTP 201) is a page object — hand url back to the user:
{ "id": "01J0...", "subdomain": "my-page", "url": "https://my-page.yourwebs.app",
"title": "My Page", "size_bytes": 4096, "total_views": 0, "status": "active",
"created_at": 1747900800000, "updated_at": 1747900800000 }
title and subdomain are optional. The page is served at
https://<subdomain>.yourwebs.app. subdomain only takes effect with a token
(anonymous publishes get a random subdomain) and must be 3–32 chars, lowercase
a-z 0-9 -, no leading/trailing or doubled hyphen, not a reserved word. Omit it to
get a random subdomain.
Manage existing pages
All of these require the token.
# List your pages -> { "pages": [ ... ] }
curl -sS https://yourwebs.cc/api/v1/pages \
-H "Authorization: Bearer $YOURWEBS_API_TOKEN"
# Get one page
curl -sS https://yourwebs.cc/api/v1/pages/PAGE_ID \
-H "Authorization: Bearer $YOURWEBS_API_TOKEN"
# Replace a page's HTML (body: { html })
jq -n --rawfile html index.html '{html: $html}' \
| curl -sS -X PUT https://yourwebs.cc/api/v1/pages/PAGE_ID \
-H "Authorization: Bearer $YOURWEBS_API_TOKEN" \
-H "Content-Type: application/json" --data-binary @-
# Delete a page -> { "deleted": true }
curl -sS -X DELETE https://yourwebs.cc/api/v1/pages/PAGE_ID \
-H "Authorization: Bearer $YOURWEBS_API_TOKEN"
Quick reference
| Method | Path | Body | Token | Success |
|---|---|---|---|---|
| POST | /pages |
{ html, title?, subdomain? } |
optional | 201 page |
| GET | /pages |
— | required | 200 { pages: [...] } |
| GET | /pages/:id |
— | required | 200 page |
| PUT | /pages/:id |
{ html } |
required | 200 page |
| DELETE | /pages/:id |
— | required | 200 { deleted: true } |
Constraints & errors
- HTML: UTF-8, contains
<!doctype html>/<html>, ≤ 1 MB (the raw HTML byte size, matchingsize_bytes, not the JSON body). Else400 invalid_html— fix the HTML, don't retry unchanged. 400 subdomain_invalid: the subdomain breaks the format rules — fix it, don't blindly retry.409 subdomain_taken: it's valid but in use — pick another or omit.- Rate limits: 30 publishes/hour, 60 updates/hour. On
429 rate_limited, wait and retry later rather than hammering — the window is hourly. - Errors are
{ "error": { "code": "...", "message": "..." } }. Common codes:bad_request(400),invalid_html(400),subdomain_invalid(400),unauthorized/invalid_token(401),not_found(404),subdomain_taken(409),rate_limited(429),no_subdomain_available(503). - Anonymous pages (no token) auto-delete after 30 days and can't be claimed later; publish with a token for anything you want to keep.
Full contract: see reference/api.md.