webcake-landing-mcp 1.0.4 → 1.0.6

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 CHANGED
@@ -1,4 +1,50 @@
1
- # WebCake Landing MCP Server
1
+ # 🍰 WebCake Landing MCP
2
+
3
+ **English** · [Tiếng Việt](./README.vi.md)
4
+
5
+ > **Describe a landing page in plain words — your AI builds it, checks it, and ships it straight to WebCake.**
6
+
7
+ > *"Build a landing page for my coffee shop — a hero with a sign-up button, a 3-feature section, and a lead form. Save it to my workspace."*
8
+
9
+ …and a real, **editable** WebCake page appears in your account. No dragging boxes, no learning the schema, no hand-writing JSON.
10
+
11
+ ---
12
+
13
+ ## 🧩 How it works
14
+
15
+ This server is the **bridge** between your AI assistant and WebCake. The AI never *guesses* what a WebCake
16
+ page looks like — it asks this MCP, which knows the entire element model, validates the result, and saves it for you.
17
+
18
+ ```text
19
+ You AI assistant webcake-landing MCP WebCake
20
+ ┌──────┐ prompt ┌────────────┐ tools ┌──────────────────────┐ API ┌──────────┐
21
+ │ idea │ ───────► │ Claude / │ ──────► │ • knows the element │ ────► │ a real │
22
+ │ │ │ Cursor / │ │ model + AI hints │ │ editable │
23
+ │ │ ◄─────── │ Windsurf │ ◄────── │ • builds + validates │ ◄──── │ page in │
24
+ └──────┘ page URL └────────────┘ result │ • saves to your acct │ │ WebCake │
25
+ └──────────────────────┘ └──────────┘
26
+ ```
27
+
28
+ 1. **You ask** in plain language — goal, brand, sections, CTA, form fields.
29
+ 2. **The AI learns the model** from the MCP: the element catalog, the absolute-positioning canvas, the event vocabulary — so it builds a *real* WebCake page, not a guess.
30
+ 3. **It assembles + validates** the full `{ page, popup, settings, options }` JSON. `validate_page` catches off-canvas boxes, dangling CTAs, and missing form fields **before** anything is saved.
31
+ 4. **It persists** to your WebCake account — dry-run preview first, then for real.
32
+ 5. **You get an editor link** — open it, tweak, publish. The AI did the heavy lifting.
33
+
34
+ ### Why it's reliable
35
+
36
+ | | |
37
+ |---|---|
38
+ | 📚 **Knows the real model** | Serves WebCake's actual element catalog (40+ types — hero, form, countdown, gallery, product list…), each with its exact `specials` and AI hints, drawn straight from the editor's renderers. |
39
+ | ✅ **Validates before saving** | Structural + semantic checks (unique ids, on-canvas layout, working CTAs, unique form fields) so the page isn't broken when it lands. |
40
+ | 🛡️ **Safe by default** | Every write is **dry-run first** (preview the request, token masked) — nothing touches your account until you confirm. |
41
+ | ✏️ **Edits surgically** | Ask for one change ("make the CTA green") and it edits *only* that element — every other id, coordinate, and block stays exactly as it was. |
42
+
43
+ > 💡 **Lead-gen, events, invitations, app promos** — or **selling COD/online**? It speaks WebCake's commerce model too (product lists, variations, cart).
44
+
45
+ ---
46
+
47
+ ## Under the hood
2
48
 
3
49
  MCP (Model Context Protocol) server that teaches AI agents how to build a complete
4
50
  **WebCake landing-page source JSON** from a requirement — and persist it to a WebCake backend.
@@ -144,7 +190,7 @@ The MCP config is the same as the local one, but `command`/`args` point at `npx`
144
190
  git clone https://github.com/vuluu2k/webcake-landing-mcp.git
145
191
  cd webcake-landing-mcp
146
192
  npm install # postinstall `prepare` builds dist/ automatically
147
- npm run build # (re)build: tsc -> dist/ + copies page-schema.json
193
+ npm run build # (re)build: tsc -> dist/ + copies src/**/*.json (page-schema.json) into dist/
148
194
  npm run smoke # offline self-test of factory + validator (prints "ALL GOOD")
