Publish a webpage to a live URL, straight from your AI.

Yapp turns "build me a page and publish it" into a live URL.

Community: Submitted by a user or imported; check the owner before granting accessOnlineNo sign-inGlobalFreeCan modify data

What it can do

  • Publish Page: Publish an HTML web page to yapp.page and get a live shareable URL. (To host an existing PDF, image, or ZIP file AS-IS — like a manual upload — use `publish_file` instead; do NOT convert
  • Publish File: Publish a FILE as-is to yapp.page — a PDF, image, or ZIP — and get a live shareable URL. This hosts the REAL file exactly like uploading it in the browser: a PDF gets a clean PDF viewer
  • List My Pages: List all pages owned by the current authenticated user. Returns each page with id (slug), name, url, views, expiresAt, hasForm, submission count, and demo flag. Use this when the user a

What data it sees

Do you need an account

No: the server works without sign-in

Yapp turns "build me a page and publish it" into a live URL. Connect once (browser OAuth, or a token for terminal clients) and your AI can publish a webpage from HTML, or host a PDF, image, or ZIP exactly as-is to a public .yapp.page URL in seconds, then update, password-protect, set expiry, attach a custom domain, or read form submissions, all by asking. Free to start; no local install.

Tools (15): publish_page, publish_file, update_page, delete_page, get_page_stats, list_my_pages, rename_page, change_page_slug, set_page_expiry, set_page_password, list_submissions, add_custom_domain, list_custom_domains, check_custom_domain, remove_custom_domain.

Server tool list (15)

Raw names from tools/list. Only developers need these.

publish_pagePublish an HTML web page to yapp.page and get a live shareable URL. (To host an existing PDF, image, or ZIP file AS-IS — like a manual upload — use `publish_file` instead; do NOT convert a PDF into HTML.) LARGE FILES: if the HTML document is big (roughly >100 KB, or it contains a long minified array/blob), DO NOT paste it inline as `html` — it will be truncated/corrupted because the content has to be reproduced as model output. Instead host the file at a public https URL and pass `htmlUrl` — yapp downloads the document itself, byte-for-byte. Use `html` only for small pages. ATTACHED / UN-EMBEDDABLE FILES: if the user attached a file (or it is too large to reproduce) and you do NOT have a public URL for it, call publish_page with NO `html` and NO `htmlUrl`. You get back an `uploadUrl` — share it with the user so they drop the file in their browser. This is the reliable path for any file you cannot pass inline. BUNDLING ASSETS (images, CSS, JS, fonts): pass `assets` — an array where each entry has a `name` (the relative filename inside the page) plus either `base64` (raw bytes of the file) OR `url` (yapp.page will fetch and bundle for you). Reference each asset from your HTML by its `name`. EXAMPLES # Single HTML page publish_page({ html: "<h1>Hello</h1>" }) # Page with one inline image (you have the bytes) publish_page({ html: '<h1>Hi</h1><img src="hero.jpg">', assets: [{ name: "hero.jpg", base64: "<base64 bytes of the JPG>" }] }) # Page with multiple images + a stylesheet (relative paths preserved) publish_page({ html: '<link rel="stylesheet" href="style.css"><img src="img/logo.png"><img src="img/hero.jpg">', assets: [ { name: "style.css", base64: "..." }, { name: "img/logo.png", base64: "..." }, { name: "img/hero.jpg", base64: "..." } ] }) # Page that uses an image already hosted somewhere — yapp will fetch it publish_page({ html: '<img src="hero.jpg" style="width:100%">', assets: [{ name: "hero.jpg", url: "https://picsum.photos/seed/y/1200/800" }] }) Each asset name must be a safe relative path (letters/digits/dot/dash/underscore/slash, no ".."). FORMS — IMPORTANT: yapp.page auto-captures any `<form>` in your HTML. You DO NOT need Formspree, Netlify Forms, or any external service. Just write a normal HTML form: <form> <input name="email" type="email" required> <textarea name="message"></textarea> <button>Send</button> </form> No `action` attribute needed. yapp.page intercepts the submission, stores it in the database, and the owner sees submissions at /messages/<page-id> in their dashboard. Field names you choose become JSON keys. Max 16 KB per submission. Use the `list_submissions` tool later to read entries. OWNERSHIP: Pages you publish via MCP are owned by your account — you can `update_page`, `delete_page`, and `list_submissions` for them without an editKey.
publish_filePublish a FILE as-is to yapp.page — a PDF, image, or ZIP — and get a live shareable URL. This hosts the REAL file exactly like uploading it in the browser: a PDF gets a clean PDF viewer (with a download button), an image gets an image viewer, and a ZIP becomes a hosted website (if it contains index.html) or a download page. Use this whenever the user gives you an EXISTING file to host — do NOT rebuild a PDF as HTML; publish the actual file. Provide the file ONE of two ways: • `fileUrl` — a public https URL to the file. yapp downloads it byte-for-byte (reliable for any size). • `fileBase64` + `filename` — the raw bytes base64-encoded, for small/medium files you already have. (Large files become unreliable as model output — prefer `fileUrl`.) If you have NEITHER (e.g. a large chat attachment with no URL), call publish_file with no `fileUrl`/`fileBase64` to get a one-time browser upload link to share with the user. Supported: .pdf, .zip, and images (.png .jpg .jpeg .gif .webp .avif). The filename extension decides how the file is hosted. To build a web PAGE from HTML you write, use `publish_page` instead. OWNERSHIP: files you publish are owned by your account — update/delete them like any page.
list_my_pagesList all pages owned by the current authenticated user. Returns each page with id (slug), name, url, views, expiresAt, hasForm, submission count, and demo flag. Use this when the user asks "what pages do I have", "show me my pages", or to find a page id when they refer to one by name.
update_pageReplace the entire HTML content of a published page, keeping the same URL. This overwrites the existing content (the previous version is not recoverable), so confirm with the user before overwriting. Only the page owner can call this without an editKey.
rename_pageChange the friendly display name of a page (what shows in dashboards). Does NOT change the URL — use `change_page_slug` for that. Safe and reversible (just call again to set a new name).
change_page_slugChange a page's URL slug. The page moves from <old-id>.<apex> to <new-slug>.<apex>, and the old URL stops working (anyone who has it gets a 404). Confirm with the user before changing it, and share the new URL afterward. To change only the display name without affecting the URL, use `rename_page` instead.
set_page_expiryChange when a page auto-deletes. Pass `days` (e.g. 7, 30, 90) for relative expiry, or `forever` to disable auto-delete entirely. If shortening the expiry significantly (e.g. from "forever" to "1 day"), confirm with the user first — the page will delete sooner than they may expect.
set_page_passwordAdd, change, or remove a view password on an existing page — at any time, not just at publish. Pass `password` to require visitors to enter it before they can view the page; pass `remove: true` to take the page public again. Changing the password immediately logs out anyone who unlocked it with the old one. Note: this is a single shared password (good for casual gating, staging previews, soft-launches), not per-visitor accounts. Password protection requires the Pro plan. Only the page owner can call this without an editKey.
delete_pagePermanently delete a published page. The URL stops working and any form submissions are removed; this cannot be undone, so always confirm with the user first. If they are unsure, suggest `set_page_expiry { days: 1 }` instead, which lets the page expire naturally.
get_page_statsGet views, daily traffic, referrers and expiry info for a published page.
list_submissionsRead form submissions captured from a published page. yapp.page auto-captures any `<form>` on a page (no action attribute needed) and stores submissions in the database, ordered newest first. Use this to retrieve email signups, contact form entries, RSVPs, etc. Only the page owner (you, when publishing via MCP) and admins can read submissions. Returns up to `limit` entries (default 50, max 200).
add_custom_domainAttach a custom domain (e.g. example.com) to a published page. Pro / Team plans only. Either the bare apex or the www form is accepted — we always store the www form, and the apex is handled implicitly by a redirector (visitors typing example.com get 301-redirected to https://www.example.com). Returns the two DNS records the user must add at their registrar (one CNAME for www, one A record for the apex). After they paste those records, call `check_custom_domain` to poll status until `ssl_status` becomes "active" (usually a few minutes).
list_custom_domainsList all custom domains attached to pages you own. Returns hostname, status, SSL status, the page id each domain points to, and the DNS records needed (still useful after the fact in case the user needs to migrate registrars).
check_custom_domainForce a fresh poll of a custom domain's status with Cloudflare. Use this after the user has added the DNS records to confirm propagation + cert issuance. Status progresses: pending → dns_verified → ssl_active. Returns updated status fields.
remove_custom_domainDetach a custom domain from its page. The www hostname stops serving the page and the apex redirect stops responding for it. The user's DNS records become harmless orphans they can leave or remove. Confirm with the user before detaching.