webcake-storefront-mcp 1.1.2 → 1.1.3
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/dist/index.js +1 -1
- package/dist/install.js +58 -16
- package/dist/legal.js +1 -1
- package/dist/web-guide.js +29 -24
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -8,7 +8,7 @@ Usage: npx -y webcake-storefront-mcp [command] [options]
|
|
|
8
8
|
|
|
9
9
|
Commands:
|
|
10
10
|
(none) start the stdio MCP server (use this in IDE configs)
|
|
11
|
-
install configure the server in your IDE(s) — interactive or via flags
|
|
11
|
+
install configure the server in your IDE(s) — interactive (env + browser login/token) or via flags
|
|
12
12
|
uninstall remove the server from your IDE configs
|
|
13
13
|
login grab your token via the browser (saved to the local config db)
|
|
14
14
|
serve [--port N] run the remote Streamable-HTTP server (default 8787; or PORT env)
|
package/dist/install.js
CHANGED
|
@@ -5,6 +5,7 @@ import { homedir } from "node:os";
|
|
|
5
5
|
import { dirname, join } from "node:path";
|
|
6
6
|
import { fileURLToPath } from "node:url";
|
|
7
7
|
import { createInterface } from "node:readline/promises";
|
|
8
|
+
import { runLogin } from "./auth/login.js";
|
|
8
9
|
const SERVER_KEY = "webcake-storefront";
|
|
9
10
|
function parseArgs(argv) {
|
|
10
11
|
const o = { uninstall: false, ides: [] };
|
|
@@ -100,34 +101,72 @@ function applyToIde(ide, opts, launch, env) {
|
|
|
100
101
|
writeJson(cfg.path, json);
|
|
101
102
|
return `${ide}: configured (${cfg.path})`;
|
|
102
103
|
}
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
104
|
+
/**
|
|
105
|
+
* Interactive wizard (TTY only): pick environment → authenticate (browser login,
|
|
106
|
+
* recommended, or paste a token) → pick IDEs. Mirrors webcake-landing-mcp's
|
|
107
|
+
* installer. Returns whether a browser login completed (token then lives in the
|
|
108
|
+
* local config db, so it is NOT written into the IDE env block).
|
|
109
|
+
*/
|
|
110
|
+
async function promptInteractive(opts) {
|
|
111
|
+
let loggedIn = false;
|
|
112
|
+
if (!process.stdin.isTTY || !process.stdout.isTTY)
|
|
113
|
+
return { loggedIn };
|
|
106
114
|
const rl = createInterface({ input: process.stdin, output: process.stderr });
|
|
107
115
|
try {
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
116
|
+
// 1) Environment — drives which API/app URLs are used (default prod).
|
|
117
|
+
if (!opts.uninstall && !opts.env && !process.env.WEBCAKE_ENV) {
|
|
118
|
+
const e = (await rl.question("Environment [prod] / staging / local: ")).trim().toLowerCase();
|
|
119
|
+
if (e === "staging" || e === "local")
|
|
120
|
+
opts.env = e;
|
|
111
121
|
}
|
|
122
|
+
if (opts.env)
|
|
123
|
+
process.env.WEBCAKE_ENV = opts.env; // so the login flow opens the right app
|
|
124
|
+
// 2) Authentication — browser login (recommended) or paste a token. An explicit
|
|
125
|
+
// --token/--jwt or an ambient WEBCAKE_TOKEN skips this entirely.
|
|
112
126
|
if (!opts.uninstall && !opts.token && !process.env.WEBCAKE_TOKEN) {
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
127
|
+
console.error("\nHow do you want to connect your WebCake account?");
|
|
128
|
+
console.error(" 1) Log in via browser (recommended — opens WebCake, saves a token)");
|
|
129
|
+
console.error(" 2) Paste a token manually");
|
|
130
|
+
const choice = (await rl.question("Choose [1]: ")).trim() || "1";
|
|
131
|
+
if (choice === "1") {
|
|
132
|
+
try {
|
|
133
|
+
rl.pause();
|
|
134
|
+
await runLogin([]); // loopback browser flow → saves token + session to local config db
|
|
135
|
+
loggedIn = true;
|
|
136
|
+
}
|
|
137
|
+
catch (e) {
|
|
138
|
+
console.error(`Login didn't complete (${e?.message ?? e}). Paste a token now, or run \`npx -y webcake-storefront-mcp login\` later.`);
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
if (!loggedIn && choice !== "1") {
|
|
142
|
+
const t = (await rl.question(" Token (paste JWT): ")).trim();
|
|
143
|
+
if (t)
|
|
144
|
+
opts.token = t;
|
|
145
|
+
const s = (await rl.question(" Session id (x-session-id): ")).trim();
|
|
146
|
+
if (s)
|
|
147
|
+
opts.sessionId = s;
|
|
148
|
+
}
|
|
116
149
|
}
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
150
|
+
// 3) IDEs to configure.
|
|
151
|
+
if (!opts.ides.length) {
|
|
152
|
+
const ans = (await rl.question(`\nIDE(s) to configure [${ALL_IDES.join(", ")}, all]: `)).trim();
|
|
153
|
+
opts.ides = ans === "all" || ans === "" ? ALL_IDES : ans.split(",").map((s) => s.trim());
|
|
121
154
|
}
|
|
122
155
|
// Site is chosen at runtime — use the list_my_sites / switch_site tools in chat.
|
|
123
156
|
}
|
|
124
157
|
finally {
|
|
125
|
-
|
|
158
|
+
try {
|
|
159
|
+
rl.close();
|
|
160
|
+
}
|
|
161
|
+
catch {
|
|
162
|
+
/* already closed */
|
|
163
|
+
}
|
|
126
164
|
}
|
|
165
|
+
return { loggedIn };
|
|
127
166
|
}
|
|
128
167
|
export async function runInstaller(argv) {
|
|
129
168
|
const opts = parseArgs(argv);
|
|
130
|
-
await
|
|
169
|
+
const { loggedIn } = await promptInteractive(opts);
|
|
131
170
|
let ides = opts.ides.length ? opts.ides : ALL_IDES;
|
|
132
171
|
if (ides.includes("all"))
|
|
133
172
|
ides = ALL_IDES;
|
|
@@ -136,6 +175,9 @@ export async function runInstaller(argv) {
|
|
|
136
175
|
console.error(opts.uninstall ? "Removing webcake-storefront MCP…" : "Configuring webcake-storefront MCP…");
|
|
137
176
|
for (const ide of ides)
|
|
138
177
|
console.error(" " + applyToIde(ide, opts, launch, env));
|
|
139
|
-
if (!opts.uninstall)
|
|
178
|
+
if (!opts.uninstall) {
|
|
179
|
+
if (loggedIn)
|
|
180
|
+
console.error("\n✓ Logged in — your token is saved to the local config (no token written into IDE files).");
|
|
140
181
|
console.error("\nDone. Restart your IDE to pick up the new MCP server.");
|
|
182
|
+
}
|
|
141
183
|
}
|
package/dist/legal.js
CHANGED
|
@@ -13,7 +13,7 @@ function page(title, bodyHtml) {
|
|
|
13
13
|
<style>
|
|
14
14
|
:root{color-scheme:light dark}
|
|
15
15
|
body{margin:0;font-family:system-ui,-apple-system,"Segoe UI",Roboto,sans-serif;line-height:1.65;color:#1e293b;background:#f8fafc}
|
|
16
|
-
@media(prefers-color-scheme:dark){body{color:#
|
|
16
|
+
@media(prefers-color-scheme:dark){body{color:#eaf1ee;background:#0f1714}a{color:#6fe6c0}}
|
|
17
17
|
main{max-width:760px;margin:0 auto;padding:48px 24px 80px}
|
|
18
18
|
h1{font-size:1.9rem;margin:0 0 4px}
|
|
19
19
|
h2{font-size:1.2rem;margin:32px 0 8px}
|
package/dist/web-guide.js
CHANGED
|
@@ -14,7 +14,10 @@
|
|
|
14
14
|
*
|
|
15
15
|
* Self-contained (inline CSS + JS, no external fonts/trackers) so it loads instantly.
|
|
16
16
|
*/
|
|
17
|
-
|
|
17
|
+
// The SPA page (on the builder app) that shows the user their personal remote
|
|
18
|
+
// connector link with login already built in — see builderx_spa McpRemoteStore.vue
|
|
19
|
+
// (/mcp-remote-store). The raw MCP endpoint itself is {ENDPOINT} = <origin>/mcp.
|
|
20
|
+
const MCP_REMOTE_URL = "https://webcake.io/mcp-remote-store";
|
|
18
21
|
const INSTALL_CMD = "npx -y webcake-storefront-mcp install";
|
|
19
22
|
const INSTALL_ALL_CMD = "npx -y webcake-storefront-mcp install --ide all --token <TOKEN> --session <SESSION>";
|
|
20
23
|
const GITHUB_URL = "https://github.com/vuluu2k/webcake-storefront-mcp";
|
|
@@ -226,15 +229,15 @@ const T = {
|
|
|
226
229
|
'<b>Mở lại ứng dụng AI.</b> Khi thấy <code class="inl">webcake-storefront</code> xuất hiện trong danh sách công cụ là bạn đã kết nối thành công — hãy thử nói "Tạo cho tôi trang sản phẩm…"',
|
|
227
230
|
],
|
|
228
231
|
m1Note: "Muốn cài cho nhiều ứng dụng cùng lúc — dùng lệnh này:",
|
|
229
|
-
m2Tag: "Cách ② · Dùng
|
|
230
|
-
m2Sub: "Phù hợp khi bạn dùng Claude trên web (claude.ai)
|
|
232
|
+
m2Tag: "Cách ② · Dùng link — không cần cài gì",
|
|
233
|
+
m2Sub: "Phù hợp khi bạn dùng Claude trên web (claude.ai), máy không cài được phần mềm, hoặc dùng theo nhóm.",
|
|
231
234
|
m2Steps: [
|
|
232
|
-
'<b>
|
|
233
|
-
'<b>
|
|
234
|
-
"<b>Dán
|
|
235
|
-
"<b>Bấm
|
|
235
|
+
'<b>Lấy link riêng của bạn</b> (đã gắn sẵn mã đăng nhập) — mở trang dưới đây rồi bấm <b>Copy</b>:<a class="btn" href="{REMOTE}">Mở {REMOTE_HOST} {ARROW}</a>',
|
|
236
|
+
'<b>Vào nơi thêm kết nối</b> trong ứng dụng:<br>• claude.ai: <i>Settings → Connectors → Add custom connector</i><br>• Cursor / Claude Code: mở file <code class="inl">.mcp.json</code>',
|
|
237
|
+
"<b>Dán link</b> bạn vừa copy (trông giống như):<pre>{ENDPOINT}?jwt=<MÃ CỦA BẠN>&session_id=<PHIÊN CỦA BẠN></pre>",
|
|
238
|
+
"<b>Bấm Add</b> (hoặc lưu file) rồi chờ một chút. Khi biểu tượng WebCake chuyển xanh là dùng được.",
|
|
236
239
|
],
|
|
237
|
-
m2Note: "
|
|
240
|
+
m2Note: "⚠️ Link có chứa mã đăng nhập riêng của bạn — hãy coi như mật khẩu, đừng chia sẻ cho ai.",
|
|
238
241
|
toolsH2: "Trợ lý có thể giúp bạn làm gì",
|
|
239
242
|
toolsSub: "Nói chuyện bình thường với trợ lý — bạn không cần biết tên công cụ hay lệnh nào cả.",
|
|
240
243
|
toolGroups: [
|
|
@@ -384,15 +387,15 @@ const T = {
|
|
|
384
387
|
'<b>Reopen your AI app.</b> When you see <code class="inl">webcake-storefront</code> in the tools list, you\'re connected — try saying "Create a product page for…"',
|
|
385
388
|
],
|
|
386
389
|
m1Note: "Want to set up multiple apps at once — use this command:",
|
|
387
|
-
m2Tag: "
|
|
388
|
-
m2Sub: "Best if you use Claude on the web (claude.ai)
|
|
390
|
+
m2Tag: "Way ② · Use a link — nothing to install",
|
|
391
|
+
m2Sub: "Best if you use Claude on the web (claude.ai), can't install software, or work as a team.",
|
|
389
392
|
m2Steps: [
|
|
390
|
-
'<b>
|
|
391
|
-
'<b>Open your
|
|
392
|
-
"<b>Paste the
|
|
393
|
-
"<b>Click Add</b> (or save the file). When the WebCake icon turns
|
|
393
|
+
'<b>Get your personal link</b> (your login is built in) — open the page below and hit <b>Copy</b>:<a class="btn" href="{REMOTE}">Open {REMOTE_HOST} {ARROW}</a>',
|
|
394
|
+
'<b>Open where you add a connection</b> in your app:<br>• claude.ai: <i>Settings → Connectors → Add custom connector</i><br>• Cursor / Claude Code: open <code class="inl">.mcp.json</code>',
|
|
395
|
+
"<b>Paste the link</b> you just copied (it looks like):<pre>{ENDPOINT}?jwt=<YOUR TOKEN>&session_id=<YOUR SESSION></pre>",
|
|
396
|
+
"<b>Click Add</b> (or save the file) and wait a moment. When the WebCake icon turns green, you're good to go.",
|
|
394
397
|
],
|
|
395
|
-
m2Note: "
|
|
398
|
+
m2Note: "⚠️ This link contains your personal login — treat it like a password and don't share it.",
|
|
396
399
|
toolsH2: "What your assistant can help you do",
|
|
397
400
|
toolsSub: "Just talk to your assistant naturally — you don't need to know any tool names or commands.",
|
|
398
401
|
toolGroups: [
|
|
@@ -504,8 +507,10 @@ export function guideHtml(origin, lang = "vi") {
|
|
|
504
507
|
],
|
|
505
508
|
};
|
|
506
509
|
const jsonLdScript = JSON.stringify(jsonLd).replace(/</g, "\\u003c");
|
|
510
|
+
const remoteHost = MCP_REMOTE_URL.replace("https://", "");
|
|
507
511
|
const fill = (s) => s
|
|
508
512
|
.replaceAll("{REMOTE}", MCP_REMOTE_URL)
|
|
513
|
+
.replaceAll("{REMOTE_HOST}", remoteHost)
|
|
509
514
|
.replaceAll("{ENDPOINT}", endpoint)
|
|
510
515
|
.replaceAll("{ARROW}", icon("arrow"));
|
|
511
516
|
return `<!doctype html>
|
|
@@ -546,10 +551,10 @@ export function guideHtml(origin, lang = "vi") {
|
|
|
546
551
|
:root{--g:#108B67;--g7:#0c6f52;--ink:#11121e;--mut:#5e5f7a;--bg:#f6f5ff;--card:#ffffff;
|
|
547
552
|
--line:rgba(16,14,40,.09);--shadow:0 1px 2px rgba(16,14,40,.05),0 6px 20px -12px rgba(16,14,40,.18);--code:#0e0d1a;
|
|
548
553
|
--ic-fg:#0c6f52;--btn-hover:#0c6f52;--navbg:rgba(246,245,255,.82)}
|
|
549
|
-
@media(prefers-color-scheme:dark){:root:not([data-theme="light"]){--ink:#
|
|
550
|
-
--line:rgba(255,255,255,.
|
|
551
|
-
:root[data-theme="dark"]{--ink:#
|
|
552
|
-
--line:rgba(255,255,255,.
|
|
554
|
+
@media(prefers-color-scheme:dark){:root:not([data-theme="light"]){--ink:#eaf1ee;--mut:#9fb0a9;--bg:#0f1714;--card:#18211d;
|
|
555
|
+
--line:rgba(255,255,255,.09);--shadow:0 1px 2px rgba(0,0,0,.35),0 12px 34px -16px rgba(0,0,0,.6);--code:#0b120f;--g:#16a37c;--g7:#6fe6c0;--ic-fg:#8aecc9;--btn-hover:#1cba8d;--navbg:rgba(15,23,20,.82)}}
|
|
556
|
+
:root[data-theme="dark"]{--ink:#eaf1ee;--mut:#9fb0a9;--bg:#0f1714;--card:#18211d;
|
|
557
|
+
--line:rgba(255,255,255,.09);--shadow:0 1px 2px rgba(0,0,0,.35),0 12px 34px -16px rgba(0,0,0,.6);--code:#0b120f;--g:#16a37c;--g7:#6fe6c0;--ic-fg:#8aecc9;--btn-hover:#1cba8d;--navbg:rgba(15,23,20,.82)}
|
|
553
558
|
*{box-sizing:border-box}
|
|
554
559
|
html{scroll-behavior:auto}
|
|
555
560
|
html.smooth{scroll-behavior:smooth}
|
|
@@ -605,12 +610,12 @@ export function guideHtml(origin, lang = "vi") {
|
|
|
605
610
|
text-transform:uppercase;letter-spacing:.04em;flex-wrap:wrap}
|
|
606
611
|
.tag .ic{width:30px;height:30px;border-radius:9px}
|
|
607
612
|
.tag .ic .i{width:16px;height:16px}
|
|
608
|
-
pre{margin:0;background:var(--code);color:#
|
|
613
|
+
pre{margin:0;background:var(--code);color:#e7efe9;border-radius:11px;padding:12px 14px;overflow-x:auto;
|
|
609
614
|
border:1px solid rgba(255,255,255,.06);font:600 .82rem/1.5 ui-monospace,SFMono-Regular,Menlo,monospace}
|
|
610
615
|
.codewrap{position:relative}
|
|
611
616
|
.codewrap pre{padding-right:46px}
|
|
612
617
|
.copy{position:absolute;top:8px;right:8px;width:30px;height:30px;display:grid;place-items:center;cursor:pointer;
|
|
613
|
-
border:1px solid rgba(255,255,255,.15);border-radius:8px;background:rgba(255,255,255,.06);color:#
|
|
618
|
+
border:1px solid rgba(255,255,255,.15);border-radius:8px;background:rgba(255,255,255,.06);color:#cdd8d2;
|
|
614
619
|
transition:background .15s ease,color .15s ease,border-color .15s ease}
|
|
615
620
|
.copy:hover{background:rgba(255,255,255,.13);color:#fff}
|
|
616
621
|
.copy svg{width:15px;height:15px}
|
|
@@ -910,7 +915,7 @@ export function ogImageSvg() {
|
|
|
910
915
|
return `<svg xmlns="http://www.w3.org/2000/svg" width="1200" height="630" viewBox="0 0 1200 630" fill="none" font-family="system-ui,-apple-system,Segoe UI,Roboto,sans-serif">
|
|
911
916
|
<defs>
|
|
912
917
|
<linearGradient id="bg" x1="0" y1="0" x2="1200" y2="630" gradientUnits="userSpaceOnUse">
|
|
913
|
-
<stop stop-color="#
|
|
918
|
+
<stop stop-color="#0f1714"/><stop offset="1" stop-color="#0c241c"/>
|
|
914
919
|
</linearGradient>
|
|
915
920
|
<radialGradient id="glow" cx="0" cy="0" r="1" gradientTransform="translate(960 70) rotate(130) scale(620)" gradientUnits="userSpaceOnUse">
|
|
916
921
|
<stop stop-color="#108B67" stop-opacity="0.40"/><stop offset="1" stop-color="#108B67" stop-opacity="0"/>
|
|
@@ -934,12 +939,12 @@ export function ogImageSvg() {
|
|
|
934
939
|
<text x="90" y="300" fill="#ffffff" font-size="64" font-weight="800" letter-spacing="-2">Bạn nói điều mình muốn —</text>
|
|
935
940
|
<text x="90" y="380" fill="#ffffff" font-size="64" font-weight="800" letter-spacing="-2">AI dựng trang, kiểm tra,</text>
|
|
936
941
|
<text x="90" y="460" fill="#108B67" font-size="64" font-weight="800" letter-spacing="-2">đăng lên là xong.</text>
|
|
937
|
-
<text x="90" y="534" fill="#
|
|
942
|
+
<text x="90" y="534" fill="#9fb0a9" font-size="28" font-weight="500">Không cần kéo-thả · Không cần biết lập trình · Luôn xem trước khi lưu</text>
|
|
938
943
|
<g transform="translate(90 560)">
|
|
939
944
|
<rect width="540" height="52" rx="12" fill="#108B67"/>
|
|
940
945
|
<text x="270" y="34" fill="#ffffff" font-size="22" font-weight="700" text-anchor="middle">store.toolvn.io.vn</text>
|
|
941
946
|
</g>
|
|
942
|
-
<text x="1110" y="600" fill="#
|
|
947
|
+
<text x="1110" y="600" fill="#5a7269" font-size="22" font-weight="600" text-anchor="end">github.com/vuluu2k/webcake-storefront-mcp</text>
|
|
943
948
|
</svg>`;
|
|
944
949
|
}
|
|
945
950
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "webcake-storefront-mcp",
|
|
3
|
-
"version": "1.1.
|
|
3
|
+
"version": "1.1.3",
|
|
4
4
|
"description": "MCP server for the WebCake/StoreCake storefront builder — page CRUD, page authoring, products, orders, and more",
|
|
5
5
|
"mcpName": "io.github.vuluu2k/webcake-storefront-mcp",
|
|
6
6
|
"license": "MIT",
|