webcake-landing-mcp 1.0.1
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 +535 -0
- package/dist/factory.js +421 -0
- package/dist/index.js +244 -0
- package/dist/library.js +372 -0
- package/dist/page-schema.json +266 -0
- package/dist/smoke.js +122 -0
- package/dist/validate.js +211 -0
- package/dist/webcake.js +238 -0
- package/package.json +42 -0
package/README.md
ADDED
|
@@ -0,0 +1,535 @@
|
|
|
1
|
+
# WebCake Landing MCP Server
|
|
2
|
+
|
|
3
|
+
MCP (Model Context Protocol) server that teaches AI agents how to build a complete
|
|
4
|
+
**WebCake landing-page source JSON** from a requirement — and persist it to a WebCake backend.
|
|
5
|
+
|
|
6
|
+
It exposes the element catalog, per-element usage hints + `specials`, the full page JSON Schema,
|
|
7
|
+
valid element/page skeletons, a page validator, and tools to create or edit pages on the backend.
|
|
8
|
+
The AI agent produces the full `{ page, popup, settings, options, cartConfigs }` JSON; `create_page`
|
|
9
|
+
persists it (source-only — the page opens in the editor where re-saving renders it).
|
|
10
|
+
|
|
11
|
+
## Two ways to run
|
|
12
|
+
|
|
13
|
+
| Mode | Command | When |
|
|
14
|
+
|------|---------|------|
|
|
15
|
+
| **CDN / npx** (no clone) | `npx -y webcake-landing-mcp` | Fastest start — npm fetches & runs it, no clone or build. Auto-updates to the latest published version. |
|
|
16
|
+
| **Local** (cloned build) | `node /abs/path/dist/index.js` | Hacking on the server, offline, or pinning a specific build. Run `npm run build` first. |
|
|
17
|
+
|
|
18
|
+
Both expose the exact same tools. Every IDE config below shows the **local** form; to use **CDN** mode,
|
|
19
|
+
just swap `command`/`args` for the npx form (see [Run without cloning](#run-without-cloning-npx)).
|
|
20
|
+
|
|
21
|
+
## Quick Install (Recommended)
|
|
22
|
+
|
|
23
|
+
Run the auto-install script — it handles everything: clone, install dependencies, build, and configure your IDE.
|
|
24
|
+
|
|
25
|
+
### macOS / Linux
|
|
26
|
+
|
|
27
|
+
If you already cloned the repo:
|
|
28
|
+
```bash
|
|
29
|
+
./install.sh
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
Or download and run directly:
|
|
33
|
+
```bash
|
|
34
|
+
curl -fsSL https://raw.githubusercontent.com/vuluu2k/webcake-landing-mcp/main/install.sh -o install.sh && bash install.sh
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
The installer is interactive: it asks where to install (default `~/.webcake-landing-mcp`), prompts for
|
|
38
|
+
the env vars (`WEBCAKE_API_BASE`, `WEBCAKE_JWT`, `WEBCAKE_ORG_ID` — all optional, Enter to skip), then
|
|
39
|
+
lets you pick which IDE(s) to configure: `claude-desktop`, `claude-code`, `cursor`, `windsurf`, `augment`,
|
|
40
|
+
`codex`, or all.
|
|
41
|
+
|
|
42
|
+
Uninstall (removes the MCP server entry from every configured IDE):
|
|
43
|
+
```bash
|
|
44
|
+
./install.sh --uninstall
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
### Windows (PowerShell)
|
|
48
|
+
|
|
49
|
+
If you already cloned the repo:
|
|
50
|
+
```powershell
|
|
51
|
+
.\install.ps1
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
Or download and run directly:
|
|
55
|
+
```powershell
|
|
56
|
+
irm https://raw.githubusercontent.com/vuluu2k/webcake-landing-mcp/main/install.ps1 -OutFile install.ps1; .\install.ps1
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
Uninstall:
|
|
60
|
+
```powershell
|
|
61
|
+
.\install.ps1 --uninstall
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
---
|
|
65
|
+
|
|
66
|
+
## Update
|
|
67
|
+
|
|
68
|
+
Update to the latest version:
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
cd ~/.webcake-landing-mcp # or wherever you installed it
|
|
72
|
+
git pull
|
|
73
|
+
npm install
|
|
74
|
+
npm run build
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
Then restart your IDE.
|
|
78
|
+
|
|
79
|
+
---
|
|
80
|
+
|
|
81
|
+
## Run without cloning (npx)
|
|
82
|
+
|
|
83
|
+
Once published to npm, the server runs straight from the registry — no clone, no build:
|
|
84
|
+
|
|
85
|
+
```bash
|
|
86
|
+
npx -y webcake-landing-mcp
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
Or run the latest from GitHub (npx clones + builds via the `prepare` script on the fly):
|
|
90
|
+
|
|
91
|
+
```bash
|
|
92
|
+
npx -y github:vuluu2k/webcake-landing-mcp
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
The MCP config is the same as the local one, but `command`/`args` point at `npx` instead of a built file:
|
|
96
|
+
|
|
97
|
+
```json
|
|
98
|
+
{
|
|
99
|
+
"mcpServers": {
|
|
100
|
+
"webcake-landing": {
|
|
101
|
+
"command": "npx",
|
|
102
|
+
"args": ["-y", "webcake-landing-mcp"],
|
|
103
|
+
"env": {
|
|
104
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
105
|
+
"WEBCAKE_JWT": "<your-jwt>"
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
```
|
|
111
|
+
|
|
112
|
+
> npx caches the package after the first run, so subsequent launches are fast. Use a pinned version
|
|
113
|
+
> (`webcake-landing-mcp@1.0.0`) if you need a reproducible build.
|
|
114
|
+
|
|
115
|
+
## Manual Setup (local)
|
|
116
|
+
|
|
117
|
+
```bash
|
|
118
|
+
git clone https://github.com/vuluu2k/webcake-landing-mcp.git
|
|
119
|
+
cd webcake-landing-mcp
|
|
120
|
+
npm install # postinstall `prepare` builds dist/ automatically
|
|
121
|
+
npm run build # (re)build: tsc -> dist/ + copies page-schema.json
|
|
122
|
+
npm run smoke # offline self-test of factory + validator (prints "ALL GOOD")
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
The reference/validation tools work with **zero config**. Env vars are only needed for the persistence
|
|
126
|
+
tools (`create_page`, `update_page`, `list_pages`, `get_page`, `list_organizations`).
|
|
127
|
+
|
|
128
|
+
## Environment Variables
|
|
129
|
+
|
|
130
|
+
| Variable | Required | Description |
|
|
131
|
+
|----------|----------|-------------|
|
|
132
|
+
| `WEBCAKE_API_BASE` | No* | Backend base URL, e.g. `http://localhost:5800`. Required to persist. |
|
|
133
|
+
| `WEBCAKE_JWT` | No* | Account JWT (dashboard auth). Required to persist — expires, refresh when needed. |
|
|
134
|
+
| `WEBCAKE_ORG_ID` | No | Default organization id for `create_page` (overridden by its `organization_id` arg). Omit → personal page. |
|
|
135
|
+
| `WEBCAKE_HOST` | No | Optional `Host` header (Phoenix routes by host, e.g. `builder.localhost`). |
|
|
136
|
+
| `WEBCAKE_APP_BASE` | No | Optional base used to build editor/preview URLs in the result. |
|
|
137
|
+
|
|
138
|
+
> \* `WEBCAKE_API_BASE` and `WEBCAKE_JWT` are only needed for the persistence tools. The reference and
|
|
139
|
+
> validation tools (`get_generation_guide`, `list_elements`, `get_element`, `validate_page`, …) work without them.
|
|
140
|
+
|
|
141
|
+
> Persisting writes a real page to whatever `WEBCAKE_API_BASE` points at, using the JWT as that account.
|
|
142
|
+
> Start against local/staging.
|
|
143
|
+
|
|
144
|
+
### How to get `WEBCAKE_JWT`
|
|
145
|
+
|
|
146
|
+
1. Open the WebCake builder dashboard and log in
|
|
147
|
+
2. Open DevTools (`F12` or `Cmd + Option + I`)
|
|
148
|
+
3. Go to the **Network** tab > click any page
|
|
149
|
+
4. Find an API request (e.g. `@me`, `organizations`…)
|
|
150
|
+
5. In **Request Headers**, copy the value after `Authorization: Bearer ` → this is your `WEBCAKE_JWT`
|
|
151
|
+
6. Use the `list_organizations` tool to list orgs and pick `WEBCAKE_ORG_ID`
|
|
152
|
+
|
|
153
|
+
---
|
|
154
|
+
|
|
155
|
+
## Configuration by IDE / AI Tool
|
|
156
|
+
|
|
157
|
+
> Replace `/absolute-path/webcake-landing-mcp/dist/index.js` below with the actual path where you
|
|
158
|
+
> cloned/built the repo. Example: `/Users/username/webcake-landing-mcp/dist/index.js`.
|
|
159
|
+
> Run `npm run build` first so `dist/` exists.
|
|
160
|
+
|
|
161
|
+
### 1. Claude Desktop
|
|
162
|
+
|
|
163
|
+
Open Settings > Developer > Edit Config, or edit the file directly:
|
|
164
|
+
|
|
165
|
+
- **macOS**: `~/Library/Application Support/Claude/claude_desktop_config.json`
|
|
166
|
+
- **Windows**: `%APPDATA%\Claude\claude_desktop_config.json`
|
|
167
|
+
- **Linux**: `~/.config/Claude/claude_desktop_config.json`
|
|
168
|
+
|
|
169
|
+
```json
|
|
170
|
+
{
|
|
171
|
+
"mcpServers": {
|
|
172
|
+
"webcake-landing": {
|
|
173
|
+
"command": "node",
|
|
174
|
+
"args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
|
|
175
|
+
"env": {
|
|
176
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
177
|
+
"WEBCAKE_JWT": "<your-jwt>",
|
|
178
|
+
"WEBCAKE_HOST": "builder.localhost",
|
|
179
|
+
"WEBCAKE_APP_BASE": "http://builder.localhost:5800"
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
Restart Claude Desktop. The MCP tools will appear in the chat input (hammer icon).
|
|
187
|
+
|
|
188
|
+
---
|
|
189
|
+
|
|
190
|
+
### 2. Claude Code (CLI)
|
|
191
|
+
|
|
192
|
+
Run in terminal — **local** build:
|
|
193
|
+
|
|
194
|
+
```bash
|
|
195
|
+
claude mcp add webcake-landing \
|
|
196
|
+
-e WEBCAKE_API_BASE=http://localhost:5800 \
|
|
197
|
+
-e WEBCAKE_JWT=<your-jwt> \
|
|
198
|
+
-e WEBCAKE_HOST=builder.localhost \
|
|
199
|
+
-- node /absolute-path/webcake-landing-mcp/dist/index.js
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
Or **CDN / npx** (no clone):
|
|
203
|
+
|
|
204
|
+
```bash
|
|
205
|
+
claude mcp add webcake-landing \
|
|
206
|
+
-e WEBCAKE_API_BASE=http://localhost:5800 \
|
|
207
|
+
-e WEBCAKE_JWT=<your-jwt> \
|
|
208
|
+
-- npx -y webcake-landing-mcp
|
|
209
|
+
```
|
|
210
|
+
|
|
211
|
+
Or create `.claude.json` at project root (or `~/.claude.json` globally):
|
|
212
|
+
|
|
213
|
+
```json
|
|
214
|
+
{
|
|
215
|
+
"mcpServers": {
|
|
216
|
+
"webcake-landing": {
|
|
217
|
+
"command": "node",
|
|
218
|
+
"args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
|
|
219
|
+
"env": {
|
|
220
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
221
|
+
"WEBCAKE_JWT": "<your-jwt>"
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
```
|
|
227
|
+
|
|
228
|
+
Verify:
|
|
229
|
+
```bash
|
|
230
|
+
claude mcp list
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
---
|
|
234
|
+
|
|
235
|
+
### 3. Cursor
|
|
236
|
+
|
|
237
|
+
Create `.cursor/mcp.json` at project root (or `~/.cursor/mcp.json` globally):
|
|
238
|
+
|
|
239
|
+
```json
|
|
240
|
+
{
|
|
241
|
+
"mcpServers": {
|
|
242
|
+
"webcake-landing": {
|
|
243
|
+
"command": "node",
|
|
244
|
+
"args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
|
|
245
|
+
"env": {
|
|
246
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
247
|
+
"WEBCAKE_JWT": "<your-jwt>"
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
Restart Cursor and check Settings > MCP Servers for **"Connected"** status.
|
|
255
|
+
|
|
256
|
+
---
|
|
257
|
+
|
|
258
|
+
### 4. Windsurf
|
|
259
|
+
|
|
260
|
+
Create `~/.codeium/windsurf/mcp_config.json`:
|
|
261
|
+
|
|
262
|
+
```json
|
|
263
|
+
{
|
|
264
|
+
"mcpServers": {
|
|
265
|
+
"webcake-landing": {
|
|
266
|
+
"command": "node",
|
|
267
|
+
"args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
|
|
268
|
+
"env": {
|
|
269
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
270
|
+
"WEBCAKE_JWT": "<your-jwt>"
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
}
|
|
275
|
+
```
|
|
276
|
+
|
|
277
|
+
Restart Windsurf. Type `@` in Cascade chat to see `webcake-landing` tools.
|
|
278
|
+
|
|
279
|
+
---
|
|
280
|
+
|
|
281
|
+
### 5. Augment (VS Code Extension)
|
|
282
|
+
|
|
283
|
+
Open Command Palette: `Cmd + Shift + P` > **"Augment: Edit MCP Settings"**, then add:
|
|
284
|
+
|
|
285
|
+
```json
|
|
286
|
+
{
|
|
287
|
+
"mcpServers": {
|
|
288
|
+
"webcake-landing": {
|
|
289
|
+
"command": "node",
|
|
290
|
+
"args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
|
|
291
|
+
"env": {
|
|
292
|
+
"WEBCAKE_API_BASE": "http://localhost:5800",
|
|
293
|
+
"WEBCAKE_JWT": "<your-jwt>"
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
}
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
Restart VS Code.
|
|
301
|
+
|
|
302
|
+
---
|
|
303
|
+
|
|
304
|
+
### 6. Codex (OpenAI CLI)
|
|
305
|
+
|
|
306
|
+
Add to `~/.codex/config.toml`:
|
|
307
|
+
|
|
308
|
+
```toml
|
|
309
|
+
[mcp_servers.webcake-landing]
|
|
310
|
+
command = "node"
|
|
311
|
+
args = ["/absolute-path/webcake-landing-mcp/dist/index.js"]
|
|
312
|
+
env = { "WEBCAKE_API_BASE" = "http://localhost:5800", "WEBCAKE_JWT" = "<your-jwt>" }
|
|
313
|
+
```
|
|
314
|
+
|
|
315
|
+
Verify:
|
|
316
|
+
```bash
|
|
317
|
+
codex mcp list
|
|
318
|
+
```
|
|
319
|
+
|
|
320
|
+
---
|
|
321
|
+
|
|
322
|
+
## Usage Examples
|
|
323
|
+
|
|
324
|
+
### Example 1: Build a new landing page from a brief
|
|
325
|
+
|
|
326
|
+
**Prompt:**
|
|
327
|
+
```
|
|
328
|
+
Build me a WebCake landing page for "Acme Coffee" — a hero with a CTA, a 3-feature
|
|
329
|
+
section, and a signup form. Persist it to my default org.
|
|
330
|
+
```
|
|
331
|
+
|
|
332
|
+
**AI agent will automatically:**
|
|
333
|
+
|
|
334
|
+
**Step 1** — Call `get_generation_guide` to learn conventions (canvas, coordinate system, events, workflow)
|
|
335
|
+
|
|
336
|
+
**Step 2** — Call `new_page_skeleton` for an empty top-level source, then `get_element` for each type it uses:
|
|
337
|
+
|
|
338
|
+
```
|
|
339
|
+
get_element({ type: "section" })
|
|
340
|
+
get_element({ type: "text-block" })
|
|
341
|
+
get_element({ type: "button" })
|
|
342
|
+
get_element({ type: "form" })
|
|
343
|
+
```
|
|
344
|
+
|
|
345
|
+
**Step 3** — Assemble the full `{ page, popup, settings, options, cartConfigs }` JSON, then validate:
|
|
346
|
+
|
|
347
|
+
```
|
|
348
|
+
validate_page({ source })
|
|
349
|
+
→ { ok: false, errors: ["BUTTON-2: event target 'POPUP-9' not found"] } # fix every error, re-validate
|
|
350
|
+
validate_page({ source })
|
|
351
|
+
→ { ok: true, errors: [] }
|
|
352
|
+
```
|
|
353
|
+
|
|
354
|
+
**Step 4** — Persist (dry-run first, then for real):
|
|
355
|
+
|
|
356
|
+
```
|
|
357
|
+
list_organizations({}) → pick the org
|
|
358
|
+
create_page({ source }) → dry-run preview (JWT masked)
|
|
359
|
+
create_page({ source, dry_run: false }) → { page_id, editor_url, preview_url }
|
|
360
|
+
```
|
|
361
|
+
|
|
362
|
+
Open the page in the editor and re-save to render `app`/`app_css`.
|
|
363
|
+
|
|
364
|
+
---
|
|
365
|
+
|
|
366
|
+
### Example 2: Edit an existing page
|
|
367
|
+
|
|
368
|
+
**Prompt:**
|
|
369
|
+
```
|
|
370
|
+
On my "Acme Coffee" landing page, change the hero headline to "Freshly Roasted Daily"
|
|
371
|
+
and make the CTA button green.
|
|
372
|
+
```
|
|
373
|
+
|
|
374
|
+
**AI agent edits surgically — never regenerates the whole tree:**
|
|
375
|
+
|
|
376
|
+
```
|
|
377
|
+
# Step 1: find the page
|
|
378
|
+
list_pages({})
|
|
379
|
+
→ [{ id: "page_42", name: "Acme Coffee", organization_id: "org_1", ... }]
|
|
380
|
+
|
|
381
|
+
# Step 2: fetch its decoded source tree
|
|
382
|
+
get_page({ page_id: "page_42" })
|
|
383
|
+
|
|
384
|
+
# Step 3: change ONLY the headline text + button color, keep every other id/coordinate,
|
|
385
|
+
# then validate and write back
|
|
386
|
+
validate_page({ source }) → ok
|
|
387
|
+
update_page({ page_id: "page_42", source }) → dry-run preview
|
|
388
|
+
update_page({ page_id: "page_42", source, dry_run: false })
|
|
389
|
+
```
|
|
390
|
+
|
|
391
|
+
---
|
|
392
|
+
|
|
393
|
+
### Example 3: Inspect an element type before using it
|
|
394
|
+
|
|
395
|
+
**Prompt:**
|
|
396
|
+
```
|
|
397
|
+
What specials does a form element need, and show me a valid example.
|
|
398
|
+
```
|
|
399
|
+
|
|
400
|
+
**AI agent calls:**
|
|
401
|
+
|
|
402
|
+
```
|
|
403
|
+
get_element({ type: "form" })
|
|
404
|
+
→ {
|
|
405
|
+
hints: "Each input needs a unique specials.field_name…",
|
|
406
|
+
specials: { ... },
|
|
407
|
+
skeleton: { ... }, # structurally-valid default node
|
|
408
|
+
example: { ... } # filled, realistic example
|
|
409
|
+
}
|
|
410
|
+
```
|
|
411
|
+
|
|
412
|
+
---
|
|
413
|
+
|
|
414
|
+
## Detailed Tool Usage Guide
|
|
415
|
+
|
|
416
|
+
The tools split into three groups: **reference** (learn the model — no config needed),
|
|
417
|
+
**generation** (build valid nodes), and **persistence** (save to the backend — needs env vars).
|
|
418
|
+
|
|
419
|
+
### Step 1: Read the guide first — `get_generation_guide`
|
|
420
|
+
|
|
421
|
+
Always call this **first**. It returns the output shape, coordinate system (desktop ≈ 960px,
|
|
422
|
+
mobile ≈ 420px), event vocabulary, and the end-to-end workflow.
|
|
423
|
+
|
|
424
|
+
```
|
|
425
|
+
get_generation_guide({})
|
|
426
|
+
→ "## Output shape… ## Canvas… ## Events… ## Workflow…"
|
|
427
|
+
```
|
|
428
|
+
|
|
429
|
+
### Step 2: Browse the element catalog — `list_elements` / `get_element`
|
|
430
|
+
|
|
431
|
+
```
|
|
432
|
+
# All element types by category (summary + when-to-use + is it a container?)
|
|
433
|
+
list_elements({})
|
|
434
|
+
→ { categories: { layout: [...], content: [...], form: [...], ... } }
|
|
435
|
+
|
|
436
|
+
# Deep-dive one type — hints, key specials, default skeleton, filled example
|
|
437
|
+
get_element({ type: "button" })
|
|
438
|
+
```
|
|
439
|
+
|
|
440
|
+
### Step 3: Get valid building blocks — `new_element` / `new_page_skeleton`
|
|
441
|
+
|
|
442
|
+
```
|
|
443
|
+
# A structurally-valid default node for a type (fresh id)
|
|
444
|
+
new_element({ type: "section" })
|
|
445
|
+
|
|
446
|
+
# An empty but complete top-level source
|
|
447
|
+
new_page_skeleton({})
|
|
448
|
+
→ { page: [], popup: [], settings: {…}, options: { currency, mobileOnly, versionID }, cartConfigs: {} }
|
|
449
|
+
```
|
|
450
|
+
|
|
451
|
+
### Step 4: Inspect / validate — `get_page_schema` / `validate_page`
|
|
452
|
+
|
|
453
|
+
```
|
|
454
|
+
# Full JSON Schema (Draft 2020-12) of a page source
|
|
455
|
+
get_page_schema({})
|
|
456
|
+
|
|
457
|
+
# Structural + semantic validation — fix every error before persisting
|
|
458
|
+
validate_page({ source })
|
|
459
|
+
→ { ok: false, errors: [...], warnings: [...] }
|
|
460
|
+
```
|
|
461
|
+
|
|
462
|
+
`validate_page` **errors are blocking**; warnings (dangling event target, missing `field_name`) are advisory.
|
|
463
|
+
|
|
464
|
+
### Step 5: Persist — `list_organizations` / `create_page` / `update_page`
|
|
465
|
+
|
|
466
|
+
```
|
|
467
|
+
# List the account's organizations — ask which to use; default = the is_default org
|
|
468
|
+
list_organizations({})
|
|
469
|
+
→ [{ id: "org_1", name: "Acme", is_default: true }, ...]
|
|
470
|
+
|
|
471
|
+
# Create a NEW page (source-only). Defaults to dry_run=true.
|
|
472
|
+
create_page({ source, organization_id: "org_1" }) # preview
|
|
473
|
+
create_page({ source, dry_run: false }) # actually create
|
|
474
|
+
|
|
475
|
+
# Edit an EXISTING page
|
|
476
|
+
list_pages({}) # find the page
|
|
477
|
+
get_page({ page_id }) # fetch decoded source
|
|
478
|
+
update_page({ page_id, source, dry_run: false }) # overwrite (dry_run=true by default)
|
|
479
|
+
```
|
|
480
|
+
|
|
481
|
+
`create_page` calls **`POST {WEBCAKE_API_BASE}/api/v1/ai/create_page_from_source`** on the backend.
|
|
482
|
+
Both `create_page` and `update_page` **default to `dry_run=true`** (validate and return the request they
|
|
483
|
+
*would* send, JWT masked); set `dry_run=false` to actually write. The result returns `page_id` + editor/preview URLs.
|
|
484
|
+
|
|
485
|
+
---
|
|
486
|
+
|
|
487
|
+
## Suggested prompt
|
|
488
|
+
|
|
489
|
+
> Build me a WebCake landing page for <brand/offer>. Use the webcake-landing MCP:
|
|
490
|
+
> call `get_generation_guide`, `new_page_skeleton`, then `get_element` for each element type you use,
|
|
491
|
+
> assemble the `{ page, popup, settings, options }` JSON, `validate_page` until zero errors,
|
|
492
|
+
> then `create_page` (dry-run first).
|
|
493
|
+
|
|
494
|
+
---
|
|
495
|
+
|
|
496
|
+
## Available Tools
|
|
497
|
+
|
|
498
|
+
### Reference (no config needed)
|
|
499
|
+
| Tool | Description |
|
|
500
|
+
|------|-------------|
|
|
501
|
+
| `get_generation_guide` | **Read FIRST.** Output shape, coordinate system, event vocabulary, workflow. |
|
|
502
|
+
| `list_elements` | All element types by category (summary + when-to-use + container?). |
|
|
503
|
+
| `get_element` | One type: hints, key `specials`, default skeleton, filled example. |
|
|
504
|
+
| `get_page_schema` | Full JSON Schema (Draft 2020-12) of a page source. |
|
|
505
|
+
|
|
506
|
+
### Generation
|
|
507
|
+
| Tool | Description |
|
|
508
|
+
|------|-------------|
|
|
509
|
+
| `new_element` | A structurally-valid default node for a type (fresh id). |
|
|
510
|
+
| `new_page_skeleton` | An empty but complete top-level source `{ page, popup, settings, options, cartConfigs }`. |
|
|
511
|
+
| `validate_page` | Structural + semantic validation (ids, event targets, containers, `field_name`). |
|
|
512
|
+
|
|
513
|
+
### Persistence (needs `WEBCAKE_API_BASE` + `WEBCAKE_JWT`)
|
|
514
|
+
| Tool | Description |
|
|
515
|
+
|------|-------------|
|
|
516
|
+
| `list_organizations` | List the account's organizations (id, name, is_default). Default = the `is_default` org. |
|
|
517
|
+
| `create_page` | Persist a generated source as a new page (source-only). **Defaults to `dry_run=true`.** |
|
|
518
|
+
| `list_pages` | List the account's pages (id, name, organization_id, updated_at) to pick one to edit. |
|
|
519
|
+
| `get_page` | Fetch an existing page's decoded source tree so you can edit it. |
|
|
520
|
+
| `update_page` | Overwrite an existing page's source with an edited tree. **Defaults to `dry_run=true`.** |
|
|
521
|
+
|
|
522
|
+
---
|
|
523
|
+
|
|
524
|
+
## Model notes
|
|
525
|
+
|
|
526
|
+
- **Absolute-positioning canvas:** every child carries numeric `top/left/width/height` per breakpoint;
|
|
527
|
+
sections stack vertically and own a `height`. Content lives in `specials` (`text`, `src`, …), never in `styles`.
|
|
528
|
+
- **Top-level source:** `{ page: [sections], popup: [popups], settings: {…}, options: { currency, mobileOnly, versionID }, cartConfigs: {} }`.
|
|
529
|
+
Popups are a **separate** top-level array, not nested in `page`.
|
|
530
|
+
- Per-breakpoint animation lives in `config.animation = { name, delay, duration, repeat }`.
|
|
531
|
+
- Colors are `rgba()`; `top/left/width/height/fontSize` are numbers (px); form inputs need a unique `specials.field_name`.
|
|
532
|
+
|
|
533
|
+
Reference: [docs/page-element-schema.md](docs/page-element-schema.md) and
|
|
534
|
+
[src/page-schema.json](src/page-schema.json) (the bundled JSON Schema, Draft 2020-12). The schema mirrors
|
|
535
|
+
the real editor `page_source` shape.
|