brewpage-mcp 1.10.0 → 1.12.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -15
- package/dist/index.js +52 -38
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -7,12 +7,12 @@ MCP server for [BrewPage](https://brewpage.app) -- publish and manage HTML, KV,
|
|
|
7
7
|
|
|
8
8
|
## What is BrewPage
|
|
9
9
|
|
|
10
|
-
[BrewPage](https://brewpage.app) is a free instant hosting platform designed for AI agents and developers. One `POST` request publishes HTML, Markdown, a multi-file site, a JSON document, or a binary file and returns its primary HTTPS link -- no accounts, no API keys, no infrastructure setup. Every resource carries an **owner token** returned at creation time: use it to update content in place, delete the resource, or authenticate list operations across sessions. `brewpage-mcp` exposes this API as
|
|
10
|
+
[BrewPage](https://brewpage.app) is a free instant hosting platform designed for AI agents and developers. One `POST` request publishes HTML, Markdown, a multi-file site, a JSON document, or a binary file and returns its primary HTTPS link -- no accounts, no API keys, no infrastructure setup. Every resource carries an **owner token** returned at creation time: use it to update content in place, delete the resource, or authenticate list operations across sessions. `brewpage-mcp` exposes this API as seventeen typed MCP tools so any compatible agent -- Claude, Codex, Gemini, Cursor, Cline -- can publish, update, fetch, and manage BrewPage HTML, JSON, KV, and file content without leaving the conversation.
|
|
11
11
|
|
|
12
12
|
## Quick Start
|
|
13
13
|
|
|
14
14
|
```bash
|
|
15
|
-
npx -y brewpage-mcp@1.
|
|
15
|
+
npx -y brewpage-mcp@1.12.0
|
|
16
16
|
```
|
|
17
17
|
|
|
18
18
|
Requires Node.js 20 or newer. This starts the stdio server for an MCP client.
|
|
@@ -28,7 +28,7 @@ Add to `~/Library/Application Support/Claude/claude_desktop_config.json` (macOS)
|
|
|
28
28
|
"mcpServers": {
|
|
29
29
|
"brewpage": {
|
|
30
30
|
"command": "npx",
|
|
31
|
-
"args": ["-y", "brewpage-mcp@1.
|
|
31
|
+
"args": ["-y", "brewpage-mcp@1.12.0"]
|
|
32
32
|
}
|
|
33
33
|
}
|
|
34
34
|
}
|
|
@@ -39,7 +39,7 @@ Add to `~/Library/Application Support/Claude/claude_desktop_config.json` (macOS)
|
|
|
39
39
|
Register a project-scoped stdio server:
|
|
40
40
|
|
|
41
41
|
```bash
|
|
42
|
-
claude mcp add --transport stdio --scope project brewpage -- npx -y brewpage-mcp@1.
|
|
42
|
+
claude mcp add --transport stdio --scope project brewpage -- npx -y brewpage-mcp@1.12.0
|
|
43
43
|
```
|
|
44
44
|
|
|
45
45
|
This writes `.mcp.json` in the project root. Use `--scope user` for user-scoped registration. See the [official Claude Code MCP guide](https://code.claude.com/docs/en/mcp).
|
|
@@ -53,7 +53,7 @@ Open **Settings > MCP** and add:
|
|
|
53
53
|
"mcpServers": {
|
|
54
54
|
"brewpage": {
|
|
55
55
|
"command": "npx",
|
|
56
|
-
"args": ["-y", "brewpage-mcp@1.
|
|
56
|
+
"args": ["-y", "brewpage-mcp@1.12.0"]
|
|
57
57
|
}
|
|
58
58
|
}
|
|
59
59
|
}
|
|
@@ -67,7 +67,7 @@ Open the Cline MCP settings panel and add:
|
|
|
67
67
|
{
|
|
68
68
|
"brewpage": {
|
|
69
69
|
"command": "npx",
|
|
70
|
-
"args": ["-y", "brewpage-mcp@1.
|
|
70
|
+
"args": ["-y", "brewpage-mcp@1.12.0"]
|
|
71
71
|
}
|
|
72
72
|
}
|
|
73
73
|
```
|
|
@@ -75,13 +75,13 @@ Open the Cline MCP settings panel and add:
|
|
|
75
75
|
### Global Install
|
|
76
76
|
|
|
77
77
|
```bash
|
|
78
|
-
npm install -g brewpage-mcp@1.
|
|
78
|
+
npm install -g brewpage-mcp@1.12.0
|
|
79
79
|
brewpage-mcp
|
|
80
80
|
```
|
|
81
81
|
|
|
82
82
|
## Tools
|
|
83
83
|
|
|
84
|
-
|
|
84
|
+
Seventeen tools are available. Creation returns an owner token; keep it to modify or delete the resource later. Updates (`PUT`/`PATCH`) require the original `ownerToken`. Supported password inputs use `X-Password`.
|
|
85
85
|
|
|
86
86
|
| Tool | Purpose |
|
|
87
87
|
|------|---------|
|
|
@@ -101,10 +101,11 @@ Sixteen tools are available. Creation returns an owner token; keep it to modify
|
|
|
101
101
|
| `delete_resource` | Delete HTML, JSON, KV, or file content |
|
|
102
102
|
| `search_gallery` | Browse public content or list owned resources |
|
|
103
103
|
| `get_stats` | Read platform-wide statistics |
|
|
104
|
+
| `get_limits` | Read the current upload limits (`GET /api/limits`) |
|
|
104
105
|
|
|
105
106
|
All five publish tools accept optional `deliveryMode: "path" | "subdomain"`, sent only as `X-Delivery-Mode`; authored JSON and multipart bodies keep their existing format. Visibility and password protection are separate choices. Omitted namespace still generates an unlisted `priv-<random>` namespace; anyone with an unpassworded unlisted link can read it. `public` grants gallery/search eligibility only; password-protected content remains excluded and unlisted, protected or otherwise ineligible native responses carry `noindex`; eligible public HTML, sites and files may permit indexing.
|
|
106
107
|
|
|
107
|
-
The MCP server wraps a subset of the backend-generated public [REST contract](../openapi/openapi.json).
|
|
108
|
+
The MCP server wraps a subset of the backend-generated public [REST contract](../openapi/openapi.json). TTL inputs take days or a string such as `2w`/`36h` (default 15); the server rounds to whole days and clamps to 1–30 (owner-specific caps and eligible automatic extensions can differ). Use returned `expiresAt`. Every tolerated-input adjustment (TTL clamp, format alias, skipped site member, normalised namespace) comes back in the response `notices` array and is printed as `Notice (code): message`. `get_page` reads stored rendered HTML or format-specific code/text from the API; it does not call the owner-only original-source endpoint or a browser viewer. `publish_file` uploads from a source URL and does not expose password or TTL inputs.
|
|
108
109
|
|
|
109
110
|
For a fresh publication, sites and HTML pages of format `HTML` outside `public` (including the generated unlisted namespace) always use Dedicated subdomain (`subdomain`); omit `deliveryMode` there. An explicit `path` there is not rejected: the publication is created on its subdomain and the result reports `deliveryModeMatched: false`, `deliveryModeReason: "policy:subdomain-required"` and a `Delivery notice:` line. Everything else in any namespace (Markdown, code/text, files, JSON, KV, public HTML) defaults to Promotion (`path`) and may choose Dedicated subdomain, including password-protected content. Promotion uses a BrewPage path with stricter active-document restrictions. Each NEW site gets one publication-specific host for its complete bundle, preserving relative/root-relative paths; missing assets return 404, with no SPA fallback. Third-party widgets may still need provider configuration.
|
|
110
111
|
|
|
@@ -132,7 +133,7 @@ update_hosting(type="html", namespace="public", id="aBcDeFgHiJ", ownerToken="tok
|
|
|
132
133
|
|
|
133
134
|
Publish HTML or Markdown content to BrewPage. Returns a public URL and owner token. Markdown raw HTML is rendered through an allowlist: scripts, styles, event handlers, forms, frames/embeds and `meta`/`base`/`link` are removed; links allow `http`, `https`, `mailto`, `tel` and relative URLs, images also `data:`; a lone unknown tag such as `<author>` shows as text.
|
|
134
135
|
|
|
135
|
-
Parameters: `content` (string), `format` (`HTML`
|
|
136
|
+
Parameters: `content` (string), `format` (default `HTML`; `HTML`, `MARKDOWN` or an alias the server maps, e.g. `md`), `namespace` (optional -- **omit for unlisted content**; pass `public` only for gallery/search eligibility, except when password-protected), `password` (optional), `ttlDays` (days or a string such as `2w`; default 15; the server clamps to 1--30), `filename` (optional, used as title fallback), `showTopBar` (optional boolean -- adds a toolbar with filename, Download button, and theme toggle), `deliveryMode` (optional).
|
|
136
137
|
|
|
137
138
|
The result includes `deliveryModeReason` and a `Delivery notice:` line when the server returns them (see above).
|
|
138
139
|
|
|
@@ -206,7 +207,9 @@ publish_file(url="https://example.com/diagram.png")
|
|
|
206
207
|
|
|
207
208
|
Publish a single-page or multi-file HTML site. Pass `entryContent` for a single page or `files` (array of `{path, content}`) for a multi-file site. Supports password protection, TTL, and owner token grouping.
|
|
208
209
|
|
|
209
|
-
|
|
210
|
+
Limits (current values from `get_limits`): a request is at most 25 MB; a site at most 200 files, 5 MB per file and 20 MB in total; each path at most 380 characters. System files such as `.DS_Store` and `__MACOSX/` are skipped and never count; files with an unsupported extension or a too-long path are skipped and reported in notices. Entry: `entry`, else root `index.html`, else the shallowest HTML file. A site limit hit answers 400 with a message naming the limit; 413 means the request is over 25 MB, has too many files and form fields, or a file name/path is too long; 422 means no servable file is left.
|
|
211
|
+
|
|
212
|
+
Parameters: exactly one of `entryContent` (string) or non-empty `files` (array of `{path, content}`), `entry` (optional entry file path, default `index.html`), `namespace` (optional -- omit for unlisted content; `public` grants gallery eligibility except when password-protected), `password` (optional), `ttlDays` (days or a string such as `2w`; default 15; the server clamps to 1--30), `ownerToken` (optional, groups site under an existing owner), `deliveryMode` (optional; fresh sites require `subdomain`).
|
|
210
213
|
|
|
211
214
|
Example prompt:
|
|
212
215
|
|
|
@@ -220,9 +223,9 @@ publish_site(files=[{"path": "index.html", "content": "..."}, {"path": "style.cs
|
|
|
220
223
|
|
|
221
224
|
### `republish_site`
|
|
222
225
|
|
|
223
|
-
Replace an owned site's complete file set at the same ID and primary link. Files absent from the new bundle are removed; matching files are overwritten and new files added. Hosting stays unchanged.
|
|
226
|
+
Replace an owned site's complete file set at the same ID and primary link. Files absent from the new bundle are removed; matching files are overwritten and new files added. Hosting stays unchanged. The `publish_site` limits and status codes apply.
|
|
224
227
|
|
|
225
|
-
Parameters: `namespace`, `id`, `ownerToken`, exactly one of `entryContent` or a non-empty `files` array of `{path, content}`, optional `entry` (default `index.html`), `ttlDays` (
|
|
228
|
+
Parameters: `namespace`, `id`, `ownerToken`, exactly one of `entryContent` or a non-empty `files` array of `{path, content}`, optional `entry` (default `index.html`), `ttlDays` (ignored; existing expiry is preserved and a `ttl-ignored` notice is returned), and `tags`.
|
|
226
229
|
|
|
227
230
|
```text
|
|
228
231
|
republish_site(namespace="public", id="aBcDeFgHiJ", ownerToken="tok_...", files=[{"path":"index.html","content":"<h1>Updated site</h1>"}])
|
|
@@ -236,7 +239,7 @@ republish_site(namespace="public", id="aBcDeFgHiJ", ownerToken="tok_...", files=
|
|
|
236
239
|
|
|
237
240
|
Publish a JSON document to BrewPage. Returns a public URL and owner token. The body may be passed as a JSON string or as a structured object.
|
|
238
241
|
|
|
239
|
-
Parameters: `json` (string, object, or array), `namespace` (optional -- omit for unlisted content; `public` grants gallery/search eligibility, except when password-protected), `password` (optional), `ttlDays` (
|
|
242
|
+
Parameters: `json` (string, object, or array), `namespace` (optional -- omit for unlisted content; `public` grants gallery/search eligibility, except when password-protected), `password` (optional), `ttlDays` (days or a string such as `2w`; default 15; the server clamps to 1--30), `tags` (optional `string[]`), `ownerToken` (optional existing owner), `deliveryMode` (optional).
|
|
240
243
|
|
|
241
244
|
Example prompt:
|
|
242
245
|
|
|
@@ -286,7 +289,7 @@ update_json(namespace="public", id="aBcDeFgHiJ", json={"mode": "dark", "version"
|
|
|
286
289
|
|
|
287
290
|
Create a new KV (key/value) entry. Returns a public URL and owner token. The KV entry is addressed by `(namespace, id, key)`; this tool creates the entry and emits the generated `id` along with the owner token.
|
|
288
291
|
|
|
289
|
-
Parameters: `key` (string), `value` (string), `namespace` (optional -- omit for unlisted content; `public` grants gallery/search eligibility, except when password-protected), `password` (optional), `ttlDays` (
|
|
292
|
+
Parameters: `key` (string), `value` (string), `namespace` (optional -- omit for unlisted content; `public` grants gallery/search eligibility, except when password-protected), `password` (optional), `ttlDays` (days or a string such as `2w`; default 15; the server clamps to 1--30), `tags` (optional `string[]`), `ownerToken` (optional existing owner), `deliveryMode` (optional).
|
|
290
293
|
|
|
291
294
|
Example prompt:
|
|
292
295
|
|
|
@@ -382,6 +385,22 @@ Example prompt:
|
|
|
382
385
|
get_stats()
|
|
383
386
|
```
|
|
384
387
|
|
|
388
|
+
---
|
|
389
|
+
|
|
390
|
+
### `get_limits`
|
|
391
|
+
|
|
392
|
+
Read the current upload limits from `GET /api/limits` (no auth). Sizes are bytes: `requestMaxBytes` plus `sites.maxFiles`, `maxFileBytes`, `maxTotalBytes` (uncompressed), `maxArchiveExpansionBytes`, `maxPathChars`, `maxPathBytes`, `maxNameBytes`, `defaultTtlDays`, `maxTtlDays`, `allowedExtensions`, `skippedFileNames` and `skippedRootFolders`. Call it before publishing a large or multi-file site.
|
|
393
|
+
|
|
394
|
+
Parameters: none.
|
|
395
|
+
|
|
396
|
+
Example prompt:
|
|
397
|
+
|
|
398
|
+
> "How many files can a BrewPage site have?"
|
|
399
|
+
|
|
400
|
+
```
|
|
401
|
+
get_limits()
|
|
402
|
+
```
|
|
403
|
+
|
|
385
404
|
## Common LLM Query to BrewPage Tool Mapping
|
|
386
405
|
|
|
387
406
|
| LLM query / intent | Tool | Notes |
|
|
@@ -397,6 +416,7 @@ get_stats()
|
|
|
397
416
|
| "Remove the page I published" | `delete_resource` | Requires `ownerToken` from creation |
|
|
398
417
|
| "Read back the page I published" | `get_page` | Returns raw content for editing |
|
|
399
418
|
| "How many pages are on BrewPage?" | `get_stats` | Returns platform totals |
|
|
419
|
+
| "How big can my site be?" | `get_limits` | Current request and site limits in bytes |
|
|
400
420
|
| "Store JSON state between turns" | `publish_json` | Returns short URL + owner token |
|
|
401
421
|
| "Read that JSON document back" | `get_json` | By `namespace` + `id` |
|
|
402
422
|
| "Update the JSON I stored" | `update_json` | Requires `ownerToken`; preserves URL |
|
|
@@ -433,6 +453,15 @@ Every publish response includes an **owner token** -- the only credential that a
|
|
|
433
453
|
|
|
434
454
|
## Changelog
|
|
435
455
|
|
|
456
|
+
## 1.12.0 -- 2026-10-22
|
|
457
|
+
|
|
458
|
+
- New `get_limits` tool reads `GET /api/limits`: request size, site file count, per-file and total size, ZIP expansion, path and name lengths, TTL default/maximum, allowed extensions and skipped system files.
|
|
459
|
+
- `publish_site` and `republish_site` describe the backend 1.123.0 site rules: 200 files (was 100), 5 MB per file, 20 MB total, 25 MB per request; 400 for a site limit hit, 413 for an oversized request, too many parts or an overlong file name/path, 422 when no servable file is left; entry resolution and skipped system files. Seventeen tools.
|
|
460
|
+
|
|
461
|
+
## 1.11.0 -- 2026-10-21
|
|
462
|
+
|
|
463
|
+
- Every publish/update tool prints server `notices` as `Notice (code): message` lines. `ttlDays` takes a positive number or a string such as `2w`; the server rounds and clamps instead of the client rejecting values above 30. `publish_html` `format` accepts any string; the server maps aliases. `republish_site` TTL is ignored with a `ttl-ignored` notice. Same sixteen tools.
|
|
464
|
+
|
|
436
465
|
## 1.10.0 -- 2026-10-21
|
|
437
466
|
|
|
438
467
|
- `update_hosting`: `expectedVersion` is optional; a stale version, a locked mode or an OLD link answers with a successful result plus `deliveryModeReason` and a `Delivery notice:` line instead of an error. A publish request for `path` where `subdomain` is required succeeds on the subdomain and prints the notice. Same sixteen tools.
|
package/dist/index.js
CHANGED
|
@@ -5,7 +5,7 @@ import { z } from "zod";
|
|
|
5
5
|
const BASE_URL = process.env.BREWPAGE_URL || "https://brewpage.app";
|
|
6
6
|
const server = new McpServer({
|
|
7
7
|
name: "brewpage-mcp",
|
|
8
|
-
version: "1.
|
|
8
|
+
version: "1.12.0",
|
|
9
9
|
});
|
|
10
10
|
const PUBLIC_NAMESPACE = "public";
|
|
11
11
|
/**
|
|
@@ -36,10 +36,18 @@ const NAMESPACE_DESCRIPTION = "Optional. Omit to generate an unlisted namespace:
|
|
|
36
36
|
"but it is excluded from gallery/search. Pass a custom namespace to group unlisted content, " +
|
|
37
37
|
"or pass `public` ONLY when the user explicitly wants gallery/search eligibility. " +
|
|
38
38
|
"Password-protected content stays excluded; unlisted, protected or otherwise ineligible native responses carry noindex; eligible public HTML, sites and files may permit indexing.";
|
|
39
|
+
const TTL_SCHEMA = z.union([z.number().positive(), z.string().min(1).max(32)]).optional().describe("Requested TTL: days as a number, or a string such as '2w', '36h' or '1 month' (default 15 days). " +
|
|
40
|
+
"The server rounds to whole days and clamps to the allowed range (1-30 by default; owner caps differ), reporting each adjustment in notices; use returned expiresAt.");
|
|
39
41
|
const DELIVERY_MODE_SCHEMA = z.enum(["path", "subdomain"]).optional().describe("Optional delivery choice for a fresh publication, independent of password/namespace. " +
|
|
40
42
|
"Fresh sites and HTML-format pages outside public (including the default unlisted namespace) always use subdomain; an explicit path there still publishes, on subdomain, with a delivery notice. " +
|
|
41
43
|
"Everything else in any namespace (Markdown, code/text, files, JSON, KV, public HTML) defaults to path (Promotion); public HTML may automatically choose subdomain for browser features. " +
|
|
42
44
|
"When creation returns an existing publication, it keeps its actual mode and URL.");
|
|
45
|
+
/** Site upload rules shared by publish_site and republish_site; current values come from get_limits. */
|
|
46
|
+
const SITE_LIMITS_TEXT = "Limits (call get_limits for current values): a request is at most 25 MB; a site at most 200 files, 5 MB per file and 20 MB in total; " +
|
|
47
|
+
"each path at most 380 characters. System files (.DS_Store, __MACOSX/ and similar) are skipped and never count; files with an unsupported extension " +
|
|
48
|
+
"or a too-long path are skipped and listed in notices. Entry: `entry`, else root index.html, else the shallowest HTML file. " +
|
|
49
|
+
"Errors: 400 = a site limit exceeded (the message names it and what to do), invalid path or no HTML file; 413 = request over 25 MB, " +
|
|
50
|
+
"too many files and form fields, or a file name/path too long; 422 = no servable file left.";
|
|
43
51
|
function hostingResponseLines(data) {
|
|
44
52
|
const fields = ["routingCohort", "deliveryMode", "requestedDeliveryMode", "effectiveDeliveryMode",
|
|
45
53
|
"deliveryModeMatched", "modeLocked", "hostingVersion", "access", "managementLink"];
|
|
@@ -49,8 +57,17 @@ function hostingResponseLines(data) {
|
|
|
49
57
|
if (data.deliveryModeMatched === false)
|
|
50
58
|
lines.push("Requested hosting differs from the effective mode; use the returned URL.");
|
|
51
59
|
lines.push(...deliveryReasonLines(data));
|
|
60
|
+
lines.push(...noticeLines(data));
|
|
52
61
|
return lines;
|
|
53
62
|
}
|
|
63
|
+
/** Server `notices` ({code, message}) on publish/update responses: each tolerated-input adjustment, verbatim. */
|
|
64
|
+
function noticeLines(data) {
|
|
65
|
+
if (!Array.isArray(data.notices))
|
|
66
|
+
return [];
|
|
67
|
+
return data.notices
|
|
68
|
+
.filter((n) => typeof n === "object" && n !== null && typeof n.code === "string" && typeof n.message === "string")
|
|
69
|
+
.map((n) => `Notice (${n.code}): ${n.message}`);
|
|
70
|
+
}
|
|
54
71
|
/** Optional delivery fields on HTML and hosting responses: why the mode was chosen, flagged or not applied. */
|
|
55
72
|
function deliveryReasonLines(data) {
|
|
56
73
|
const { deliveryModeReason: reason, deliveryNotice: notice } = data;
|
|
@@ -115,9 +132,10 @@ server.tool("publish_html", "Publish HTML or Markdown content to BrewPage (repos
|
|
|
115
132
|
content: z.string().describe("HTML or Markdown content to publish"),
|
|
116
133
|
deliveryMode: DELIVERY_MODE_SCHEMA,
|
|
117
134
|
format: z
|
|
118
|
-
.
|
|
135
|
+
.string()
|
|
136
|
+
.min(1)
|
|
119
137
|
.default("HTML")
|
|
120
|
-
.describe("Content format
|
|
138
|
+
.describe("Content format, default HTML. HTML or MARKDOWN; the server also maps aliases (md, text/markdown, file extensions, code languages) and detects unknown values from content, reporting the change in notices."),
|
|
121
139
|
namespace: z
|
|
122
140
|
.string()
|
|
123
141
|
.optional()
|
|
@@ -126,13 +144,7 @@ server.tool("publish_html", "Publish HTML or Markdown content to BrewPage (repos
|
|
|
126
144
|
.string()
|
|
127
145
|
.optional()
|
|
128
146
|
.describe("Optional password to protect the page"),
|
|
129
|
-
ttlDays:
|
|
130
|
-
.number()
|
|
131
|
-
.int()
|
|
132
|
-
.min(1)
|
|
133
|
-
.max(30)
|
|
134
|
-
.optional()
|
|
135
|
-
.describe("Requested TTL in days (1-30, default 15). Backend owner caps and eligible automatic extensions can affect expiry; use returned expiresAt."),
|
|
147
|
+
ttlDays: TTL_SCHEMA,
|
|
136
148
|
filename: z
|
|
137
149
|
.string()
|
|
138
150
|
.max(200)
|
|
@@ -360,7 +372,7 @@ server.tool("get_stats", "Get BrewPage platform-wide usage statistics including
|
|
|
360
372
|
],
|
|
361
373
|
};
|
|
362
374
|
});
|
|
363
|
-
server.tool("publish_site", "Publish an HTML site to BrewPage. Single-page: pass `entryContent`. Multi-page: pass `files` (array of `{path, content}`). Optional `entry` overrides default `index.html`.
|
|
375
|
+
server.tool("publish_site", "Publish an HTML site to BrewPage. Single-page: pass `entryContent`. Multi-page: pass `files` (array of `{path, content}`). Optional `entry` overrides default `index.html`. Use its returned primary link and retain the owner token. " + SITE_LIMITS_TEXT, {
|
|
364
376
|
deliveryMode: DELIVERY_MODE_SCHEMA,
|
|
365
377
|
entryContent: z
|
|
366
378
|
.string()
|
|
@@ -382,12 +394,7 @@ server.tool("publish_site", "Publish an HTML site to BrewPage. Single-page: pass
|
|
|
382
394
|
.string()
|
|
383
395
|
.optional()
|
|
384
396
|
.describe("Optional password to protect the site"),
|
|
385
|
-
ttlDays:
|
|
386
|
-
.number()
|
|
387
|
-
.min(1)
|
|
388
|
-
.max(30)
|
|
389
|
-
.optional()
|
|
390
|
-
.describe("Requested TTL in days (1-30, default 15). Backend owner caps and eligible automatic extensions can affect expiry; use returned expiresAt."),
|
|
397
|
+
ttlDays: TTL_SCHEMA,
|
|
391
398
|
ownerToken: z
|
|
392
399
|
.string()
|
|
393
400
|
.optional()
|
|
@@ -476,7 +483,7 @@ server.tool("publish_site", "Publish an HTML site to BrewPage. Single-page: pass
|
|
|
476
483
|
content: [{ type: "text", text: lines.join("\n") }],
|
|
477
484
|
};
|
|
478
485
|
});
|
|
479
|
-
server.tool("republish_site", "Republish (full-replace) an existing multi-file BrewPage site in place at the SAME URL/ID. Requires owner token. The uploaded bundle becomes the complete new file set — files absent from it are removed, new files added, matching files overwritten. Single-page: pass `entryContent`. Multi-page: pass `files` (array of `{path, content}`). Optional `entry` overrides the default `index.html`.
|
|
486
|
+
server.tool("republish_site", "Republish (full-replace) an existing multi-file BrewPage site in place at the SAME URL/ID. Requires owner token. The uploaded bundle becomes the complete new file set — files absent from it are removed, new files added, matching files overwritten. Single-page: pass `entryContent`. Multi-page: pass `files` (array of `{path, content}`). Optional `entry` overrides the default `index.html`. Republishing preserves existing expiry. " + SITE_LIMITS_TEXT, {
|
|
480
487
|
namespace: z.string().describe("Site namespace"),
|
|
481
488
|
id: z.string().describe("Site ID"),
|
|
482
489
|
ownerToken: z
|
|
@@ -494,12 +501,7 @@ server.tool("republish_site", "Republish (full-replace) an existing multi-file B
|
|
|
494
501
|
.string()
|
|
495
502
|
.optional()
|
|
496
503
|
.describe("Entry file path, default index.html"),
|
|
497
|
-
ttlDays:
|
|
498
|
-
.number()
|
|
499
|
-
.min(1)
|
|
500
|
-
.max(30)
|
|
501
|
-
.optional()
|
|
502
|
-
.describe("Compatibility input (1-30); site republishing preserves existing expiry. Use returned expiresAt."),
|
|
504
|
+
ttlDays: TTL_SCHEMA.describe("Ignored: republishing keeps the existing expiry; a supplied value comes back as a ttl-ignored notice."),
|
|
503
505
|
tags: z
|
|
504
506
|
.array(z.string())
|
|
505
507
|
.optional()
|
|
@@ -634,13 +636,7 @@ server.tool("publish_json", "Publish a JSON document to BrewPage (repository def
|
|
|
634
636
|
.string()
|
|
635
637
|
.optional()
|
|
636
638
|
.describe("Optional password to protect the document"),
|
|
637
|
-
ttlDays:
|
|
638
|
-
.number()
|
|
639
|
-
.int()
|
|
640
|
-
.min(1)
|
|
641
|
-
.max(30)
|
|
642
|
-
.optional()
|
|
643
|
-
.describe("Requested TTL in days (1-30, default 15). Backend owner caps and eligible automatic extensions can affect expiry; use returned expiresAt."),
|
|
639
|
+
ttlDays: TTL_SCHEMA,
|
|
644
640
|
tags: z
|
|
645
641
|
.array(z.string())
|
|
646
642
|
.optional()
|
|
@@ -780,13 +776,7 @@ server.tool("publish_kv", "Publish a key/value entry to BrewPage. Creates a KV s
|
|
|
780
776
|
.string()
|
|
781
777
|
.optional()
|
|
782
778
|
.describe("Optional password to protect the KV store"),
|
|
783
|
-
ttlDays:
|
|
784
|
-
.number()
|
|
785
|
-
.int()
|
|
786
|
-
.min(1)
|
|
787
|
-
.max(30)
|
|
788
|
-
.optional()
|
|
789
|
-
.describe("Requested TTL in days (1-30, default 15). Backend owner caps and eligible automatic extensions can affect expiry; use returned expiresAt."),
|
|
779
|
+
ttlDays: TTL_SCHEMA,
|
|
790
780
|
tags: z
|
|
791
781
|
.array(z.string())
|
|
792
782
|
.optional()
|
|
@@ -903,6 +893,30 @@ server.tool("get_kv", "Fetch a value from a BrewPage KV store by namespace, ID,
|
|
|
903
893
|
],
|
|
904
894
|
};
|
|
905
895
|
});
|
|
896
|
+
server.tool("get_limits", "Get the current BrewPage upload limits (GET /api/limits, no auth): request size, site file count, per-file and total size, " +
|
|
897
|
+
"ZIP expansion, path and name lengths, TTL default/maximum, allowed file extensions and skipped system files. Sizes are bytes. " +
|
|
898
|
+
"Call it before publishing a large or multi-file site.", {}, async () => {
|
|
899
|
+
const { ok, status, data } = await apiRequest("GET", "/api/limits");
|
|
900
|
+
if (!ok) {
|
|
901
|
+
return {
|
|
902
|
+
content: [
|
|
903
|
+
{
|
|
904
|
+
type: "text",
|
|
905
|
+
text: `Failed to fetch limits (${status}): ${JSON.stringify(data)}`,
|
|
906
|
+
},
|
|
907
|
+
],
|
|
908
|
+
isError: true,
|
|
909
|
+
};
|
|
910
|
+
}
|
|
911
|
+
return {
|
|
912
|
+
content: [
|
|
913
|
+
{
|
|
914
|
+
type: "text",
|
|
915
|
+
text: `BrewPage upload limits (bytes):\n\n${JSON.stringify(data, null, 2)}`,
|
|
916
|
+
},
|
|
917
|
+
],
|
|
918
|
+
};
|
|
919
|
+
});
|
|
906
920
|
server.tool("search_gallery", "Search the BrewPage public gallery. Optional filters: text query, pagination, sort, and 'mine' (owner-scoped, requires owner token).", {
|
|
907
921
|
q: z.string().optional().describe("Free-text search query"),
|
|
908
922
|
page: z
|
package/package.json
CHANGED