figma-relai 0.7.7 → 0.7.8
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 +63 -35
- package/dist/{chunk-PQGMCFD7.js → chunk-VKBEC37P.js} +7 -3
- package/dist/chunk-VKBEC37P.js.map +1 -0
- package/dist/index.js +2 -2
- package/dist/{manifest-ASJDLEEP.js → manifest-BQSVYOOE.js} +2 -2
- package/package.json +1 -1
- package/dist/chunk-PQGMCFD7.js.map +0 -1
- /package/dist/{manifest-ASJDLEEP.js.map → manifest-BQSVYOOE.js.map} +0 -0
package/README.md
CHANGED
|
@@ -1,14 +1,15 @@
|
|
|
1
|
-
<
|
|
2
|
-
|
|
3
|
-
|
|
1
|
+
<picture>
|
|
2
|
+
<source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/syoooo/figma-relai/main/assets/relai-logo-cream.svg">
|
|
3
|
+
<img src="https://raw.githubusercontent.com/syoooo/figma-relai/main/assets/relai-logo-ink.svg" alt="Relai" height="36">
|
|
4
|
+
</picture>
|
|
4
5
|
|
|
5
6
|
[figma-relai.vercel.app](https://figma-relai.vercel.app)
|
|
6
7
|
|
|
7
|
-
**Your AI, on the canvas.** Relai connects Claude Code, Cursor, Codex — any MCP client — to Figma, so you can read, edit, audit, and build design systems by talking to the model you already use.
|
|
8
|
+
**Your AI, on the canvas.** Relai connects Claude Code, Cursor, Codex — any MCP client — to Figma, so you can read, edit, audit, and build design systems by talking to the model you already use. And the file is not a bystander: it carries your conventions, your precedents, your no-go zones. Every client that opens it inherits them, and an edit that breaks them is refused before it runs — the file has a veto. That is what makes it safe to hand agents real work.
|
|
8
9
|
|
|
9
10
|
Relai's position: the AI era should put designers *more* in charge, not less. Taste and judgment stay with you; the labor moves to a model you already trust, with every step visible.
|
|
10
11
|
|
|
11
|
-
<img src="assets/plugin-ui.png" alt="The Relai plugin: activity feed, connection status, and a Stop button" width="380" />
|
|
12
|
+
<img src="https://raw.githubusercontent.com/syoooo/figma-relai/main/assets/plugin-ui.png" alt="The Relai plugin: activity feed, connection status, and a Stop button" width="380" />
|
|
12
13
|
|
|
13
14
|
## What a session looks like
|
|
14
15
|
|
|
@@ -19,8 +20,12 @@ Relai's position: the AI era should put designers *more* in charge, not less. Ta
|
|
|
19
20
|
> **You:** Now sweep the whole screen for dark mode.
|
|
20
21
|
>
|
|
21
22
|
> **AI:** `set_properties · 24 nodes · 1.2s ✓` → `analyze_design · overall → 92/100`
|
|
23
|
+
>
|
|
24
|
+
> **You:** Same sweep on Brand / Masters.
|
|
25
|
+
>
|
|
26
|
+
> **File:** `✗ blocked — "Brand / Masters" is a no-go zone`
|
|
22
27
|
|
|
23
|
-
Every command shows up in the plugin as it runs, with timing and success or failure. Click an entry to jump to that layer on the canvas. Press **Stop** if you change your mind — the rest of the batch is cancelled.
|
|
28
|
+
Every command shows up in the plugin as it runs, with timing and success or failure. Click an entry to jump to that layer on the canvas. Press **Stop** if you change your mind — the rest of the batch is cancelled. And some commands never run at all: pages you fenced off reject writes before they touch the canvas, with the reason on the receipt.
|
|
24
29
|
|
|
25
30
|
The numbers scale. Relai is how its author maintains a production design system, and this excerpt is from one of those sessions — July 2026, unedited:
|
|
26
31
|
|
|
@@ -32,11 +37,43 @@ batch_execute 25,351 bindings rebound
|
|
|
32
37
|
re-census 30,251 → 936 · zero visual change
|
|
33
38
|
```
|
|
34
39
|
|
|
40
|
+
The gate in the middle is the point: one explicit yes from the designer licensed a 25,351-binding rebind — and every fence stayed up while it ran.
|
|
41
|
+
|
|
42
|
+
## The file carries the law
|
|
43
|
+
|
|
44
|
+
Code already escaped the speed-versus-standards trade, and not by making models careful: the repo pushes back. Lint flags, checks gate, protected branches refuse — which is why a developer can hand an agent real work and go do something else. Relai builds that pushback into the design file itself. Not a leash — a license.
|
|
45
|
+
|
|
46
|
+
Rules you'd normally paste into every prompt live inside the Figma file, so any future session — from any MCP client, by anyone who opens the file — starts already briefed. And the load-bearing part is not prose the model might happen to read: the law runs as checks.
|
|
47
|
+
|
|
48
|
+
**Conventions** are a little CLAUDE.md stored in the file: naming rules, token routing, spacing habits. The AI reads them before working. Unlike a CLAUDE.md, they belong to the file rather than to one person's agent setup — every client inherits them, configured or not. Add one by telling the AI ("new convention: colors route through Theme tokens"); the panel's RULES row shows what's stored.
|
|
49
|
+
|
|
50
|
+
**Memory** holds your precedents. Rule once — the file remembers. Say "this gap is on purpose" and the ruling is recorded in the file; any later edit that touches what it references gets your words attached to its result:
|
|
51
|
+
|
|
52
|
+
```text
|
|
53
|
+
you "this gap is on purpose — remember it"
|
|
54
|
+
file record_precedent · saved ✓
|
|
55
|
+
|
|
56
|
+
(another session, a different AI, about to "fix" the gap)
|
|
57
|
+
file precedent attached — "…is on purpose" · the edit backs off
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
The panel's Memory row lists every entry; delete any of them any time. Nothing is recorded silently. Case law, not documentation.
|
|
61
|
+
|
|
62
|
+
**Kits.** One designer usually runs one product, and its files share the same law. Save this file's rules under a name and other files can use it. Figma drops file-carried law on branch merges; the kit puts it back — one click, or automatically if you flip that kit's auto-restore on.
|
|
63
|
+
|
|
64
|
+
**AI no-go zones** fence off whole pages — brand masters, legal, the one that is already pixel-perfect. Writes into a guarded page are rejected before they run, with the reason on the receipt, and only you edit the guard list. Protected branches, for the canvas.
|
|
65
|
+
|
|
66
|
+
**Confirmation** is a dial with four stops — OPEN · RISK · BULK · ALL. At RISK, the default, only destructive operations ask (deleting variables or styles, detach, flatten); everything else keeps moving. Set it in the panel; agents can't move it.
|
|
67
|
+
|
|
68
|
+
Where the law lives, and how far it reaches: it is stored as plugin data inside the file — no extra layers on the canvas, nothing teammates have to tiptoe around — and it survives duplication (branch merges drop it; kits put it back). Enforcement runs in the plugin, on the file's side of the wire, and comes in two strengths: no-go zones and Lock to selection are walls — the write itself is rejected; precedents are your recorded words arriving at the exact moment an edit touches what they reference — the agent backs off because the author shows up. Any client that connects through Relai is bound, including ones you never configured. An agent pointed at some other bridge is not — the law cannot guard a door it does not hold, which is why everything leaves receipts.
|
|
69
|
+
|
|
70
|
+
None of this is setup you grind through — it accumulates. On day one the file is blank law, and the agent behaves like anyone's agent. A month in, it arrives briefed on your conventions and precedents and stops at your fences: the same prompt that produces the average of everyone's design in a fresh file produces yours in yours. Two long-time users are not holding the same tool. They are holding two different instruments.
|
|
71
|
+
|
|
35
72
|
## Get started
|
|
36
73
|
|
|
37
74
|
You need [Figma Desktop](https://www.figma.com/downloads/), [Node.js](https://nodejs.org/) 18+, and an MCP client.
|
|
38
75
|
|
|
39
|
-
**1. Install the plugin.** Download `relai-plugin.zip` from [the latest release](https://github.com/syoooo/figma-relai/releases/latest), unzip it, then open **Plugins → Development → Import plugin from manifest…** in the desktop app and pick `manifest.json`. It connects on its own and remembers its room across restarts.
|
|
76
|
+
**1. Install the plugin.** Download `relai-plugin.zip` from [the latest release](https://github.com/syoooo/figma-relai/releases/latest), unzip it, then open **Plugins → Development → Import plugin from manifest…** in the desktop app and pick `manifest.json`. Open it in the file you want to edit and keep the panel open — writes go through it. It connects on its own and remembers its room across restarts; when a release ships a new plugin, re-import the new zip.
|
|
40
77
|
|
|
41
78
|
**2. Register the server** with your AI client:
|
|
42
79
|
|
|
@@ -51,7 +88,16 @@ For Cursor, add this to `.cursor/mcp.json`:
|
|
|
51
88
|
{ "mcpServers": { "Relai": { "command": "npx", "args": ["-y", "figma-relai"] } } }
|
|
52
89
|
```
|
|
53
90
|
|
|
54
|
-
|
|
91
|
+
Or hand the setup to your agent — paste this:
|
|
92
|
+
|
|
93
|
+
```text
|
|
94
|
+
Set up Relai: register the MCP server for this client (the command is
|
|
95
|
+
`npx -y figma-relai`, e.g. `claude mcp add Relai -- npx -y figma-relai`),
|
|
96
|
+
then walk me through importing the Figma plugin from
|
|
97
|
+
https://github.com/syoooo/figma-relai/releases/latest — I'll do the Figma clicks.
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
**3. Ask for something.** Pairing is automatic; there is nothing to copy between windows. A good first ask: *"How is this screen put together?"*
|
|
55
101
|
|
|
56
102
|
## What it's good at
|
|
57
103
|
|
|
@@ -59,35 +105,11 @@ Understanding a design. "How is this screen put together?" gets you structure, c
|
|
|
59
105
|
|
|
60
106
|
Bulk edits. "Translate every button label to English" or "recolor this for dark mode" become one round-trip across dozens of layers instead of an afternoon of clicking.
|
|
61
107
|
|
|
62
|
-
Audits. `analyze_design` checks color-token coverage, auto-layout quality, component health, and accessibility (WCAG contrast, touch targets, text sizes) — or all four at once as a weighted 0–100 health score you can put in a review. It also scores agent-readiness (how prepared the file is for AI work, with top gaps), fingerprints the file's voice (its radius/spacing/type signature), and runs a ghost census
|
|
108
|
+
Audits. `analyze_design` checks color-token coverage, auto-layout quality, component health, and accessibility (WCAG contrast, touch targets, text sizes) — or all four at once as a weighted 0–100 health score you can put in a review, with deviations you already ruled intentional staying waived instead of re-flagged. It also scores agent-readiness (how prepared the file is for AI work, with top gaps), fingerprints the file's voice (its radius/spacing/type signature), and runs a ghost census: references still pointing at soft-deleted variables.
|
|
63
109
|
|
|
64
110
|
Design systems. Variable collections with modes, token binding, shared styles, components with proper variants, team-library imports. `get_design_system` inventories what the file — and the libraries it uses — already has (with a token, the library's whole catalog, including components the file has never placed), so the AI builds from your components instead of redrawing near-copies; `analyze_design`'s tokens aspect finds hardcoded values that visually match an existing variable, and one `tokenize` call binds them all. These run as declarative operations with precondition checks, so the same request behaves the same way every time, and a failure tells the AI what to do next ("call set_layout_mode first") instead of dumping a stack trace.
|
|
65
111
|
|
|
66
|
-
Everything else. `execute_figma` runs JavaScript against the Figma Plugin API directly — the same escape-hatch approach as Figma's official MCP — with a `relai.*` helper library that makes the correct pattern the shortest one,
|
|
67
|
-
|
|
68
|
-
## The file carries the law
|
|
69
|
-
|
|
70
|
-
Rules you'd normally paste into every prompt live inside the Figma file itself, so any future session — from any MCP client, by anyone who opens the file — starts already briefed.
|
|
71
|
-
|
|
72
|
-
**Conventions** are a little CLAUDE.md stored in the file: naming rules, token routing, spacing habits. The AI reads them before working.
|
|
73
|
-
|
|
74
|
-
**Memory** holds your precedents. Rule once — "this gap is on purpose" — and the ruling is recorded in the file; any later edit that touches what it references gets your words attached to its result:
|
|
75
|
-
|
|
76
|
-
```text
|
|
77
|
-
you "this gap is on purpose — remember it"
|
|
78
|
-
file record_precedent · saved ✓
|
|
79
|
-
|
|
80
|
-
(another session, a different AI, about to "fix" the gap)
|
|
81
|
-
file precedent attached — "…is on purpose" · the edit backs off
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
The panel's Memory row lists every entry; delete any of them any time. Nothing is recorded silently.
|
|
85
|
-
|
|
86
|
-
**Kits.** One designer usually runs one product, and its files share the same law. Save this file’s rules under a name and other files can use it. Figma drops file-carried law on branch merges; the kit puts it back — one click, or automatically if you flip that kit’s auto-restore on.
|
|
87
|
-
|
|
88
|
-
**AI no-go zones** fence off whole pages — brand masters, legal, the one that is already pixel-perfect. Writes into a guarded page are rejected before they run, with the reason on the receipt, and only you edit the guard list.
|
|
89
|
-
|
|
90
|
-
**Confirmation** is one level with four stops — OPEN · RISK · BULK · ALL. At RISK, the default, only dangerous operations ask (deleting variables or styles, detach, flatten); everything else keeps moving. Set it in the panel; agents can't move it.
|
|
112
|
+
Everything else. `execute_figma` runs JavaScript against the Figma Plugin API directly — the same escape-hatch approach as Figma's official MCP — with a `relai.*` helper library that makes the correct pattern the shortest one, a registry of pitfalls learned in production that attaches the fix to known errors, and a lint that flags silent mistakes. If you'd rather the AI never ran code, turn it off with the plugin's "Allow code execution" toggle.
|
|
91
113
|
|
|
92
114
|
## You stay in control
|
|
93
115
|
|
|
@@ -95,6 +117,8 @@ The plugin is the designer's side of the deal: a live activity feed of everythin
|
|
|
95
117
|
|
|
96
118
|
**Lock to selection** rejects edits outside whatever you've selected — the AI gets a clear error, not a silent pass. The relay is local: file contents move only between Figma, your machine, and the AI client you already trust. The UI speaks English, 日本語, and 中文.
|
|
97
119
|
|
|
120
|
+
When something goes wrong anyway — a bad sweep, a wrong "fix" — the feed is your reconstruction and Figma's version history is your restore path. There is no magic undo, and Relai doesn't pretend to have one: `diff_nodes` checkpoints tell you exactly what changed; version history takes you back. And when the law itself is wrong — a stale precedent guarding a gap you've since changed your mind about — tell the agent to go ahead, then delete the entry from the panel's Memory row. Rulings are one click to remove; the law stays yours to amend.
|
|
121
|
+
|
|
98
122
|
## How it works
|
|
99
123
|
|
|
100
124
|
```
|
|
@@ -108,6 +132,8 @@ Figma plugin executes Plugin API calls
|
|
|
108
132
|
|
|
109
133
|
The relay lives inside the MCP server, so there is no extra process to keep alive. When several MCP clients run at once, the first one hosts the relay and the others connect to it; if the host exits, a survivor takes over. Both sides remember their room, rejoin after restarts or sleep, and find each other without any copy-pasting. The `join_room` tool exists for one rare case only: two Figma files running the plugin at the same time.
|
|
110
134
|
|
|
135
|
+
The receipts above are real timings: rule checks run in the plugin before each write, small edits land sub-second, and the 45,509-node audit took 3.9s.
|
|
136
|
+
|
|
111
137
|
Ports are fixed by Figma's plugin sandbox: the manifest allowlists `ws://localhost:9055–9057`, and other ports cannot work without editing `manifest.json`. That's why there is no port setting in the UI.
|
|
112
138
|
|
|
113
139
|
## The tools
|
|
@@ -131,7 +157,7 @@ Each tool is self-describing, so the AI sees full parameter docs. The same contr
|
|
|
131
157
|
|
|
132
158
|
## Relai and Figma's official MCP
|
|
133
159
|
|
|
134
|
-
Figma's own AI has grown fast — the official MCP server now writes to the canvas, and the Figma Design Agent collaborates right inside the editor. Both are reserved for full seats on paid plans, with usage metered in AI credits and models chosen by Figma. Relai is the open-source counterpart on the other side of that line:
|
|
160
|
+
Figma's own AI has grown fast — the official MCP server now writes to the canvas, and the Figma Design Agent collaborates right inside the editor. Both are reserved for full seats on paid plans, with usage metered in AI credits and models chosen by Figma. Relai is the open-source counterpart on the other side of that line: your model, your subscription, your machine — and the designer holding the controls. Writes go through the Relai Figma plugin rather than the paid REST API, which is why it works on every plan, free included. If you have the seats, the two coexist happily — run both.
|
|
135
161
|
|
|
136
162
|
## Optional: a Figma token
|
|
137
163
|
|
|
@@ -182,6 +208,8 @@ bun test
|
|
|
182
208
|
|
|
183
209
|
Requires [Bun](https://bun.sh/) v1.0+ (the setup script is bash; on Windows use WSL). Load the plugin via **Plugins → Development → Import plugin from manifest…** → `packages/figma-plugin/manifest.json`. A standalone relay (`bun socket`) exists for the unusual case where the relay must run on another machine. More in [CONTRIBUTING.md](CONTRIBUTING.md); manual QA lives in [docs/smoke-checklist.md](docs/smoke-checklist.md).
|
|
184
210
|
|
|
211
|
+
Project status: Relai is built and dogfooded daily against a production design system; releases track that work. MIT plus local-first is the longevity hedge — nothing phones home, and nothing stops working if the repo goes quiet.
|
|
212
|
+
|
|
185
213
|
## License
|
|
186
214
|
|
|
187
215
|
MIT — see [LICENSE](LICENSE).
|
|
@@ -11,7 +11,7 @@ import {
|
|
|
11
11
|
} from "./chunk-2H7UOFLK.js";
|
|
12
12
|
|
|
13
13
|
// src/version.ts
|
|
14
|
-
var VERSION = "0.7.
|
|
14
|
+
var VERSION = "0.7.8";
|
|
15
15
|
|
|
16
16
|
// src/server.ts
|
|
17
17
|
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
@@ -2922,7 +2922,11 @@ function register19(server, sendCommand) {
|
|
|
2922
2922
|
const result = await sendCommand("find_nodes", {
|
|
2923
2923
|
name: query,
|
|
2924
2924
|
types,
|
|
2925
|
-
parentId
|
|
2925
|
+
parentId,
|
|
2926
|
+
// Sideloaded plugins ≤0.7.7 read the scope as nodeId; npx serves the
|
|
2927
|
+
// latest server automatically, so old-plugin/new-server is the common
|
|
2928
|
+
// pairing. Drop once the 0.7.7 zip is no longer in circulation.
|
|
2929
|
+
nodeId: parentId
|
|
2926
2930
|
});
|
|
2927
2931
|
const matches = (Array.isArray(result) ? result : []).map((n) => ({
|
|
2928
2932
|
id: n.id,
|
|
@@ -4485,4 +4489,4 @@ export {
|
|
|
4485
4489
|
listToolCatalog,
|
|
4486
4490
|
registerPrompts
|
|
4487
4491
|
};
|
|
4488
|
-
//# sourceMappingURL=chunk-
|
|
4492
|
+
//# sourceMappingURL=chunk-VKBEC37P.js.map
|