149
195
  ```
150
196
 
@@ -557,5 +603,5 @@ Both `create_page` and `update_page` **default to `dry_run=true`** (validate and
557
603
  - Colors are `rgba()`; `top/left/width/height/fontSize` are numbers (px); form inputs need a unique `specials.field_name`.
558
604
 
559
605
  Reference: [docs/page-element-schema.md](docs/page-element-schema.md) and
560
- [src/page-schema.json](src/page-schema.json) (the bundled JSON Schema, Draft 2020-12). The schema mirrors
606
+ [src/domains/landing/page-schema.json](src/domains/landing/page-schema.json) (the bundled JSON Schema, Draft 2020-12). The schema mirrors
561
607
  the real editor `page_source` shape.
package/README.vi.md ADDED
@@ -0,0 +1,608 @@
1
+ # 🍰 WebCake Landing MCP
2
+
3
+ [English](./README.md) · **Tiếng Việt**
4
+
5
+ > **Mô tả landing page bằng lời nói — AI tự dựng, tự kiểm tra và đẩy thẳng lên WebCake.**
6
+
7
+ > *"Dựng cho tôi một landing page quán cà phê — một hero có nút đăng ký, một mục 3 tính năng, và một form thu lead. Lưu vào workspace của tôi."*
8
+
9
+ …và một trang WebCake **thật, sửa được** hiện ra trong tài khoản của bạn. Không kéo-thả từng khối, không cần học schema, không phải tự viết JSON.
10
+
11
+ ---
12
+
13
+ ## 🧩 Mô hình hoạt động
14
+
15
+ Server này là **cầu nối** giữa trợ lý AI và WebCake. AI không *đoán* trang WebCake trông thế nào —
16
+ nó hỏi MCP (vốn nắm trọn mô hình element), kiểm tra hợp lệ, rồi lưu giúp bạn.
17
+
18
+ ```text
19
+ Bạn Trợ lý AI webcake-landing MCP WebCake
20
+ ┌──────┐ yêu cầu┌────────────┐ tools ┌──────────────────────┐ API ┌──────────┐
21
+ │ ý │ ───────►│ Claude / │ ──────► │ • nắm mô hình element│ ────► │ trang │
22
+ │ tưởng│ │ Cursor / │ │ + gợi ý cho AI │ │ thật, │
23
+ │ │ ◄───────│ Windsurf │ ◄────── │ • dựng + kiểm tra │ ◄──── │ sửa được│
24
+ └──────┘ link └────────────┘ kết quả │ • lưu vào tài khoản │ │ trên │
25
+ trang └──────────────────────┘ │ WebCake │
26
+ └──────────┘
27
+ ```
28
+
29
+ 1. **Bạn yêu cầu** bằng lời — mục tiêu, thương hiệu, các section, nút CTA, trường form.
30
+ 2. **AI học mô hình** từ MCP: danh mục element, canvas toạ độ tuyệt đối, bộ sự kiện — nên nó dựng trang WebCake *thật*, không phải đoán.
31
+ 3. **Dựng + kiểm tra** trọn JSON `{ page, popup, settings, options }`. `validate_page` bắt lỗi (element lệch khung, CTA trỏ sai, thiếu trường form) **trước khi** lưu.
32
+ 4. **Lưu** vào tài khoản WebCake — xem trước dry-run, rồi mới lưu thật.
33
+ 5. **Nhận link editor** — mở, chỉnh, publish. AI lo phần nặng.
34
+
35
+ ### Vì sao đáng tin
36
+
37
+ | | |
38
+ |---|---|
39
+ | 📚 **Nắm đúng mô hình** | Cung cấp danh mục element thật của WebCake (40+ loại — hero, form, đếm ngược, gallery, danh sách sản phẩm…), mỗi loại kèm `specials` chính xác và gợi ý cho AI, rút thẳng từ renderer của editor. |
40
+ | ✅ **Kiểm tra trước khi lưu** | Kiểm tra cấu trúc + ngữ nghĩa (id duy nhất, layout trong khung, CTA hoạt động, trường form không trùng) để trang không hỏng khi lưu. |
41
+ | 🛡️ **An toàn mặc định** | Mọi thao tác ghi đều **dry-run trước** (xem trước request, token được che) — không đụng tài khoản của bạn cho tới khi bạn xác nhận. |
42
+ | ✏️ **Sửa đúng chỗ** | Yêu cầu một thay đổi ("đổi nút CTA sang xanh") thì nó chỉ sửa *đúng* element đó — mọi id, toạ độ, khối khác giữ nguyên. |
43
+
44
+ > 💡 **Thu lead, sự kiện, thiệp mời, quảng bá app** — hay **bán hàng COD/online**? Nó hiểu cả mô hình thương mại của WebCake (danh sách sản phẩm, biến thể, giỏ hàng).
45
+
46
+ ---
47
+
48
+ ## Bản chất kỹ thuật
49
+
50
+ Server MCP (Model Context Protocol) dạy AI cách dựng trọn **JSON nguồn (page_source) của landing page WebCake**
51
+ từ một yêu cầu — và lưu nó về backend WebCake.
52
+
53
+ Nó expose danh mục element, gợi ý dùng từng element + `specials`, JSON Schema đầy đủ của trang, skeleton
54
+ element/trang hợp lệ, bộ kiểm tra trang, và các tool để tạo/sửa trang trên backend. AI dựng trọn JSON
55
+ `{ page, popup, settings, options, cartConfigs }`; `create_page` lưu nó (chỉ-source — trang mở trong editor,
56
+ lưu lại sẽ render).
57
+
58
+ ## Hai cách chạy
59
+
60
+ | Chế độ | Lệnh | Khi nào |
61
+ |------|------|------|
62
+ | **CDN / npx** (không clone) | `npx -y webcake-landing-mcp` | Khởi động nhanh nhất — npm tự tải & chạy, không cần clone hay build. Tự cập nhật bản mới nhất. |
63
+ | **Local** (clone & build) | `node /abs/path/dist/index.js` | Khi đang sửa server, offline, hoặc cần ghim một bản build cụ thể. Chạy `npm run build` trước. |
64
+
65
+ Cả hai cùng expose y hệt các tool. Mọi cấu hình IDE bên dưới dùng dạng **local**; để dùng **CDN**, chỉ cần
66
+ đổi `command`/`args` sang dạng npx (xem [Chạy không cần clone (npx)](#chạy-không-cần-clone-npx)).
67
+
68
+ ## Cài nhanh (Khuyến nghị)
69
+
70
+ Chạy script tự cài — lo trọn gói: clone, cài dependencies, build, và cấu hình IDE của bạn.
71
+
72
+ ### macOS / Linux
73
+
74
+ Nếu bạn đã clone repo:
75
+ ```bash
76
+ ./install.sh
77
+ ```
78
+
79
+ Hoặc tải & chạy trực tiếp:
80
+ ```bash
81
+ curl -fsSL https://raw.githubusercontent.com/vuluu2k/webcake-landing-mcp/main/install.sh -o install.sh && bash install.sh
82
+ ```
83
+
84
+ Trình cài tương tác: hỏi nơi cài (mặc định `~/.webcake-landing-mcp`), hỏi các biến môi trường
85
+ (`WEBCAKE_API_BASE`, `WEBCAKE_JWT`, `WEBCAKE_ORG_ID` — đều tuỳ chọn, Enter để bỏ qua), rồi cho bạn chọn
86
+ IDE cần cấu hình: `claude-desktop`, `claude-code`, `cursor`, `windsurf`, `augment`, `codex`, hoặc tất cả.
87
+
88
+ Gỡ cài (xoá entry MCP server khỏi mọi IDE đã cấu hình):
89
+ ```bash
90
+ ./install.sh --uninstall
91
+ ```
92
+
93
+ ### Windows (PowerShell)
94
+
95
+ Nếu bạn đã clone repo:
96
+ ```powershell
97
+ .\install.ps1
98
+ ```
99
+
100
+ Hoặc tải & chạy trực tiếp:
101
+ ```powershell
102
+ irm https://raw.githubusercontent.com/vuluu2k/webcake-landing-mcp/main/install.ps1 -OutFile install.ps1; .\install.ps1
103
+ ```
104
+
105
+ Gỡ cài:
106
+ ```powershell
107
+ .\install.ps1 --uninstall
108
+ ```
109
+
110
+ ---
111
+
112
+ ## Cập nhật
113
+
114
+ Cập nhật lên bản mới nhất:
115
+
116
+ ```bash
117
+ cd ~/.webcake-landing-mcp # hoặc nơi bạn đã cài
118
+ git pull
119
+ npm install
120
+ npm run build
121
+ ```
122
+
123
+ Rồi khởi động lại IDE.
124
+
125
+ ---
126
+
127
+ ## Chạy không cần clone (npx)
128
+
129
+ Sau khi đã publish lên npm, server chạy thẳng từ registry — không clone, không build:
130
+
131
+ ```bash
132
+ npx -y webcake-landing-mcp
133
+ ```
134
+
135
+ Hoặc chạy bản mới nhất từ GitHub (npx tự clone + build qua script `prepare`):
136
+
137
+ ```bash
138
+ npx -y github:vuluu2k/webcake-landing-mcp
139
+ ```
140
+
141
+ ### Tự cấu hình IDE (lệnh con `install`)
142
+
143
+ `npx` chỉ **chạy** server — khác với `install.sh`/`install.ps1`, nó không ghi cấu hình MCP vào IDE.
144
+ Lệnh con `install` đi kèm sẽ làm hộ bạn bước đó, không cần clone:
145
+
146
+ ```bash
147
+ # Tương tác — hỏi env + chọn IDE từng bước
148
+ npx -y webcake-landing-mcp install
149
+
150
+ # Không tương tác — cấu hình mọi IDE hỗ trợ cùng lúc
151
+ npx -y webcake-landing-mcp install --ide all --jwt <your-jwt> --api-base http://localhost:5800
152
+
153
+ # Chỉ một IDE
154
+ npx -y webcake-landing-mcp install --ide cursor --jwt <your-jwt>
155
+
156
+ # Gỡ server khỏi mọi cấu hình IDE
157
+ npx -y webcake-landing-mcp uninstall
158
+ ```
159
+
160
+ Nó ghi entry `webcake-landing` (dùng dạng khởi chạy `npx` bên dưới) vào đúng file cấu hình của từng IDE:
161
+ `claude-desktop`, `claude-code`, `cursor`, `windsurf`, `augment` (VS Code), `codex`, hoặc `all`. Cờ:
162
+ `--ide`, `--api-base`, `--jwt`, `--org-id`, `--host`, `--app-base`, `--npx`/`--local`, `-y`. Chạy
163
+ `npx -y webcake-landing-mcp --help` để xem đầy đủ.
164
+
165
+ ### Cấu hình thủ công
166
+
167
+ Cấu hình MCP giống bản local, chỉ khác `command`/`args` trỏ tới `npx` thay vì file đã build:
168
+
169
+ ```json
170
+ {
171
+ "mcpServers": {
172
+ "webcake-landing": {
173
+ "command": "npx",
174
+ "args": ["-y", "webcake-landing-mcp"],
175
+ "env": {
176
+ "WEBCAKE_API_BASE": "http://localhost:5800",
177
+ "WEBCAKE_JWT": "<your-jwt>"
178
+ }
179
+ }
180
+ }
181
+ }
182
+ ```
183
+
184
+ > npx cache lại package sau lần chạy đầu, nên các lần sau khởi động nhanh. Dùng phiên bản ghim
185
+ > (`webcake-landing-mcp@1.0.0`) nếu cần build tái lập được.
186
+
187
+ ## Cài thủ công (local)
188
+
189
+ ```bash
190
+ git clone https://github.com/vuluu2k/webcake-landing-mcp.git
191
+ cd webcake-landing-mcp
192
+ npm install # postinstall `prepare` tự build dist/
193
+ npm run build # (re)build: tsc -> dist/ + copy src/**/*.json (page-schema.json) vào dist/
194
+ npm run smoke # self-test offline của factory + validator (in "ALL GOOD")
195
+ ```
196
+
197
+ Các tool tham chiếu/kiểm tra chạy với **zero config**. Biến môi trường chỉ cần cho các tool lưu trữ
198
+ (`create_page`, `update_page`, `list_pages`, `get_page`, `list_organizations`).
199
+
200
+ ## Biến môi trường
201
+
202
+ | Biến | Bắt buộc | Mô tả |
203
+ |----------|----------|-------------|
204
+ | `WEBCAKE_API_BASE` | Không* | Base URL backend, ví dụ `http://localhost:5800`. Cần để lưu trang. |
205
+ | `WEBCAKE_JWT` | Không* | JWT tài khoản (auth dashboard). Cần để lưu trang — sẽ hết hạn, làm mới khi cần. |
206
+ | `WEBCAKE_ORG_ID` | Không | Organization mặc định cho `create_page` (bị ghi đè bởi tham số `organization_id`). Bỏ trống → trang cá nhân. |
207
+ | `WEBCAKE_HOST` | Không | Header `Host` tuỳ chọn (Phoenix route theo host, ví dụ `builder.localhost`). |
208
+ | `WEBCAKE_APP_BASE` | Không | Base tuỳ chọn để dựng URL editor/preview trong kết quả. |
209
+
210
+ > \* `WEBCAKE_API_BASE` và `WEBCAKE_JWT` chỉ cần cho các tool lưu trữ. Các tool tham chiếu và kiểm tra
211
+ > (`get_generation_guide`, `list_elements`, `get_element`, `validate_page`, …) chạy không cần chúng.
212
+
213
+ > Lưu trang sẽ ghi một trang thật vào nơi `WEBCAKE_API_BASE` trỏ tới, dùng JWT làm tài khoản đó.
214
+ > Hãy bắt đầu với local/staging.
215
+
216
+ ### Cách lấy `WEBCAKE_JWT`
217
+
218
+ 1. Mở dashboard builder WebCake và đăng nhập
219
+ 2. Mở DevTools (`F12` hoặc `Cmd + Option + I`)
220
+ 3. Vào tab **Network** > click một trang bất kỳ
221
+ 4. Tìm một request API (ví dụ `@me`, `organizations`…)
222
+ 5. Trong **Request Headers**, copy giá trị sau `Authorization: Bearer ` → đó là `WEBCAKE_JWT`
223
+ 6. Dùng tool `list_organizations` để liệt kê org và chọn `WEBCAKE_ORG_ID`
224
+
225
+ ---
226
+
227
+ ## Cấu hình theo IDE / công cụ AI
228
+
229
+ > Thay `/absolute-path/webcake-landing-mcp/dist/index.js` bên dưới bằng đường dẫn thật nơi bạn đã
230
+ > clone/build repo. Ví dụ: `/Users/username/webcake-landing-mcp/dist/index.js`.
231
+ > Chạy `npm run build` trước để `dist/` tồn tại.
232
+
233
+ ### 1. Claude Desktop
234
+
235
+ Mở Settings > Developer > Edit Config, hoặc sửa file trực tiếp:
236
+
237
+ - **macOS**: `~/Library/Application Support/Claude/claude_desktop_config.json`
238
+ - **Windows**: `%APPDATA%\Claude\claude_desktop_config.json`
239
+ - **Linux**: `~/.config/Claude/claude_desktop_config.json`
240
+
241
+ ```json
242
+ {
243
+ "mcpServers": {
244
+ "webcake-landing": {
245
+ "command": "node",
246
+ "args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
247
+ "env": {
248
+ "WEBCAKE_API_BASE": "http://localhost:5800",
249
+ "WEBCAKE_JWT": "<your-jwt>",
250
+ "WEBCAKE_HOST": "builder.localhost",
251
+ "WEBCAKE_APP_BASE": "http://builder.localhost:5800"
252
+ }
253
+ }
254
+ }
255
+ }
256
+ ```
257
+
258
+ Khởi động lại Claude Desktop. Các tool MCP sẽ hiện trong ô chat (biểu tượng búa).
259
+
260
+ ---
261
+
262
+ ### 2. Claude Code (CLI)
263
+
264
+ Chạy trong terminal — bản **local**:
265
+
266
+ ```bash
267
+ claude mcp add webcake-landing \
268
+ -e WEBCAKE_API_BASE=http://localhost:5800 \
269
+ -e WEBCAKE_JWT=<your-jwt> \
270
+ -e WEBCAKE_HOST=builder.localhost \
271
+ -- node /absolute-path/webcake-landing-mcp/dist/index.js
272
+ ```
273
+
274
+ Hoặc **CDN / npx** (không clone):
275
+
276
+ ```bash
277
+ claude mcp add webcake-landing \
278
+ -e WEBCAKE_API_BASE=http://localhost:5800 \
279
+ -e WEBCAKE_JWT=<your-jwt> \
280
+ -- npx -y webcake-landing-mcp
281
+ ```
282
+
283
+ Hoặc tạo `.claude.json` ở thư mục gốc dự án (hoặc `~/.claude.json` toàn cục):
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
+ Kiểm tra:
301
+ ```bash
302
+ claude mcp list
303
+ ```
304
+
305
+ ---
306
+
307
+ ### 3. Cursor
308
+
309
+ Tạo `.cursor/mcp.json` ở gốc dự án (hoặc `~/.cursor/mcp.json` toàn cục):
310
+
311
+ ```json
312
+ {
313
+ "mcpServers": {
314
+ "webcake-landing": {
315
+ "command": "node",
316
+ "args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
317
+ "env": {
318
+ "WEBCAKE_API_BASE": "http://localhost:5800",
319
+ "WEBCAKE_JWT": "<your-jwt>"
320
+ }
321
+ }
322
+ }
323
+ }
324
+ ```
325
+
326
+ Khởi động lại Cursor và xem Settings > MCP Servers để thấy trạng thái **"Connected"**.
327
+
328
+ ---
329
+
330
+ ### 4. Windsurf
331
+
332
+ Tạo `~/.codeium/windsurf/mcp_config.json`:
333
+
334
+ ```json
335
+ {
336
+ "mcpServers": {
337
+ "webcake-landing": {
338
+ "command": "node",
339
+ "args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
340
+ "env": {
341
+ "WEBCAKE_API_BASE": "http://localhost:5800",
342
+ "WEBCAKE_JWT": "<your-jwt>"
343
+ }
344
+ }
345
+ }
346
+ }
347
+ ```
348
+
349
+ Khởi động lại Windsurf. Gõ `@` trong chat Cascade để thấy các tool `webcake-landing`.
350
+
351
+ ---
352
+
353
+ ### 5. Augment (Extension VS Code)
354
+
355
+ Mở Command Palette: `Cmd + Shift + P` > **"Augment: Edit MCP Settings"**, rồi thêm:
356
+
357
+ ```json
358
+ {
359
+ "mcpServers": {
360
+ "webcake-landing": {
361
+ "command": "node",
362
+ "args": ["/absolute-path/webcake-landing-mcp/dist/index.js"],
363
+ "env": {
364
+ "WEBCAKE_API_BASE": "http://localhost:5800",
365
+ "WEBCAKE_JWT": "<your-jwt>"
366
+ }
367
+ }
368
+ }
369
+ }
370
+ ```
371
+
372
+ Khởi động lại VS Code.
373
+
374
+ ---
375
+
376
+ ### 6. Codex (OpenAI CLI)
377
+
378
+ Thêm vào `~/.codex/config.toml`:
379
+
380
+ ```toml
381
+ [mcp_servers.webcake-landing]
382
+ command = "node"
383
+ args = ["/absolute-path/webcake-landing-mcp/dist/index.js"]
384
+ env = { "WEBCAKE_API_BASE" = "http://localhost:5800", "WEBCAKE_JWT" = "<your-jwt>" }
385
+ ```
386
+
387
+ Kiểm tra:
388
+ ```bash
389
+ codex mcp list
390
+ ```
391
+
392
+ ---
393
+
394
+ ## Ví dụ sử dụng
395
+
396
+ ### Ví dụ 1: Dựng landing page mới từ một brief
397
+
398
+ **Prompt:**
399
+ ```
400
+ Dựng cho tôi một landing page WebCake cho "Acme Coffee" — một hero có CTA, một mục 3 tính năng,
401
+ và một form đăng ký. Lưu vào org mặc định của tôi.
402
+ ```
403
+
404
+ **AI sẽ tự động:**
405
+
406
+ **Bước 1** — Gọi `get_generation_guide` để học quy ước (canvas, hệ toạ độ, sự kiện, workflow)
407
+
408
+ **Bước 2** — Gọi `new_page_skeleton` để có source top-level rỗng, rồi `get_element` cho từng loại element nó dùng:
409
+
410
+ ```
411
+ get_element({ type: "section" })
412
+ get_element({ type: "text-block" })
413
+ get_element({ type: "button" })
414
+ get_element({ type: "form" })
415
+ ```
416
+
417
+ **Bước 3** — Lắp trọn JSON `{ page, popup, settings, options, cartConfigs }`, rồi kiểm tra:
418
+
419
+ ```
420
+ validate_page({ source })
421
+ → { ok: false, errors: ["BUTTON-2: event target 'POPUP-9' not found"] } # sửa hết lỗi, validate lại
422
+ validate_page({ source })
423
+ → { ok: true, errors: [] }
424
+ ```
425
+
426
+ **Bước 4** — Lưu (dry-run trước, rồi mới thật):
427
+
428
+ ```
429
+ list_organizations({}) → chọn org
430
+ create_page({ source }) → xem trước dry-run (JWT được che)
431
+ create_page({ source, dry_run: false }) → { page_id, editor_url, preview_url }
432
+ ```
433
+
434
+ Mở trang trong editor và lưu lại để render `app`/`app_css`.
435
+
436
+ ---
437
+
438
+ ### Ví dụ 2: Sửa một trang có sẵn
439
+
440
+ **Prompt:**
441
+ ```
442
+ Trên landing page "Acme Coffee" của tôi, đổi headline hero thành "Freshly Roasted Daily"
443
+ và làm nút CTA màu xanh lá.
444
+ ```
445
+
446
+ **AI sửa đúng chỗ — không bao giờ dựng lại cả cây:**
447
+
448
+ ```
449
+ # Bước 1: tìm trang
450
+ list_pages({})
451
+ → [{ id: "page_42", name: "Acme Coffee", organization_id: "org_1", ... }]
452
+
453
+ # Bước 2: lấy cây source đã decode
454
+ get_page({ page_id: "page_42" })
455
+
456
+ # Bước 3: chỉ đổi text headline + màu nút, giữ mọi id/toạ độ khác,
457
+ # rồi validate và ghi lại
458
+ validate_page({ source }) → ok
459
+ update_page({ page_id: "page_42", source }) → xem trước dry-run
460
+ update_page({ page_id: "page_42", source, dry_run: false })
461
+ ```
462
+
463
+ ---
464
+
465
+ ### Ví dụ 3: Xem chi tiết một loại element trước khi dùng
466
+
467
+ **Prompt:**
468
+ ```
469
+ Một element form cần những specials gì, và cho tôi xem một ví dụ hợp lệ.
470
+ ```
471
+
472
+ **AI gọi:**
473
+
474
+ ```
475
+ get_element({ type: "form" })
476
+ → {
477
+ hints: "Mỗi input cần một specials.field_name duy nhất…",
478
+ specials: { ... },
479
+ skeleton: { ... }, # node mặc định hợp lệ về cấu trúc
480
+ example: { ... } # ví dụ đã điền, thực tế
481
+ }
482
+ ```
483
+
484
+ ---
485
+
486
+ ## Hướng dẫn dùng tool chi tiết
487
+
488
+ Các tool chia thành ba nhóm: **tham chiếu** (học mô hình — không cần config),
489
+ **generation** (dựng node hợp lệ), và **lưu trữ** (ghi về backend — cần biến môi trường).
490
+
491
+ ### Bước 1: Đọc guide trước — `get_generation_guide`
492
+
493
+ Luôn gọi cái này **đầu tiên**. Nó trả về hình dạng output, hệ toạ độ (desktop ≈ 960px,
494
+ mobile ≈ 420px), bộ từ vựng sự kiện, và workflow đầu-cuối.
495
+
496
+ ```
497
+ get_generation_guide({})
498
+ → "## Output shape… ## Canvas… ## Events… ## Workflow…"
499
+ ```
500
+
501
+ ### Bước 2: Duyệt danh mục element — `list_elements` / `get_element`
502
+
503
+ ```
504
+ # Mọi loại element theo nhóm (tóm tắt + khi nào dùng + có phải container?)
505
+ list_elements({})
506
+ → { categories: { layout: [...], content: [...], form: [...], ... } }
507
+
508
+ # Xem sâu một loại — hints, specials chính, skeleton mặc định, ví dụ đã điền
509
+ get_element({ type: "button" })
510
+ ```
511
+
512
+ ### Bước 3: Lấy khối dựng hợp lệ — `new_element` / `new_page_skeleton`
513
+
514
+ ```
515
+ # Một node mặc định hợp lệ về cấu trúc cho một loại (id mới)
516
+ new_element({ type: "section" })
517
+
518
+ # Một source top-level rỗng nhưng đầy đủ
519
+ new_page_skeleton({})
520
+ → { page: [], popup: [], settings: {…}, options: { currency, mobileOnly, versionID }, cartConfigs: {} }
521
+ ```
522
+
523
+ ### Bước 4: Xem / kiểm tra — `get_page_schema` / `validate_page`
524
+
525
+ ```
526
+ # JSON Schema đầy đủ (Draft 2020-12) của một page source
527
+ get_page_schema({})
528
+
529
+ # Kiểm tra cấu trúc + ngữ nghĩa — sửa hết lỗi trước khi lưu
530
+ validate_page({ source })
531
+ → { ok: false, errors: [...], warnings: [...] }
532
+ ```
533
+
534
+ `validate_page` **errors là chặn**; warnings (event target lửng lơ, thiếu `field_name`) chỉ là khuyến cáo.
535
+
536
+ ### Bước 5: Lưu — `list_organizations` / `create_page` / `update_page`
537
+
538
+ ```
539
+ # Liệt kê các organization của tài khoản — hỏi dùng cái nào; mặc định = org is_default
540
+ list_organizations({})
541
+ → [{ id: "org_1", name: "Acme", is_default: true }, ...]
542
+
543
+ # Tạo trang MỚI (chỉ-source). Mặc định dry_run=true.
544
+ create_page({ source, organization_id: "org_1" }) # xem trước
545
+ create_page({ source, dry_run: false }) # tạo thật
546
+
547
+ # Sửa một trang CÓ SẴN
548
+ list_pages({}) # tìm trang
549
+ get_page({ page_id }) # lấy source đã decode
550
+ update_page({ page_id, source, dry_run: false }) # ghi đè (mặc định dry_run=true)
551
+ ```
552
+
553
+ `create_page` gọi **`POST {WEBCAKE_API_BASE}/api/v1/ai/create_page_from_source`** trên backend.
554
+ Cả `create_page` và `update_page` đều **mặc định `dry_run=true`** (kiểm tra và trả về request nó *sẽ*
555
+ gửi, JWT được che); đặt `dry_run=false` để ghi thật. Kết quả trả về `page_id` + URL editor/preview.
556
+
557
+ ---
558
+
559
+ ## Prompt gợi ý
560
+
561
+ > Dựng cho tôi một landing page WebCake cho &lt;thương hiệu/ưu đãi&gt;. Dùng MCP webcake-landing:
562
+ > gọi `get_generation_guide`, `new_page_skeleton`, rồi `get_element` cho từng loại element bạn dùng,
563
+ > lắp JSON `{ page, popup, settings, options }`, `validate_page` đến khi 0 lỗi,
564
+ > rồi `create_page` (dry-run trước).
565
+
566
+ ---
567
+
568
+ ## Danh sách tool
569
+
570
+ ### Tham chiếu (không cần config)
571
+ | Tool | Mô tả |
572
+ |------|-------------|
573
+ | `get_generation_guide` | **Đọc ĐẦU TIÊN.** Hình dạng output, hệ toạ độ, bộ sự kiện, workflow. |
574
+ | `list_elements` | Mọi loại element theo nhóm (tóm tắt + khi nào dùng + container?). |
575
+ | `get_element` | Một loại: hints, `specials` chính, skeleton mặc định, ví dụ đã điền. |
576
+ | `get_page_schema` | JSON Schema đầy đủ (Draft 2020-12) của một page source. |
577
+
578
+ ### Generation
579
+ | Tool | Mô tả |
580
+ |------|-------------|
581
+ | `new_element` | Một node mặc định hợp lệ về cấu trúc cho một loại (id mới). |
582
+ | `new_page_skeleton` | Một source top-level rỗng nhưng đầy đủ `{ page, popup, settings, options, cartConfigs }`. |
583
+ | `validate_page` | Kiểm tra cấu trúc + ngữ nghĩa (ids, event targets, containers, `field_name`). |
584
+
585
+ ### Lưu trữ (cần `WEBCAKE_API_BASE` + `WEBCAKE_JWT`)
586
+ | Tool | Mô tả |
587
+ |------|-------------|
588
+ | `list_organizations` | Liệt kê organization của tài khoản (id, name, is_default). Mặc định = org `is_default`. |
589
+ | `create_page` | Lưu một source đã sinh thành trang mới (chỉ-source). **Mặc định `dry_run=true`.** |
590
+ | `list_pages` | Liệt kê các trang của tài khoản (id, name, organization_id, updated_at) để chọn cái cần sửa. |
591
+ | `get_page` | Lấy cây source đã decode của một trang có sẵn để sửa. |
592
+ | `update_page` | Ghi đè source của một trang có sẵn bằng cây đã sửa. **Mặc định `dry_run=true`.** |
593
+
594
+ ---
595
+
596
+ ## Ghi chú về mô hình
597
+
598
+ - **Canvas toạ độ tuyệt đối:** mỗi phần tử con mang `top/left/width/height` dạng số theo từng breakpoint;
599
+ section xếp dọc và tự giữ `height`. Nội dung nằm trong `specials` (`text`, `src`, …), không bao giờ trong `styles`.
600
+ - **Source top-level:** `{ page: [sections], popup: [popups], settings: {…}, options: { currency, mobileOnly, versionID }, cartConfigs: {} }`.
601
+ Popup là một mảng top-level **riêng**, không lồng trong `page`.
602
+ - Animation theo breakpoint nằm trong `config.animation = { name, delay, duration, repeat }`.
603
+ - Màu dạng `rgba()`; `top/left/width/height/fontSize` là số (px); input form cần một `specials.field_name` duy nhất.
604
+
605
+ Tham khảo: [docs/page-element-schema.md](docs/page-element-schema.md),
606
+ [docs/element-specials-reference.md](docs/element-specials-reference.md) (tham chiếu đầy đủ mọi specials/event),
607
+ và [src/domains/landing/page-schema.json](src/domains/landing/page-schema.json) (JSON Schema, Draft 2020-12). Schema phản ánh đúng
608
+ hình dạng `page_source` thật của editor.