Conversation
Release 0.14.0
chore(release): v0.15.0
enable-unsafe-webgpu was applied on any X11 session (!isWayland), leaving WebGPU silently ON for X11 users who had the enableWebGPU toggle OFF — contradicting the setting. Figma probes navigator.gpu (exposed by enable-unsafe-webgpu) to switch on its Shader/Halftone/ Noise effects, so the flag belongs behind the toggle alongside the shaders. Now gate it on shadersActive (X11 + enableWebGPU) with the existing userForcesVulkan escape hatch preserved. Only the X11 + toggle-off quadrant changes; X11/Wayland toggle-on and Wayland toggle-off are unaffected. The change is scoped to WebGPU only — ignore-gpu-blocklist and enable-webgl stay on X11, so the normal WebGL canvas keeps its hardware acceleration; a toggle-off X11 user loses only the shader effects. Update the truth-table tests to lock all four quadrants. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QWRSUEUKBsLy4paZR4noBb
"Export video" calls window.open("https://www.figma.com/export/<fileKey>?fuid=…").
/export/ was missing from isFigmaRunUrl's validPaths, so the URL fell through to
shell.openExternal and landed in the system browser — where the render queue is
always empty, because it lives in the app's session. Logging in there does not
help, as reported in #41.
- add /^\/export\// to validPaths so the queue opens as an in-app tab
- give export tabs their own dedup prefix (export:<key>), so a repeated
"Export video" click reuses the queue tab and cannot collide with the
design tab for the same file
- log every window.open with url/frameName/disposition/features — Tab had no
logging at all here, which is why this took a live capture to find
- route only http(s) to shell.openExternal; other schemes were passed through
as a silent no-op and are now logged as blocked
Verified against a live capture: the export URL above, and the Linear plugin's
OAuth (response_type=stringauth, redirect_uri=figma-plugin.linear.app/callback),
which completes in the browser and returns through Linear's own callback.
Refs #41
NixOS packaging
The flake read its version from package.json but carried hard-coded sha256 hashes, so every `perl scripts/bump_version.pl` left it naming a release whose binaries it could not hash — `nix build` then failed on a hash mismatch until someone recomputed both by hand. The PR shipped with a "Chore: update hashes when release binaries change" comment; this replaces the comment with the mechanism. - flake.nix: version and both hashes live in one `release` block, so they are rewritten as a unit and cannot drift - scripts/update_flake_release.py: rewrites that block, converting sha256sum hex digests to the SRI form Nix expects; fails loudly if the layout moved - release.yml: new `flake` job hashes both release zips after the release is published and commits the pinned flake to staging (dev is protected, so the flake there trails by one release) - README: note that the flake installs prebuilt binaries and how to pin a tag - CLAUDE.md, build skill: document that flake.nix is CI-owned, never bumped by hand Not verified with `nix build` — no Nix on this machine. Follow-up to #42
Nix resolves `github:arximus88/figma-linux-next` from the default branch, which is dev. Committing the release hashes only to staging meant NixOS installed whatever dev still named — always the previous release, since staging reaches dev with the next release PR. The flake job now checks out dev with RELEASE_PAT (fine-grained, Contents:write on this repo only) and pushes there first, then mirrors the same change to staging. The default GITHUB_TOKEN cannot do this: it is refused by the branch protection on dev. The job still runs last and depends on `release`, so a rejected push leaves the release, its binaries and both AUR packages already published — the only casualty is the flake update, and the failure is visible in the run. Token expiry (2027-08-05) is recorded in CLAUDE.md and the build skill, because a 403 on that push is the sole symptom and would otherwise be a blind diagnosis.
The gemini-cli copy under .agent was byte-identical to the global ~/.claude/skills/gemini-cli. The .gemini skills duplicated capabilities already available (frontend-design, the Figma MCP workflows, generic refactoring smells) or contradicted this project: electron-app-planning prescribes raw ipcMain.handle and electron-updater, neither of which applies here. .gemini/settings.json listed the same MCP servers as .mcp.json plus figma-remote. One item survives as a CLAUDE.md note instead of a file: `bunx @sveltejs/mcp svelte-autofixer <file>` catches Svelte 5 rune antipatterns that svelte-check misses, which matters because Biome does not lint .svelte. The gitignore "Agents" block matched only .gemini/settings.*, so the skills stayed tracked despite it; widened to .gemini and dropped the duplicate .agent/skills entry.
… Nix section The Nix material was already current — the skill was written alongside 358ada0/75b23e4. Verifying it line by line against release.yml, update_flake_release.py and flake.nix surfaced five other divergences: - The release checklist pushed the tag together with the branch, ahead of the PR steps, contradicting the rule stated at the top of the same file. Following it literally would publish a release before dev was updated. - push_aur_dev_git.yml was listed as an existing workflow; 3c3a762 deleted it. - RELEASE_PAT was described in prose but missing from the secrets table, so its 2027-08-05 expiry was not where someone would look for it. - The aur/aur-bin/flake pre-release guard from e011888 was undocumented: an -rc tag produces a GitHub Release and no AUR or flake update. - Key Files listed no flake file at all — neither flake.nix nor scripts/update_flake_release.py.
CLAUDE.md:
- Critical Files pointed at src/utils/Render/frameConfig.ts and
frameStyles.ts; neither exists. The icon/component config is
frameTheme.ts and the frames themselves are Svelte components under
src/renderer/Panel/frames/.
- Utils/Render/defaultSettings.ts was called the authoritative settings
schema. It is a four-line re-export whose own comment calls itself a
placeholder; the values live in Utils/Common/defaultSettings.ts as
BASE_DEFAULT_SETTINGS. Documented all three same-named files so
"add a new setting" lands in the right one.
- The path-alias example imported a symbol named `defaultSettings`,
which nothing exports.
- FrameStyle was listed as three values; the union in
src/types/Common/index.d.ts has four (kde was missing) and the
default is gnome.
- ci.yml was described as PRs to dev; it runs on push and PR to both
staging and dev.
README.md:
- The AppImage snippet globbed figma-linux-next-*.AppImage with a dash.
electron-builder names artifacts ${name}_${version}_${platform}_${arch},
so the glob matched nothing.
- The NixOS section set programs.figma-linux-next.enable without
importing nixosModules.default, which fails evaluation with an
undefined option.
Both AUR packages publish license=('MIT') while the project is
GPL-2.0-only — LICENSE is GNU GPL v2, and package.json, src/package.json
and flake.nix all say so. Verified against the live AUR RPC:
figma-linux-next 0.15.0-1 and figma-linux-next-bin both report
License: ["MIT"].
The line drifted because the aur and aur-bin jobs rewrite pkgver, pkgrel
and sha256sums and nothing else, so whatever license the AUR repo was
seeded with survived every release. Deriving it from package.json means
the two can no longer disagree; the value there is already an exact SPDX
identifier, so it drops into the PKGBUILD verbatim.
python3 is used rather than jq because the archlinux container installs
python and not jq.
Verified: actionlint clean, YAML parses, and the sed produces
license=('GPL-2.0-only') against a real PKGBUILD.
A clone under /home/arx/aur/ had drifted five releases behind live AUR (0.13.1 vs 0.15.0) while still looking like a working copy. Pushing it would have rolled both packages back, and CI would not have caught it — each run clones whatever AUR currently holds and edits that in place. Also records which fields CI rewrites (now including license) versus the ones that only change by hand, and that AUR maintenance takes down the SSH endpoint alone: push fails while the web UI and HTTPS git stay up.
The project sat on 42.0.1 because 42.3.0 broke `/app_auth/redeem` — Figma rejected the request headers from that Chromium roll and returned login HTML instead of Set-Cookie, killing first-login and add-account. Verified against the bundled 43.3.0 binary (Chromium 150.0.7871.212), which is what electron-builder ships: first login on clean storage completes, the figma:// redeem redirect lands, and the session survives restarts. Image paste and frameless window decorations also check out, covering the two behaviour changes in 43 that touch us — sRGB normalisation in nativeImage.toBitmap() and rounded corners on Linux CSD. Chromium 148 -> 150 also brings three months of security fixes, a faster boot (startup snapshot for main, bytecode-cached preloads) and a newer WebGPU stack. CLAUDE.md now records how to run the OAuth test correctly: use the bundled binary rather than a distro Electron, carry mimeapps.list into the isolated config, and shadow the installed .desktop so the redirect comes back.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Collected work from
workspace. Every item below was verified on a running build, not just compiled.Electron 43.3.0
The project was pinned to 42.0.1 because 42.3.0 broke
/app_auth/redeem— Figma rejected that Chromium roll's request headers and returned login HTML instead ofSet-Cookie, killing first-login and add-account.Verified against the bundled binary from
node_modules(Chromium 150.0.7871.212), which is what electron-builder ships — a distro Electron would not have proven anything, since those are rebuilt from source without the same closed-source components:figma.auth_idlands 8s after the redeem redirectnativeImage.toBitmap()Also brings three months of Chromium security fixes, a faster boot (startup snapshot for main, bytecode-cached preloads) and a newer WebGPU stack.
NixOS support
Flake from @iamcalledrob (#42), reworked so version and both platform hashes live in one
releaseblock that CI rewrites as a unit after each release — the hashes only exist once the binaries are built, so this cannot be part ofbump_version.pl.The new
flakejob pushes the pinned flake todevfirst (where Nix resolves the input from) and mirrors it tostaging, usingRELEASE_PATbecauseGITHUB_TOKENcannot push to a protected branch.Figma Motion export queue (#41)
"Export video" opened
figma.com/export/<key>in the system browser, which always showed an empty queue — the queue lives in the app's session./export/is now a recognised in-app path with its own tab dedup key, so repeated exports reuse the tab instead of stacking or hijacking the design tab.Also
enableWebGPUtoggle on X11 instead of being forced on for every X11 sessionpackage.jsoneach release (was hardcodedMIT, project isGPL-2.0-only)CLAUDE.md, the build skill andREADME.mdChecks
bun test213 pass ·tsc --noEmitclean ·biome checkclean ·svelte-check0 errorsKnown follow-up, not in this PR
Electron 44 removes the
clipboardmodule from the renderer process.src/renderer/DesktopAPI/webBinding.tsuses it in eight places, and the AURfigma-linux-nextpackage depends on the floatingelectronmeta-package — so it will move to 44 on its own. Either pinelectron43there or move clipboard reads into main before 44 lands.