@mp3wizard/figma-console-mcp 1.25.1 → 1.27.2
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 +49 -33
- package/dist/cloudflare/core/config.js +0 -8
- package/dist/cloudflare/core/console-monitor.js +3 -3
- package/dist/cloudflare/core/diagnose-tool.js +96 -0
- package/dist/cloudflare/core/figma-tools.js +69 -229
- package/dist/cloudflare/core/identity.js +96 -0
- package/dist/cloudflare/core/tokens/alias-resolver.js +98 -0
- package/dist/cloudflare/core/tokens/config.js +284 -0
- package/dist/cloudflare/core/tokens/figma-converter.js +195 -0
- package/dist/cloudflare/core/tokens/formatters/css-vars.js +329 -0
- package/dist/cloudflare/core/tokens/formatters/dtcg.js +300 -0
- package/dist/cloudflare/core/tokens/formatters/index.js +45 -0
- package/dist/cloudflare/core/tokens/formatters/json.js +7 -0
- package/dist/cloudflare/core/tokens/formatters/less.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/scss.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/stubs.js +11 -0
- package/dist/cloudflare/core/tokens/formatters/style-dictionary-v3.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/tailwind-v3.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/tailwind-v4.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/tokens-studio.js +4 -0
- package/dist/cloudflare/core/tokens/formatters/ts-module.js +4 -0
- package/dist/cloudflare/core/tokens/index.js +15 -0
- package/dist/cloudflare/core/tokens/parsers/css-vars.js +4 -0
- package/dist/cloudflare/core/tokens/parsers/dtcg.js +253 -0
- package/dist/cloudflare/core/tokens/parsers/index.js +138 -0
- package/dist/cloudflare/core/tokens/parsers/json.js +7 -0
- package/dist/cloudflare/core/tokens/parsers/scss.js +4 -0
- package/dist/cloudflare/core/tokens/parsers/stubs.js +13 -0
- package/dist/cloudflare/core/tokens/parsers/style-dictionary-v3.js +4 -0
- package/dist/cloudflare/core/tokens/parsers/tailwind-v3.js +4 -0
- package/dist/cloudflare/core/tokens/parsers/tailwind-v4.js +4 -0
- package/dist/cloudflare/core/tokens/parsers/tokens-studio.js +4 -0
- package/dist/cloudflare/core/tokens/schemas.js +148 -0
- package/dist/cloudflare/core/tokens/transforms/color.js +12 -0
- package/dist/cloudflare/core/tokens/transforms/index.js +29 -0
- package/dist/cloudflare/core/tokens/transforms/size.js +7 -0
- package/dist/cloudflare/core/tokens/types.js +18 -0
- package/dist/cloudflare/core/tokens-tools.js +849 -0
- package/dist/cloudflare/core/websocket-server.js +5 -55
- package/dist/cloudflare/index.js +37 -26
- package/dist/core/config.d.ts.map +1 -1
- package/dist/core/config.js +0 -8
- package/dist/core/config.js.map +1 -1
- package/dist/core/console-monitor.d.ts +2 -2
- package/dist/core/console-monitor.d.ts.map +1 -1
- package/dist/core/console-monitor.js +3 -3
- package/dist/core/console-monitor.js.map +1 -1
- package/dist/core/diagnose-tool.d.ts +33 -0
- package/dist/core/diagnose-tool.d.ts.map +1 -0
- package/dist/core/diagnose-tool.js +97 -0
- package/dist/core/diagnose-tool.js.map +1 -0
- package/dist/core/figma-connector.d.ts +1 -1
- package/dist/core/figma-connector.d.ts.map +1 -1
- package/dist/core/figma-tools.d.ts +1 -2
- package/dist/core/figma-tools.d.ts.map +1 -1
- package/dist/core/figma-tools.js +69 -229
- package/dist/core/figma-tools.js.map +1 -1
- package/dist/core/identity.d.ts +41 -0
- package/dist/core/identity.d.ts.map +1 -0
- package/dist/core/identity.js +97 -0
- package/dist/core/identity.js.map +1 -0
- package/dist/core/tokens/alias-resolver.d.ts +40 -0
- package/dist/core/tokens/alias-resolver.d.ts.map +1 -0
- package/dist/core/tokens/alias-resolver.js +99 -0
- package/dist/core/tokens/alias-resolver.js.map +1 -0
- package/dist/core/tokens/config.d.ts +352 -0
- package/dist/core/tokens/config.d.ts.map +1 -0
- package/dist/core/tokens/config.js +285 -0
- package/dist/core/tokens/config.js.map +1 -0
- package/dist/core/tokens/figma-converter.d.ts +81 -0
- package/dist/core/tokens/figma-converter.d.ts.map +1 -0
- package/dist/core/tokens/figma-converter.js +196 -0
- package/dist/core/tokens/figma-converter.js.map +1 -0
- package/dist/core/tokens/formatters/css-vars.d.ts +24 -0
- package/dist/core/tokens/formatters/css-vars.d.ts.map +1 -0
- package/dist/core/tokens/formatters/css-vars.js +330 -0
- package/dist/core/tokens/formatters/css-vars.js.map +1 -0
- package/dist/core/tokens/formatters/dtcg.d.ts +28 -0
- package/dist/core/tokens/formatters/dtcg.d.ts.map +1 -0
- package/dist/core/tokens/formatters/dtcg.js +301 -0
- package/dist/core/tokens/formatters/dtcg.js.map +1 -0
- package/dist/core/tokens/formatters/index.d.ts +30 -0
- package/dist/core/tokens/formatters/index.d.ts.map +1 -0
- package/dist/core/tokens/formatters/index.js +46 -0
- package/dist/core/tokens/formatters/index.js.map +1 -0
- package/dist/core/tokens/formatters/json.d.ts +5 -0
- package/dist/core/tokens/formatters/json.d.ts.map +1 -0
- package/dist/core/tokens/formatters/json.js +8 -0
- package/dist/core/tokens/formatters/json.js.map +1 -0
- package/dist/core/tokens/formatters/less.d.ts +4 -0
- package/dist/core/tokens/formatters/less.d.ts.map +1 -0
- package/dist/core/tokens/formatters/less.js +5 -0
- package/dist/core/tokens/formatters/less.js.map +1 -0
- package/dist/core/tokens/formatters/scss.d.ts +4 -0
- package/dist/core/tokens/formatters/scss.d.ts.map +1 -0
- package/dist/core/tokens/formatters/scss.js +5 -0
- package/dist/core/tokens/formatters/scss.js.map +1 -0
- package/dist/core/tokens/formatters/stubs.d.ts +9 -0
- package/dist/core/tokens/formatters/stubs.d.ts.map +1 -0
- package/dist/core/tokens/formatters/stubs.js +12 -0
- package/dist/core/tokens/formatters/stubs.js.map +1 -0
- package/dist/core/tokens/formatters/style-dictionary-v3.d.ts +4 -0
- package/dist/core/tokens/formatters/style-dictionary-v3.d.ts.map +1 -0
- package/dist/core/tokens/formatters/style-dictionary-v3.js +5 -0
- package/dist/core/tokens/formatters/style-dictionary-v3.js.map +1 -0
- package/dist/core/tokens/formatters/tailwind-v3.d.ts +4 -0
- package/dist/core/tokens/formatters/tailwind-v3.d.ts.map +1 -0
- package/dist/core/tokens/formatters/tailwind-v3.js +5 -0
- package/dist/core/tokens/formatters/tailwind-v3.js.map +1 -0
- package/dist/core/tokens/formatters/tailwind-v4.d.ts +4 -0
- package/dist/core/tokens/formatters/tailwind-v4.d.ts.map +1 -0
- package/dist/core/tokens/formatters/tailwind-v4.js +5 -0
- package/dist/core/tokens/formatters/tailwind-v4.js.map +1 -0
- package/dist/core/tokens/formatters/tokens-studio.d.ts +4 -0
- package/dist/core/tokens/formatters/tokens-studio.d.ts.map +1 -0
- package/dist/core/tokens/formatters/tokens-studio.js +5 -0
- package/dist/core/tokens/formatters/tokens-studio.js.map +1 -0
- package/dist/core/tokens/formatters/ts-module.d.ts +4 -0
- package/dist/core/tokens/formatters/ts-module.d.ts.map +1 -0
- package/dist/core/tokens/formatters/ts-module.js +5 -0
- package/dist/core/tokens/formatters/ts-module.js.map +1 -0
- package/dist/core/tokens/index.d.ts +17 -0
- package/dist/core/tokens/index.d.ts.map +1 -0
- package/dist/core/tokens/index.js +16 -0
- package/dist/core/tokens/index.js.map +1 -0
- package/dist/core/tokens/parsers/css-vars.d.ts +3 -0
- package/dist/core/tokens/parsers/css-vars.d.ts.map +1 -0
- package/dist/core/tokens/parsers/css-vars.js +5 -0
- package/dist/core/tokens/parsers/css-vars.js.map +1 -0
- package/dist/core/tokens/parsers/dtcg.d.ts +21 -0
- package/dist/core/tokens/parsers/dtcg.d.ts.map +1 -0
- package/dist/core/tokens/parsers/dtcg.js +254 -0
- package/dist/core/tokens/parsers/dtcg.js.map +1 -0
- package/dist/core/tokens/parsers/index.d.ts +37 -0
- package/dist/core/tokens/parsers/index.d.ts.map +1 -0
- package/dist/core/tokens/parsers/index.js +139 -0
- package/dist/core/tokens/parsers/index.js.map +1 -0
- package/dist/core/tokens/parsers/json.d.ts +4 -0
- package/dist/core/tokens/parsers/json.d.ts.map +1 -0
- package/dist/core/tokens/parsers/json.js +8 -0
- package/dist/core/tokens/parsers/json.js.map +1 -0
- package/dist/core/tokens/parsers/scss.d.ts +3 -0
- package/dist/core/tokens/parsers/scss.d.ts.map +1 -0
- package/dist/core/tokens/parsers/scss.js +5 -0
- package/dist/core/tokens/parsers/scss.js.map +1 -0
- package/dist/core/tokens/parsers/stubs.d.ts +11 -0
- package/dist/core/tokens/parsers/stubs.d.ts.map +1 -0
- package/dist/core/tokens/parsers/stubs.js +14 -0
- package/dist/core/tokens/parsers/stubs.js.map +1 -0
- package/dist/core/tokens/parsers/style-dictionary-v3.d.ts +3 -0
- package/dist/core/tokens/parsers/style-dictionary-v3.d.ts.map +1 -0
- package/dist/core/tokens/parsers/style-dictionary-v3.js +5 -0
- package/dist/core/tokens/parsers/style-dictionary-v3.js.map +1 -0
- package/dist/core/tokens/parsers/tailwind-v3.d.ts +3 -0
- package/dist/core/tokens/parsers/tailwind-v3.d.ts.map +1 -0
- package/dist/core/tokens/parsers/tailwind-v3.js +5 -0
- package/dist/core/tokens/parsers/tailwind-v3.js.map +1 -0
- package/dist/core/tokens/parsers/tailwind-v4.d.ts +3 -0
- package/dist/core/tokens/parsers/tailwind-v4.d.ts.map +1 -0
- package/dist/core/tokens/parsers/tailwind-v4.js +5 -0
- package/dist/core/tokens/parsers/tailwind-v4.js.map +1 -0
- package/dist/core/tokens/parsers/tokens-studio.d.ts +3 -0
- package/dist/core/tokens/parsers/tokens-studio.d.ts.map +1 -0
- package/dist/core/tokens/parsers/tokens-studio.js +5 -0
- package/dist/core/tokens/parsers/tokens-studio.js.map +1 -0
- package/dist/core/tokens/schemas.d.ts +152 -0
- package/dist/core/tokens/schemas.d.ts.map +1 -0
- package/dist/core/tokens/schemas.js +149 -0
- package/dist/core/tokens/schemas.js.map +1 -0
- package/dist/core/tokens/transforms/color.d.ts +9 -0
- package/dist/core/tokens/transforms/color.d.ts.map +1 -0
- package/dist/core/tokens/transforms/color.js +13 -0
- package/dist/core/tokens/transforms/color.js.map +1 -0
- package/dist/core/tokens/transforms/index.d.ts +36 -0
- package/dist/core/tokens/transforms/index.d.ts.map +1 -0
- package/dist/core/tokens/transforms/index.js +30 -0
- package/dist/core/tokens/transforms/index.js.map +1 -0
- package/dist/core/tokens/transforms/size.d.ts +7 -0
- package/dist/core/tokens/transforms/size.d.ts.map +1 -0
- package/dist/core/tokens/transforms/size.js +8 -0
- package/dist/core/tokens/transforms/size.js.map +1 -0
- package/dist/core/tokens/types.d.ts +228 -0
- package/dist/core/tokens/types.d.ts.map +1 -0
- package/dist/core/tokens/types.js +19 -0
- package/dist/core/tokens/types.js.map +1 -0
- package/dist/core/tokens-tools.d.ts +42 -0
- package/dist/core/tokens-tools.d.ts.map +1 -0
- package/dist/core/tokens-tools.js +850 -0
- package/dist/core/tokens-tools.js.map +1 -0
- package/dist/core/types/index.d.ts +0 -8
- package/dist/core/types/index.d.ts.map +1 -1
- package/dist/core/websocket-connector.d.ts +1 -1
- package/dist/core/websocket-connector.d.ts.map +1 -1
- package/dist/core/websocket-server.d.ts +4 -3
- package/dist/core/websocket-server.d.ts.map +1 -1
- package/dist/core/websocket-server.js +5 -55
- package/dist/core/websocket-server.js.map +1 -1
- package/dist/local.d.ts +0 -12
- package/dist/local.d.ts.map +1 -1
- package/dist/local.js +959 -3406
- package/dist/local.js.map +1 -1
- package/figma-desktop-bridge/code.js +11 -63
- package/figma-desktop-bridge/ui.html +72 -11
- package/package.json +10 -9
- package/figma-desktop-bridge/ui-full.html +0 -1353
|
@@ -1,22 +1,23 @@
|
|
|
1
1
|
// Figma Desktop Bridge - MCP Plugin
|
|
2
|
-
// Bridges Figma API to MCP clients via plugin UI
|
|
3
|
-
// Supports: Variables, Components, Styles, and more
|
|
4
|
-
// Uses postMessage to communicate with
|
|
5
|
-
//
|
|
2
|
+
// Bridges the Figma Plugin API to MCP clients via the plugin's UI iframe.
|
|
3
|
+
// Supports: Variables, Components, Styles, and more.
|
|
4
|
+
// Uses postMessage to communicate with ui.html (bypassing worker sandbox limitations),
|
|
5
|
+
// which then forwards messages to the MCP server over the WebSocket bridge.
|
|
6
6
|
|
|
7
7
|
// Plugin version — sent in FILE_INFO for server-side version compatibility checks.
|
|
8
8
|
// The server compares this against its own version to detect stale cached plugins.
|
|
9
|
-
var PLUGIN_VERSION = '1.
|
|
9
|
+
var PLUGIN_VERSION = '1.27.1'; // Kept in sync with package.json by scripts/release.sh — see issue #62.
|
|
10
10
|
|
|
11
11
|
console.log('🌉 [Desktop Bridge] Plugin loaded (v' + PLUGIN_VERSION + ')');
|
|
12
12
|
|
|
13
13
|
// Show minimal UI - compact status indicator
|
|
14
|
-
figma.showUI(__html__, { width:
|
|
14
|
+
figma.showUI(__html__, { width: 180, height: 50, visible: true, themeColors: true });
|
|
15
15
|
|
|
16
16
|
// ============================================================================
|
|
17
17
|
// CONSOLE CAPTURE — Intercept console.* in the QuickJS sandbox and forward
|
|
18
18
|
// to ui.html via postMessage so the WebSocket bridge can relay them to the MCP
|
|
19
|
-
// server. This
|
|
19
|
+
// server. This is the only console-capture path in local mode (no browser
|
|
20
|
+
// process is involved).
|
|
20
21
|
// ============================================================================
|
|
21
22
|
(function() {
|
|
22
23
|
var levels = ['log', 'info', 'warn', 'error', 'debug'];
|
|
@@ -220,59 +221,6 @@ function hexToFigmaRGB(hex) {
|
|
|
220
221
|
// Listen for requests from UI (e.g., component data requests, write operations)
|
|
221
222
|
figma.ui.onmessage = async (msg) => {
|
|
222
223
|
|
|
223
|
-
// ============================================================================
|
|
224
|
-
// BOOT_LOAD_UI - Bootloader fetched fresh UI HTML from the MCP server.
|
|
225
|
-
// Replace the bootloader with the full, always-up-to-date plugin UI.
|
|
226
|
-
// This uses figma.showUI() with the HTML string directly — no redirects,
|
|
227
|
-
// no cross-origin, no CSP issues.
|
|
228
|
-
// ============================================================================
|
|
229
|
-
if (msg.type === 'BOOT_LOAD_UI' && msg.html) {
|
|
230
|
-
console.log('🌉 [Desktop Bridge] Bootloader delivered fresh UI (' + msg.html.length + ' bytes), loading...');
|
|
231
|
-
figma.showUI(msg.html, { width: 140, height: 50, visible: true, themeColors: true });
|
|
232
|
-
|
|
233
|
-
// Re-send variables data to the fresh UI — the original send went to the
|
|
234
|
-
// bootloader which discarded it. The fresh UI needs it to show "ready" status.
|
|
235
|
-
(async function() {
|
|
236
|
-
try {
|
|
237
|
-
var variables = await figma.variables.getLocalVariablesAsync();
|
|
238
|
-
var collections = await figma.variables.getLocalVariableCollectionsAsync();
|
|
239
|
-
figma.ui.postMessage({
|
|
240
|
-
type: 'VARIABLES_DATA',
|
|
241
|
-
data: {
|
|
242
|
-
success: true,
|
|
243
|
-
timestamp: Date.now(),
|
|
244
|
-
fileKey: figma.fileKey || null,
|
|
245
|
-
variables: variables.map(function(v) { return {
|
|
246
|
-
id: v.id, name: v.name, key: v.key, resolvedType: v.resolvedType,
|
|
247
|
-
valuesByMode: v.valuesByMode, variableCollectionId: v.variableCollectionId,
|
|
248
|
-
scopes: v.scopes, codeSyntax: v.codeSyntax || {}, description: v.description, hiddenFromPublishing: v.hiddenFromPublishing
|
|
249
|
-
}; }),
|
|
250
|
-
variableCollections: collections.map(function(c) { return {
|
|
251
|
-
id: c.id, name: c.name, key: c.key, modes: c.modes,
|
|
252
|
-
defaultModeId: c.defaultModeId, variableIds: c.variableIds
|
|
253
|
-
}; })
|
|
254
|
-
}
|
|
255
|
-
});
|
|
256
|
-
console.log('🌉 [Desktop Bridge] Re-sent variables to fresh UI (' + variables.length + ' vars)');
|
|
257
|
-
} catch (e) {
|
|
258
|
-
console.log('🌉 [Desktop Bridge] Could not re-send variables:', e.message || e);
|
|
259
|
-
}
|
|
260
|
-
})();
|
|
261
|
-
return;
|
|
262
|
-
}
|
|
263
|
-
|
|
264
|
-
// ============================================================================
|
|
265
|
-
// BOOT_FALLBACK - Bootloader found an old server that doesn't support the
|
|
266
|
-
// bootloader protocol. Fall back to reloading the cached __html__ which
|
|
267
|
-
// contains the full UI (for users who haven't switched to the bootloader yet,
|
|
268
|
-
// __html__ IS the full UI; for bootloader users, this is a no-op reload).
|
|
269
|
-
// ============================================================================
|
|
270
|
-
if (msg.type === 'BOOT_FALLBACK') {
|
|
271
|
-
console.log('🌉 [Desktop Bridge] Old server detected on port ' + msg.port + ', using cached UI');
|
|
272
|
-
figma.showUI(__html__, { width: 140, height: 50, visible: true, themeColors: true });
|
|
273
|
-
return;
|
|
274
|
-
}
|
|
275
|
-
|
|
276
224
|
// ============================================================================
|
|
277
225
|
// EXECUTE_CODE - Arbitrary code execution (Power Tool)
|
|
278
226
|
// ============================================================================
|
|
@@ -376,7 +324,7 @@ figma.ui.onmessage = async (msg) => {
|
|
|
376
324
|
var errorMsg = error && error.message ? error.message : String(error);
|
|
377
325
|
var errorStack = error && error.stack ? error.stack : '';
|
|
378
326
|
|
|
379
|
-
// Log error details as strings so they
|
|
327
|
+
// Log error details as strings so they survive intact through the WebSocket bridge into figma_get_console_logs
|
|
380
328
|
console.error('🌉 [Desktop Bridge] Code execution error: [' + errorName + '] ' + errorMsg);
|
|
381
329
|
if (errorStack) {
|
|
382
330
|
console.error('🌉 [Desktop Bridge] Stack:', errorStack);
|
|
@@ -3101,7 +3049,7 @@ figma.ui.onmessage = async (msg) => {
|
|
|
3101
3049
|
});
|
|
3102
3050
|
// Short delay to let the response message be sent before reload
|
|
3103
3051
|
setTimeout(function() {
|
|
3104
|
-
figma.showUI(__html__, { width:
|
|
3052
|
+
figma.showUI(__html__, { width: 180, height: 50, visible: true, themeColors: true });
|
|
3105
3053
|
}, 100);
|
|
3106
3054
|
} catch (error) {
|
|
3107
3055
|
var errorMsg = error && error.message ? error.message : String(error);
|
|
@@ -6424,4 +6372,4 @@ console.log('🌉 [Desktop Bridge] Ready to handle component requests');
|
|
|
6424
6372
|
console.log('🌉 [Desktop Bridge] Plugin will stay open until manually closed');
|
|
6425
6373
|
|
|
6426
6374
|
// Plugin stays open - no auto-close
|
|
6427
|
-
// UI iframe remains accessible
|
|
6375
|
+
// UI iframe remains accessible so the in-iframe WebSocket bridge client can keep relaying state to the MCP server
|
|
@@ -217,7 +217,7 @@
|
|
|
217
217
|
|
|
218
218
|
<script>
|
|
219
219
|
// ============================================================================
|
|
220
|
-
// GLOBAL STATE
|
|
220
|
+
// GLOBAL STATE — backing store for the in-iframe WebSocket bridge client
|
|
221
221
|
// ============================================================================
|
|
222
222
|
window.__figmaVariablesData = null;
|
|
223
223
|
window.__figmaVariablesReady = false;
|
|
@@ -227,13 +227,67 @@
|
|
|
227
227
|
|
|
228
228
|
let requestIdCounter = 0;
|
|
229
229
|
|
|
230
|
-
//
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
230
|
+
// Status pill state — captured here so we can re-render whenever the
|
|
231
|
+
// mode (local port count, cloud paired) changes without losing the
|
|
232
|
+
// ready/connecting/error state set by the data layer.
|
|
233
|
+
let _currentStatusState = 'connecting';
|
|
234
|
+
let _currentStatusActive = false;
|
|
235
|
+
let _currentStatusError = false;
|
|
236
|
+
|
|
237
|
+
// Compute the mode label shown in place of the static "MCP" prefix.
|
|
238
|
+
// Returns "Local", "Cloud", "Local + Cloud", or "" (unknown — falls back
|
|
239
|
+
// to the original "MCP" label so the pill always says something).
|
|
240
|
+
// Lets users see at a glance which transport is carrying their session,
|
|
241
|
+
// so a confused user doesn't have to guess whether they're talking to
|
|
242
|
+
// the local server, the cloud relay, or both. Port numbers are omitted
|
|
243
|
+
// here to keep the pill compact — figma_diagnose exposes the port when
|
|
244
|
+
// it's actually needed.
|
|
245
|
+
//
|
|
246
|
+
// NOTE: `activeConnections` is declared inside the connection-pool IIFE
|
|
247
|
+
// below (around line ~617), so it is NOT in scope from this top-level
|
|
248
|
+
// function. The IIFE exposes `window.__wsGetActiveConnections()` for
|
|
249
|
+
// exactly this reason — calling that getter is what makes the pill
|
|
250
|
+
// update once the pool reports a live connection.
|
|
251
|
+
function renderModeText() {
|
|
252
|
+
try {
|
|
253
|
+
var getConns = window.__wsGetActiveConnections;
|
|
254
|
+
var conns = typeof getConns === 'function' ? (getConns() || []) : [];
|
|
255
|
+
var localUp = conns.some(function(c) {
|
|
256
|
+
return c && c.ws && c.ws.readyState === 1 && c.port !== 'cloud';
|
|
257
|
+
});
|
|
258
|
+
var cloudUp = conns.some(function(c) {
|
|
259
|
+
return c && c.ws && c.ws.readyState === 1 && c.port === 'cloud';
|
|
260
|
+
});
|
|
261
|
+
if (localUp && cloudUp) return 'Local + Cloud';
|
|
262
|
+
if (localUp) return 'Local';
|
|
263
|
+
if (cloudUp) return 'Cloud';
|
|
264
|
+
return '';
|
|
265
|
+
} catch (e) {
|
|
266
|
+
return '';
|
|
267
|
+
}
|
|
268
|
+
}
|
|
234
269
|
|
|
235
|
-
|
|
236
|
-
|
|
270
|
+
function refreshStatus() {
|
|
271
|
+
var dot = document.getElementById('status-dot');
|
|
272
|
+
var stateText = document.getElementById('status-state');
|
|
273
|
+
var labelEl = document.querySelector('.status-text .label');
|
|
274
|
+
if (!dot || !stateText) return;
|
|
275
|
+
dot.className = 'status-indicator ' + (_currentStatusError ? 'error' : (_currentStatusActive ? 'active' : 'loading'));
|
|
276
|
+
var mode = renderModeText();
|
|
277
|
+
// Replace the static "MCP" label with the live mode label (Local / Cloud
|
|
278
|
+
// / Local + Cloud). Fall back to "MCP" when nothing is connected yet so
|
|
279
|
+
// the pill still has a visible label during initial scan.
|
|
280
|
+
if (labelEl) labelEl.textContent = mode || 'MCP';
|
|
281
|
+
stateText.textContent = _currentStatusState;
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
// UI update helper — preserves the latest state and re-renders, picking
|
|
285
|
+
// up any mode-text changes (local/cloud connect/disconnect).
|
|
286
|
+
function updateStatus(state, isActive, isError) {
|
|
287
|
+
_currentStatusState = state;
|
|
288
|
+
_currentStatusActive = isActive;
|
|
289
|
+
_currentStatusError = isError;
|
|
290
|
+
refreshStatus();
|
|
237
291
|
}
|
|
238
292
|
|
|
239
293
|
// ============================================================================
|
|
@@ -605,7 +659,8 @@
|
|
|
605
659
|
};
|
|
606
660
|
|
|
607
661
|
// ============================================================================
|
|
608
|
-
// WEBSOCKET BRIDGE CLIENT
|
|
662
|
+
// WEBSOCKET BRIDGE CLIENT — primary transport from the plugin sandbox to
|
|
663
|
+
// the MCP server. Scans port range 9223–9232 for multiple instances.
|
|
609
664
|
// ============================================================================
|
|
610
665
|
(function() {
|
|
611
666
|
// Port range for multi-instance support (matches server's port-discovery.ts)
|
|
@@ -800,7 +855,9 @@
|
|
|
800
855
|
}
|
|
801
856
|
|
|
802
857
|
/**
|
|
803
|
-
* Update backward-compat variables (ws, wsPort, wsConnected)
|
|
858
|
+
* Update backward-compat variables (ws, wsPort, wsConnected) and
|
|
859
|
+
* re-render the status pill so the Local/Cloud mode suffix reflects
|
|
860
|
+
* the new connection set.
|
|
804
861
|
*/
|
|
805
862
|
function updateCompatState() {
|
|
806
863
|
var live = activeConnections.filter(function(c) { return c.ws.readyState === 1; });
|
|
@@ -812,6 +869,9 @@
|
|
|
812
869
|
ws = null;
|
|
813
870
|
wsPort = null;
|
|
814
871
|
}
|
|
872
|
+
// refreshStatus is defined in the outer scope (top-level script block).
|
|
873
|
+
// Guarded for the unlikely case it's invoked before that script runs.
|
|
874
|
+
if (typeof refreshStatus === 'function') refreshStatus();
|
|
815
875
|
}
|
|
816
876
|
|
|
817
877
|
/**
|
|
@@ -1109,9 +1169,10 @@
|
|
|
1109
1169
|
section.classList.toggle('visible');
|
|
1110
1170
|
toggle.classList.toggle('expanded');
|
|
1111
1171
|
|
|
1112
|
-
// Resize plugin window to fit content
|
|
1172
|
+
// Resize plugin window to fit content. Default width is 180px to give
|
|
1173
|
+
// the status pill enough room for the "Local + Cloud" mode label.
|
|
1113
1174
|
var height = isExpanding ? 130 : 50;
|
|
1114
|
-
parent.postMessage({ pluginMessage: { type: 'RESIZE_UI', width:
|
|
1175
|
+
parent.postMessage({ pluginMessage: { type: 'RESIZE_UI', width: 180, height: height } }, '*');
|
|
1115
1176
|
}
|
|
1116
1177
|
|
|
1117
1178
|
function resetCloudUI() {
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@mp3wizard/figma-console-mcp",
|
|
3
|
-
"version": "1.
|
|
4
|
-
"description": "MCP server for
|
|
3
|
+
"version": "1.27.2",
|
|
4
|
+
"description": "The most comprehensive MCP server for Figma — design tokens, variables, components, write tools, version history diff, accessibility audits, FigJam, Slides, and more. Local (WebSocket Desktop Bridge plugin) and Cloudflare Workers (paired + remote) modes.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/local.js",
|
|
7
7
|
"types": "dist/local.d.ts",
|
|
@@ -37,15 +37,18 @@
|
|
|
37
37
|
"mcp",
|
|
38
38
|
"figma",
|
|
39
39
|
"plugin",
|
|
40
|
-
"
|
|
41
|
-
"
|
|
40
|
+
"design-tokens",
|
|
41
|
+
"design-systems",
|
|
42
|
+
"variables",
|
|
43
|
+
"figjam",
|
|
44
|
+
"slides",
|
|
45
|
+
"accessibility",
|
|
42
46
|
"ai",
|
|
43
47
|
"anthropic",
|
|
44
48
|
"claude",
|
|
45
|
-
"cloudflare"
|
|
46
|
-
"workers"
|
|
49
|
+
"cloudflare"
|
|
47
50
|
],
|
|
48
|
-
"author": "
|
|
51
|
+
"author": "Southleft",
|
|
49
52
|
"license": "MIT",
|
|
50
53
|
"repository": {
|
|
51
54
|
"type": "git",
|
|
@@ -60,11 +63,9 @@
|
|
|
60
63
|
"@modelcontextprotocol/sdk": "^1.26.0",
|
|
61
64
|
"agents": "^0.7.1",
|
|
62
65
|
"axe-core": "^4.11.2",
|
|
63
|
-
"chrome-remote-interface": "^0.33.2",
|
|
64
66
|
"jsdom": "^29.0.1",
|
|
65
67
|
"pino": "^9.5.0",
|
|
66
68
|
"pino-pretty": "^13.0.0",
|
|
67
|
-
"puppeteer-core": "^23.11.1",
|
|
68
69
|
"uuid": "^11.0.3",
|
|
69
70
|
"ws": "^8.19.0",
|
|
70
71
|
"zod": "^3.25.76"
|