@akesson/figma-explorer 0.1.0 → 0.2.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/CHANGELOG.md +163 -0
- package/README.md +13 -5
- package/binary-install.js +149 -13
- package/binary.js +4 -8
- package/npm-shrinkwrap.json +8 -502
- package/package.json +5 -9
package/CHANGELOG.md
CHANGED
|
@@ -7,8 +7,116 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.2.2] - 2026-08-22
|
|
11
|
+
|
|
12
|
+
### Fixed
|
|
13
|
+
|
|
14
|
+
- **npm package for 0.2.1 was never published** — the OIDC publish job used a
|
|
15
|
+
placeholder auth token written by `actions/setup-node`. Fixed; 0.2.2 is the
|
|
16
|
+
first release on npm via Trusted Publishing. No CLI changes.
|
|
17
|
+
|
|
18
|
+
## [0.2.1] - 2026-08-22
|
|
19
|
+
|
|
20
|
+
### Changed
|
|
21
|
+
|
|
22
|
+
- **npm releases now publish via npm Trusted Publishing (OIDC)** instead of a
|
|
23
|
+
long-lived `NPM_TOKEN`. Packages carry provenance attestations. No
|
|
24
|
+
user-facing changes to the CLI.
|
|
25
|
+
|
|
26
|
+
## [0.2.0] - 2026-07-29
|
|
27
|
+
|
|
10
28
|
### Added
|
|
11
29
|
|
|
30
|
+
- **Web-search query syntax for `find`** — the syntax every agent already
|
|
31
|
+
knows from Google/GitHub: bare words stay fuzzy tokens with implicit AND
|
|
32
|
+
(unchanged); `"quoted phrases"` require the exact contiguous text
|
|
33
|
+
(case-insensitive) — the lane for hunting rendered copy like
|
|
34
|
+
`find '"Approved by you"'`; uppercase `OR` alternates adjacent terms
|
|
35
|
+
(`a b OR c` = a AND (b OR c)); `-term` / `-"phrase"` exclude any chain
|
|
36
|
+
containing them; uppercase `AND` is accepted as a no-op. Lowercase
|
|
37
|
+
`or`/`and` remain ordinary tokens, and mid-word hyphens (`night-shift`)
|
|
38
|
+
stay literal. Exact-phrase hits score above same-length fuzzy matches, so
|
|
39
|
+
copy searches rank the real thing first. Note the shell eats outer
|
|
40
|
+
quotes: write `find '"exact phrase" context'`.
|
|
41
|
+
|
|
42
|
+
- `cache status` — offline report of what the cache holds: per-file rows
|
|
43
|
+
(synth id, name, key, project, payload age, node count) with sidecar
|
|
44
|
+
presence/age for full/comments/variables, plus totals, team-catalog state,
|
|
45
|
+
and mark count. Ends agents introspecting the cache directory by hand (and
|
|
46
|
+
getting it wrong).
|
|
47
|
+
- `node-info` now emits a ready-made figma.com `url:` — on the `target` block
|
|
48
|
+
for node targets (deep link with `node-id=`) and on every `file` block —
|
|
49
|
+
so reports can link straight into Figma without hand-assembling URLs from
|
|
50
|
+
the raw `key`.
|
|
51
|
+
- `--only` now works on **file** targets too: `meta` (just the counts),
|
|
52
|
+
`pages`, `component`, `styles`, `variables`, `comments` filter the file
|
|
53
|
+
summary. Node-only sections on a file target (and the new `pages` section
|
|
54
|
+
on a node target) are rejected with a hint instead of silently emitting
|
|
55
|
+
nothing.
|
|
56
|
+
|
|
57
|
+
- **Marks** — a curated keyword→node database (`mark add`/`rm`/`list`, and a new
|
|
58
|
+
`mark:<key>` id). Once you've positively identified a node, `mark add <key>
|
|
59
|
+
<ID> [--alias …] [--note …]` writes the mapping down so the expensive
|
|
60
|
+
discovery never repeats. `find` and `library search` now fold matching marks
|
|
61
|
+
in **ahead of** their own hits, so a query in *your* vocabulary ("leave
|
|
62
|
+
tooltip") surfaces the node even when no layer name matches. `mark:<key>`
|
|
63
|
+
resolves like the underlying node, so `node-info mark:k`, `screenshot mark:k`,
|
|
64
|
+
and `--in mark:k` work transparently; a multi-node mark lists its paste-ready
|
|
65
|
+
ids so you can pick one. Marks live in `<cache-root>/marks.json` (beside
|
|
66
|
+
`synth.json`) and **survive `cache clear`**. Each mark node carries a stamp of
|
|
67
|
+
the node's name + ancestor path when added, so `mark list` flags drift as
|
|
68
|
+
`[renamed]` / `[moved]` / `[gone]` / `[uncached]` rather than silently
|
|
69
|
+
pointing at a node the design moved out from under.
|
|
70
|
+
- `find` now matches a node's **visible text**, not just its layer name. TEXT
|
|
71
|
+
content (`characters`) is captured into the structural cache (truncated to
|
|
72
|
+
160 chars) so a query like `leave details` finds the button whose layer is
|
|
73
|
+
named "Button Label" but whose copy reads "Leave details". Text-lane matches
|
|
74
|
+
render a `text:"…"` snippet line under the hit (JSON: `text_matches`), and
|
|
75
|
+
unnamed TEXT nodes with copy are now searchable. This bumps
|
|
76
|
+
`CACHE_SCHEMA_VERSION` to 2 — existing caches silently refetch on next
|
|
77
|
+
access; under `--cache-only`, run `cache prefetch` once first.
|
|
78
|
+
- `comments <ID> --grep <PATTERN>` — case-insensitive substring filter over
|
|
79
|
+
thread head + reply messages. Composes with `--unresolved`/`--since`/
|
|
80
|
+
`--limit`; the header reports `# N of M threads match "<pattern>"` (JSON
|
|
81
|
+
summary gains `grep`).
|
|
82
|
+
- `find` now surfaces a comment-mention hint: after the search it reports
|
|
83
|
+
which searched files discuss the query in their comment threads
|
|
84
|
+
(`# N comment threads mention "tooltip" — try: comments file:15 --grep
|
|
85
|
+
"tooltip"`, capped at 3 files; JSON: `comment_mentions`). A name-search
|
|
86
|
+
miss often lands in the designers' discussion, which is written in user
|
|
87
|
+
vocabulary — this closes that dead end.
|
|
88
|
+
- `ls --comments` — restore the pre-diet inline comment thread rows. By
|
|
89
|
+
default `ls` now summarizes comments (see Changed).
|
|
90
|
+
- `comments <ID>` — list every comment thread in a file (replies inline,
|
|
91
|
+
sorted newest-activity-first, full message text), threads anchored under a
|
|
92
|
+
node subtree, or one thread by `file:N:comm:M`. Filters: `--unresolved`,
|
|
93
|
+
`--since <ISO8601>` (prefix-friendly, matches head or reply activity),
|
|
94
|
+
`--limit N`. `--refresh` re-fetches a single file's comments — no full
|
|
95
|
+
`cache prefetch` needed. Previously only `node-info` exposed comments,
|
|
96
|
+
capped at 10 recent threads.
|
|
97
|
+
- `node-info` file targets now sort `recent_comments` newest-first (was:
|
|
98
|
+
API order) and add a `comments_hint` pointing at `comments file:N` when
|
|
99
|
+
more threads exist than the summary shows.
|
|
100
|
+
- `node-info --only <sections>` — restrict output to named sections
|
|
101
|
+
(`fills,strokes,effects,geometry,corner,layout,text,component,prototype,meta,styles,variables,comments`)
|
|
102
|
+
instead of piping the full dump through grep. Identity (id/type/name) is
|
|
103
|
+
always emitted; the hoisted top-level `variables`/`styles_index` blocks
|
|
104
|
+
keep exactly the entries referenced by kept sections. `--only prototype`
|
|
105
|
+
and `--only meta` imply those opt-in sections.
|
|
106
|
+
- `ls --name <PATTERN>` — case-insensitive substring filter over node names.
|
|
107
|
+
Matches keep their ancestor rail for tree context; other branches are
|
|
108
|
+
pruned; root/project listings drop files/projects with no matches inside
|
|
109
|
+
(unless their own name matches). A `# name filter "…": N matches` line
|
|
110
|
+
(JSON: `name_filter` object) makes the filtering visible.
|
|
111
|
+
- `find` now prints `# searched N cached files` on unscoped runs (JSON:
|
|
112
|
+
`searched_files`) — cross-file search has always been the no-`--in`
|
|
113
|
+
default, but nothing said so; help text and docs now do, and zero-match
|
|
114
|
+
runs are no longer silent.
|
|
115
|
+
- `FIGMA_TOKEN` (and any other env) now falls back to a global
|
|
116
|
+
`$XDG_CONFIG_HOME`-or-`~/.config/figma-explorer/.env`, loaded after the
|
|
117
|
+
cwd-upward `.env` walk (lowest priority). Covers git worktrees that don't
|
|
118
|
+
see the canonical checkout's `.env`.
|
|
119
|
+
|
|
12
120
|
- `library search <query>` — fuzzy text search across a team's published
|
|
13
121
|
design-system catalog (components, component sets, and styles). Each hit
|
|
14
122
|
reports the component/style key and a paste-ready `file:N:x:y` id when the
|
|
@@ -22,9 +130,64 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
22
130
|
- `FIGMA_TEAM_ID` environment variable (also `--team-id`), consumed by
|
|
23
131
|
`library search` and the `cache prefetch` catalog warm.
|
|
24
132
|
|
|
133
|
+
### Changed
|
|
134
|
+
|
|
135
|
+
- Root `ls` (no ID) now defaults to depth 1 — projects + files only — instead
|
|
136
|
+
of descending into every file's canvases/frames. A full workspace dump
|
|
137
|
+
measured ~237KB; the shallow default is ~2KB with a `# depth 1 …` hint on
|
|
138
|
+
how to descend (`ls file:N`, `ls proj:N`, or `--depth 2`). Explicit
|
|
139
|
+
`--depth` is unchanged; every non-root target still defaults to depth 3.
|
|
140
|
+
JSON root output is also depth 1 by default now — pass `--depth 3` for the
|
|
141
|
+
old shape.
|
|
142
|
+
- `ls` now summarizes comments by default instead of interleaving every
|
|
143
|
+
thread: a node with anchored threads shows a `[N comments]` suffix, and
|
|
144
|
+
file targets get a `# N comment threads (M unresolved) — use: comments
|
|
145
|
+
file:N …` header. Pass `--comments` for the old inline rows. Because the
|
|
146
|
+
filter now applies to those rows, `--resolved` requires `--comments`. JSON
|
|
147
|
+
output is unchanged (full comment arrays regardless).
|
|
148
|
+
- `library search` now distinguishes strong from weak fuzzy matches: when any
|
|
149
|
+
hit clears ~85% of the query's self-score, only strong hits show (with a
|
|
150
|
+
`# N weaker matches hidden` line); when none do, it prints `# no strong
|
|
151
|
+
match for "<q>"` and lists a few `(weak)`-labeled leads instead of ranking
|
|
152
|
+
subsequence junk as if it were relevant. JSON hits gain `strong`; the
|
|
153
|
+
envelope gains `no_strong_match`/`self_score`.
|
|
154
|
+
|
|
25
155
|
### Fixed
|
|
26
156
|
|
|
157
|
+
- Piping any command into a reader that closes early (`figma-explorer ls … |
|
|
158
|
+
head`) no longer panics with `failed printing to stdout: Broken pipe (os
|
|
159
|
+
error 32)`. The Rust runtime ignores `SIGPIPE` at startup, which turned a
|
|
160
|
+
broken pipe into a `println!` panic (exit 101); both binaries now restore the
|
|
161
|
+
default disposition so the process ends quietly (exit 141) like a normal Unix
|
|
162
|
+
CLI. Matters most for agents, which pipe through `head`/`grep` constantly.
|
|
163
|
+
- `--cache-only` is now enforced by the live-fetch commands (`tokens`,
|
|
164
|
+
`screenshot`, `assets`, `context`). Previously the flag was honored only
|
|
165
|
+
during id resolution, then the mandatory step-2 live fetch proceeded anyway —
|
|
166
|
+
so `--cache-only tokens …` silently hit the network. These commands cannot be
|
|
167
|
+
served offline (they need fills/strokes/type styles or the `/images` API), so
|
|
168
|
+
they now bail up front with a clear message, matching `comments --refresh`.
|
|
169
|
+
- Root `ls` on a cache with no files (fresh, or just cleared) now prints a
|
|
170
|
+
`no cached files — run … cache prefetch …` nudge (and a `hint` key in
|
|
171
|
+
`--json`) instead of only the depth hint, which gave no clue the cache needed
|
|
172
|
+
populating.
|
|
173
|
+
- Instance-descendant node ids (`I880:3606;2816:36646`) are now accepted
|
|
174
|
+
everywhere an id is: qualified (`file:7:I880:3606;2816:36646`), bare (with
|
|
175
|
+
`--in`), and in figma.com URLs (`node-id=I880-3606%3B2816-36646`).
|
|
176
|
+
Previously `ls`/`node-info` printed these ids but the parser rejected them
|
|
177
|
+
("node part is not NUM:NUM"), so the CLI's own output couldn't be pasted
|
|
178
|
+
back into `node-info`/`screenshot`.
|
|
179
|
+
- Tagged file/node targets (`file:N`, `file:N:x:y`) now cold-fetch a missing
|
|
180
|
+
or evicted cache entry instead of dead-ending with "nothing cached … (no
|
|
181
|
+
meta on disk)", matching the URL lane's behavior. Under `--cache-only` the
|
|
182
|
+
miss reports the standard remedy hint instead. The residual disk-only error
|
|
183
|
+
message now also names `cache prefetch` and the URL alternative.
|
|
27
184
|
- `cache clear` (without `--file-key`) swept only the `files/` directory,
|
|
28
185
|
silently leaving other cache state on disk; it now also clears the
|
|
29
186
|
team-catalog sidecars under `teams/`. The command's help text overstated its
|
|
30
187
|
scope and has been corrected.
|
|
188
|
+
- A cached payload written under an older `CACHE_SCHEMA_VERSION` now resolves as
|
|
189
|
+
a cache miss (→ live refetch, or a clean `--cache-only` miss) instead of a
|
|
190
|
+
hard "cache schema version mismatch" internal error. The version check
|
|
191
|
+
already promised silent refetch, but the tagged file/node resolve lane
|
|
192
|
+
mapped the mismatch to an internal error — so a schema bump would have
|
|
193
|
+
dead-ended every synth-id lookup until a manual `cache clear`.
|
package/README.md
CHANGED
|
@@ -4,14 +4,16 @@ A command-line tool for navigating, inspecting, and exporting from Figma files v
|
|
|
4
4
|
|
|
5
5
|
## What it does
|
|
6
6
|
|
|
7
|
-
- **`ls`** / **`find`** — navigate projects, files, and node trees by name without copy-pasting node ids.
|
|
8
|
-
- **`node-info`** — single-target view with layout, fills, strokes, effects, text, bound variables, and
|
|
7
|
+
- **`ls`** / **`find`** — navigate projects, files, and node trees by name or visible text without copy-pasting node ids. `find` speaks web-search syntax: `"exact phrases"`, uppercase `OR`, `-exclusion`.
|
|
8
|
+
- **`node-info`** — single-target view with layout, fills, strokes, effects, text, bound variables, comments, and a ready-made figma.com `url:`. Designed to be pasted into an agent prompt.
|
|
9
|
+
- **`comments`** — list a file's comment threads (replies inline, newest first), threads under a node, or a single thread; filter with `--unresolved` / `--since` / `--grep`.
|
|
10
|
+
- **`mark`** — curated keyword→node bookmarks (`mark add key file:N:x:y --alias …`); `find` and `library search` surface matching marks ahead of their own hits, and `mark:key` resolves anywhere an id is accepted.
|
|
9
11
|
- **`library search`** — fuzzy search across a team's published component library (components, component sets, styles).
|
|
10
12
|
- **`screenshot`** — export a node as PNG / JPG / SVG / PDF.
|
|
11
13
|
- **`tokens`** — extract design tokens (colors, fonts, sizes, spacing).
|
|
12
14
|
- **`assets`** — bulk-export every icon/image below a node.
|
|
13
15
|
- **`context`** — aggregate: tree + screenshot + tokens + assets for a node.
|
|
14
|
-
- **`cache prefetch`** — pre-warm a local cache so subsequent commands are offline-fast.
|
|
16
|
+
- **`cache prefetch`** / **`cache status`** — pre-warm a local cache so subsequent commands are offline-fast, and report what it holds (per-file age, sidecars, catalog) without touching the network.
|
|
15
17
|
|
|
16
18
|
All commands share a tagged-id grammar — `proj:N`, `file:N`, `file:N:x:y`, or a full `figma.com` URL — so you never paste raw node identifiers by hand.
|
|
17
19
|
|
|
@@ -61,7 +63,7 @@ Optional environment variables:
|
|
|
61
63
|
- `FIGMA_TEAM_ID` — needed by `library search` and for the catalog warm in `cache prefetch`.
|
|
62
64
|
- `FIGMA_EXPLORER_CACHE_DIR` — override the cache location (default: OS cache dir).
|
|
63
65
|
|
|
64
|
-
A `.env` file in the current directory (or any ancestor up to root) is auto-loaded.
|
|
66
|
+
A `.env` file in the current directory (or any ancestor up to root) is auto-loaded, with `~/.config/figma-explorer/.env` as the global fallback — handy for git worktrees and directories with no `.env` in their ancestry. Exported environment variables always win.
|
|
65
67
|
|
|
66
68
|
## Quickstart
|
|
67
69
|
|
|
@@ -73,7 +75,13 @@ figma-explorer ls
|
|
|
73
75
|
figma-explorer ls proj:1
|
|
74
76
|
figma-explorer ls file:2
|
|
75
77
|
|
|
76
|
-
# Find a node by name
|
|
78
|
+
# Find a node by name across every cached file
|
|
79
|
+
figma-explorer find "Button / Primary"
|
|
80
|
+
|
|
81
|
+
# Hunt rendered copy with an exact phrase (single-quote so the shell keeps the double quotes)
|
|
82
|
+
figma-explorer find '"Approved by you"'
|
|
83
|
+
|
|
84
|
+
# ...or scope the search to one file
|
|
77
85
|
figma-explorer --in file:2 find "Button / Primary"
|
|
78
86
|
|
|
79
87
|
# Get implementation-ready info for one node
|
package/binary-install.js
CHANGED
|
@@ -1,10 +1,17 @@
|
|
|
1
|
-
const {
|
|
1
|
+
const {
|
|
2
|
+
createWriteStream,
|
|
3
|
+
existsSync,
|
|
4
|
+
mkdirSync,
|
|
5
|
+
mkdtemp,
|
|
6
|
+
rmSync,
|
|
7
|
+
} = require("fs");
|
|
2
8
|
const { join, sep } = require("path");
|
|
3
9
|
const { spawnSync } = require("child_process");
|
|
4
10
|
const { tmpdir } = require("os");
|
|
5
11
|
|
|
6
|
-
const
|
|
7
|
-
const
|
|
12
|
+
const https = require("node:https");
|
|
13
|
+
const http = require("node:http");
|
|
14
|
+
|
|
8
15
|
const tmpDir = tmpdir();
|
|
9
16
|
|
|
10
17
|
const error = (msg) => {
|
|
@@ -12,6 +19,135 @@ const error = (msg) => {
|
|
|
12
19
|
process.exit(1);
|
|
13
20
|
};
|
|
14
21
|
|
|
22
|
+
function getProxyForUrl(urlString) {
|
|
23
|
+
const url = new URL(urlString);
|
|
24
|
+
const isHttps = url.protocol === "https:";
|
|
25
|
+
|
|
26
|
+
const noProxy = process.env.NO_PROXY || process.env.no_proxy || "";
|
|
27
|
+
if (noProxy === "*") return null;
|
|
28
|
+
if (noProxy) {
|
|
29
|
+
const hostname = url.hostname.toLowerCase();
|
|
30
|
+
const noProxyList = noProxy.split(",").map((s) => s.trim().toLowerCase());
|
|
31
|
+
for (const entry of noProxyList) {
|
|
32
|
+
if (hostname === entry || hostname.endsWith("." + entry)) {
|
|
33
|
+
return null;
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
const proxyEnv = isHttps
|
|
39
|
+
? process.env.HTTPS_PROXY || process.env.https_proxy
|
|
40
|
+
: process.env.HTTP_PROXY || process.env.http_proxy;
|
|
41
|
+
|
|
42
|
+
if (!proxyEnv) return null;
|
|
43
|
+
|
|
44
|
+
const proxyUrl = new URL(proxyEnv);
|
|
45
|
+
|
|
46
|
+
let auth = null;
|
|
47
|
+
if (proxyUrl.username || proxyUrl.password) {
|
|
48
|
+
auth = `${proxyUrl.username}:${proxyUrl.password}`;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
return {
|
|
52
|
+
hostname: proxyUrl.hostname,
|
|
53
|
+
port: proxyUrl.port || (proxyUrl.protocol === "https:" ? 443 : 80),
|
|
54
|
+
auth: auth,
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
function connectThroughProxy(proxy, target) {
|
|
59
|
+
return new Promise((resolve, reject) => {
|
|
60
|
+
const headers = {};
|
|
61
|
+
if (proxy.auth) {
|
|
62
|
+
headers["Proxy-Authorization"] =
|
|
63
|
+
"Basic " + Buffer.from(proxy.auth).toString("base64");
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
const connectReq = http.request({
|
|
67
|
+
hostname: proxy.hostname,
|
|
68
|
+
port: proxy.port,
|
|
69
|
+
method: "CONNECT",
|
|
70
|
+
path: `${target.hostname}:${target.port || 443}`,
|
|
71
|
+
headers,
|
|
72
|
+
});
|
|
73
|
+
connectReq.on("connect", (res, socket) => {
|
|
74
|
+
if (res.statusCode === 200) {
|
|
75
|
+
resolve(socket);
|
|
76
|
+
} else {
|
|
77
|
+
reject(new Error(`Proxy CONNECT failed with status ${res.statusCode}`));
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
connectReq.on("error", reject);
|
|
81
|
+
connectReq.end();
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
function download(urlString, maxRedirects) {
|
|
86
|
+
if (maxRedirects === undefined) maxRedirects = 5;
|
|
87
|
+
return new Promise((resolve, reject) => {
|
|
88
|
+
if (maxRedirects < 0) {
|
|
89
|
+
return reject(new Error("Too many redirects"));
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
const parsed = new URL(urlString);
|
|
93
|
+
const isHttps = parsed.protocol === "https:";
|
|
94
|
+
const mod = isHttps ? https : http;
|
|
95
|
+
const proxy = getProxyForUrl(urlString);
|
|
96
|
+
|
|
97
|
+
const doRequest = (extraOptions) => {
|
|
98
|
+
const options = Object.assign(
|
|
99
|
+
{
|
|
100
|
+
hostname: parsed.hostname,
|
|
101
|
+
port: parsed.port || (isHttps ? 443 : 80),
|
|
102
|
+
path: parsed.pathname + parsed.search,
|
|
103
|
+
method: "GET",
|
|
104
|
+
headers: { "User-Agent": "cargo-dist-npm-installer" },
|
|
105
|
+
},
|
|
106
|
+
extraOptions || {},
|
|
107
|
+
);
|
|
108
|
+
|
|
109
|
+
if (proxy && !isHttps) {
|
|
110
|
+
// HTTP through HTTP proxy: request the full URL via the proxy
|
|
111
|
+
options.hostname = proxy.hostname;
|
|
112
|
+
options.port = proxy.port;
|
|
113
|
+
options.path = urlString;
|
|
114
|
+
if (proxy.auth) {
|
|
115
|
+
options.headers["Proxy-Authorization"] =
|
|
116
|
+
"Basic " + Buffer.from(proxy.auth).toString("base64");
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
const req = mod.request(options, (res) => {
|
|
121
|
+
if (
|
|
122
|
+
res.statusCode >= 300 &&
|
|
123
|
+
res.statusCode < 400 &&
|
|
124
|
+
res.headers.location
|
|
125
|
+
) {
|
|
126
|
+
res.resume();
|
|
127
|
+
const nextUrl = new URL(res.headers.location, urlString).toString();
|
|
128
|
+
return download(nextUrl, maxRedirects - 1).then(resolve, reject);
|
|
129
|
+
}
|
|
130
|
+
if (res.statusCode < 200 || res.statusCode >= 300) {
|
|
131
|
+
res.resume();
|
|
132
|
+
return reject(new Error(`HTTP ${res.statusCode} from ${urlString}`));
|
|
133
|
+
}
|
|
134
|
+
resolve(res);
|
|
135
|
+
});
|
|
136
|
+
req.on("error", reject);
|
|
137
|
+
req.end();
|
|
138
|
+
};
|
|
139
|
+
|
|
140
|
+
if (proxy && isHttps) {
|
|
141
|
+
connectThroughProxy(proxy, parsed).then(
|
|
142
|
+
(socket) => doRequest({ socket, agent: false }),
|
|
143
|
+
reject,
|
|
144
|
+
);
|
|
145
|
+
} else {
|
|
146
|
+
doRequest();
|
|
147
|
+
}
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
|
|
15
151
|
class Package {
|
|
16
152
|
constructor(platform, name, url, filename, zipExt, binaries) {
|
|
17
153
|
let errors = [];
|
|
@@ -72,7 +208,7 @@ class Package {
|
|
|
72
208
|
return true;
|
|
73
209
|
}
|
|
74
210
|
|
|
75
|
-
install(
|
|
211
|
+
install(suppressLogs = false) {
|
|
76
212
|
if (this.exists()) {
|
|
77
213
|
if (!suppressLogs) {
|
|
78
214
|
console.error(
|
|
@@ -82,8 +218,10 @@ class Package {
|
|
|
82
218
|
return Promise.resolve();
|
|
83
219
|
}
|
|
84
220
|
|
|
85
|
-
|
|
86
|
-
|
|
221
|
+
try {
|
|
222
|
+
rmSync(this.installDirectory, { recursive: true, force: true });
|
|
223
|
+
} catch {
|
|
224
|
+
// ignore - directory may not exist
|
|
87
225
|
}
|
|
88
226
|
|
|
89
227
|
mkdirSync(this.installDirectory, { recursive: true });
|
|
@@ -92,12 +230,13 @@ class Package {
|
|
|
92
230
|
console.error(`Downloading release from ${this.url}`);
|
|
93
231
|
}
|
|
94
232
|
|
|
95
|
-
return
|
|
233
|
+
return download(this.url)
|
|
96
234
|
.then((res) => {
|
|
97
235
|
return new Promise((resolve, reject) => {
|
|
98
236
|
mkdtemp(`${tmpDir}${sep}`, (err, directory) => {
|
|
237
|
+
if (err) return reject(err);
|
|
99
238
|
let tempFile = join(directory, this.filename);
|
|
100
|
-
const sink = res.
|
|
239
|
+
const sink = res.pipe(createWriteStream(tempFile));
|
|
101
240
|
sink.on("error", (err) => reject(err));
|
|
102
241
|
sink.on("close", () => {
|
|
103
242
|
if (/\.tar\.*/.test(this.zipExt)) {
|
|
@@ -178,10 +317,8 @@ class Package {
|
|
|
178
317
|
});
|
|
179
318
|
}
|
|
180
319
|
|
|
181
|
-
run(binaryName
|
|
182
|
-
const promise = !this.exists()
|
|
183
|
-
? this.install(fetchOptions, true)
|
|
184
|
-
: Promise.resolve();
|
|
320
|
+
run(binaryName) {
|
|
321
|
+
const promise = !this.exists() ? this.install(true) : Promise.resolve();
|
|
185
322
|
|
|
186
323
|
promise
|
|
187
324
|
.then(() => {
|
|
@@ -204,7 +341,6 @@ class Package {
|
|
|
204
341
|
})
|
|
205
342
|
.catch((e) => {
|
|
206
343
|
error(e.message);
|
|
207
|
-
process.exit(1);
|
|
208
344
|
});
|
|
209
345
|
}
|
|
210
346
|
}
|
package/binary.js
CHANGED
|
@@ -1,8 +1,6 @@
|
|
|
1
1
|
const { Package } = require("./binary-install");
|
|
2
2
|
const os = require("os");
|
|
3
|
-
const cTable = require("console.table");
|
|
4
3
|
const libc = require("detect-libc");
|
|
5
|
-
const { configureProxy } = require("axios-proxy-builder");
|
|
6
4
|
|
|
7
5
|
const error = (msg) => {
|
|
8
6
|
console.error(msg);
|
|
@@ -108,17 +106,15 @@ const install = (suppressLogs) => {
|
|
|
108
106
|
console.warn("in demo mode, not installing binaries");
|
|
109
107
|
return;
|
|
110
108
|
}
|
|
111
|
-
const
|
|
112
|
-
const proxy = configureProxy(package.url);
|
|
109
|
+
const pkg = getPackage();
|
|
113
110
|
|
|
114
|
-
return
|
|
111
|
+
return pkg.install(suppressLogs);
|
|
115
112
|
};
|
|
116
113
|
|
|
117
114
|
const run = (binaryName) => {
|
|
118
|
-
const
|
|
119
|
-
const proxy = configureProxy(package.url);
|
|
115
|
+
const pkg = getPackage();
|
|
120
116
|
|
|
121
|
-
|
|
117
|
+
pkg.run(binaryName);
|
|
122
118
|
};
|
|
123
119
|
|
|
124
120
|
module.exports = {
|
package/npm-shrinkwrap.json
CHANGED
|
@@ -7,151 +7,19 @@
|
|
|
7
7
|
"figma-explorer": "run-figma-explorer.js"
|
|
8
8
|
},
|
|
9
9
|
"dependencies": {
|
|
10
|
-
"
|
|
11
|
-
"axios-proxy-builder": "^0.1.2",
|
|
12
|
-
"console.table": "^0.10.0",
|
|
13
|
-
"detect-libc": "^2.1.2",
|
|
14
|
-
"rimraf": "^6.1.3"
|
|
10
|
+
"detect-libc": "^2.1.2"
|
|
15
11
|
},
|
|
16
12
|
"devDependencies": {
|
|
17
|
-
"prettier": "^3.8.
|
|
13
|
+
"prettier": "^3.8.3"
|
|
18
14
|
},
|
|
19
15
|
"engines": {
|
|
20
|
-
"node": ">=14",
|
|
16
|
+
"node": ">=14.14",
|
|
21
17
|
"npm": ">=6"
|
|
22
18
|
},
|
|
23
19
|
"hasInstallScript": true,
|
|
24
20
|
"license": "MIT",
|
|
25
21
|
"name": "@akesson/figma-explorer",
|
|
26
|
-
"version": "0.
|
|
27
|
-
},
|
|
28
|
-
"node_modules/@isaacs/cliui": {
|
|
29
|
-
"engines": {
|
|
30
|
-
"node": ">=18"
|
|
31
|
-
},
|
|
32
|
-
"integrity": "sha512-AokJm4tuBHillT+FpMtxQ60n8ObyXBatq7jD2/JA9dxbDDokKQm8KMht5ibGzLVU9IJDIKK4TPKgMHEYMn3lMg==",
|
|
33
|
-
"license": "BlueOak-1.0.0",
|
|
34
|
-
"resolved": "https://registry.npmjs.org/@isaacs/cliui/-/cliui-9.0.0.tgz",
|
|
35
|
-
"version": "9.0.0"
|
|
36
|
-
},
|
|
37
|
-
"node_modules/asynckit": {
|
|
38
|
-
"integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==",
|
|
39
|
-
"license": "MIT",
|
|
40
|
-
"resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz",
|
|
41
|
-
"version": "0.4.0"
|
|
42
|
-
},
|
|
43
|
-
"node_modules/axios": {
|
|
44
|
-
"dependencies": {
|
|
45
|
-
"follow-redirects": "^1.15.11",
|
|
46
|
-
"form-data": "^4.0.5",
|
|
47
|
-
"proxy-from-env": "^1.1.0"
|
|
48
|
-
},
|
|
49
|
-
"integrity": "sha512-cz4ur7Vb0xS4/KUN0tPWe44eqxrIu31me+fbang3ijiNscE129POzipJJA6zniq2C/Z6sJCjMimjS8Lc/GAs8Q==",
|
|
50
|
-
"license": "MIT",
|
|
51
|
-
"resolved": "https://registry.npmjs.org/axios/-/axios-1.13.5.tgz",
|
|
52
|
-
"version": "1.13.5"
|
|
53
|
-
},
|
|
54
|
-
"node_modules/axios-proxy-builder": {
|
|
55
|
-
"dependencies": {
|
|
56
|
-
"tunnel": "^0.0.6"
|
|
57
|
-
},
|
|
58
|
-
"integrity": "sha512-6uBVsBZzkB3tCC8iyx59mCjQckhB8+GQrI9Cop8eC7ybIsvs/KtnNgEBfRMSEa7GqK2VBGUzgjNYMdPIfotyPA==",
|
|
59
|
-
"license": "MIT",
|
|
60
|
-
"resolved": "https://registry.npmjs.org/axios-proxy-builder/-/axios-proxy-builder-0.1.2.tgz",
|
|
61
|
-
"version": "0.1.2"
|
|
62
|
-
},
|
|
63
|
-
"node_modules/balanced-match": {
|
|
64
|
-
"dependencies": {
|
|
65
|
-
"jackspeak": "^4.2.3"
|
|
66
|
-
},
|
|
67
|
-
"engines": {
|
|
68
|
-
"node": "20 || >=22"
|
|
69
|
-
},
|
|
70
|
-
"integrity": "sha512-x0K50QvKQ97fdEz2kPehIerj+YTeptKF9hyYkKf6egnwmMWAkADiO0QCzSp0R5xN8FTZgYaBfSaue46Ej62nMg==",
|
|
71
|
-
"license": "MIT",
|
|
72
|
-
"resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-4.0.2.tgz",
|
|
73
|
-
"version": "4.0.2"
|
|
74
|
-
},
|
|
75
|
-
"node_modules/brace-expansion": {
|
|
76
|
-
"dependencies": {
|
|
77
|
-
"balanced-match": "^4.0.2"
|
|
78
|
-
},
|
|
79
|
-
"engines": {
|
|
80
|
-
"node": "20 || >=22"
|
|
81
|
-
},
|
|
82
|
-
"integrity": "sha512-Pdk8c9poy+YhOgVWw1JNN22/HcivgKWwpxKq04M/jTmHyCZn12WPJebZxdjSa5TmBqISrUSgNYU3eRORljfCCw==",
|
|
83
|
-
"license": "MIT",
|
|
84
|
-
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-5.0.2.tgz",
|
|
85
|
-
"version": "5.0.2"
|
|
86
|
-
},
|
|
87
|
-
"node_modules/call-bind-apply-helpers": {
|
|
88
|
-
"dependencies": {
|
|
89
|
-
"es-errors": "^1.3.0",
|
|
90
|
-
"function-bind": "^1.1.2"
|
|
91
|
-
},
|
|
92
|
-
"engines": {
|
|
93
|
-
"node": ">= 0.4"
|
|
94
|
-
},
|
|
95
|
-
"integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==",
|
|
96
|
-
"license": "MIT",
|
|
97
|
-
"resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz",
|
|
98
|
-
"version": "1.0.2"
|
|
99
|
-
},
|
|
100
|
-
"node_modules/clone": {
|
|
101
|
-
"engines": {
|
|
102
|
-
"node": ">=0.8"
|
|
103
|
-
},
|
|
104
|
-
"integrity": "sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==",
|
|
105
|
-
"license": "MIT",
|
|
106
|
-
"optional": true,
|
|
107
|
-
"resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz",
|
|
108
|
-
"version": "1.0.4"
|
|
109
|
-
},
|
|
110
|
-
"node_modules/combined-stream": {
|
|
111
|
-
"dependencies": {
|
|
112
|
-
"delayed-stream": "~1.0.0"
|
|
113
|
-
},
|
|
114
|
-
"engines": {
|
|
115
|
-
"node": ">= 0.8"
|
|
116
|
-
},
|
|
117
|
-
"integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==",
|
|
118
|
-
"license": "MIT",
|
|
119
|
-
"resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz",
|
|
120
|
-
"version": "1.0.8"
|
|
121
|
-
},
|
|
122
|
-
"node_modules/console.table": {
|
|
123
|
-
"dependencies": {
|
|
124
|
-
"easy-table": "1.1.0"
|
|
125
|
-
},
|
|
126
|
-
"engines": {
|
|
127
|
-
"node": "> 0.10"
|
|
128
|
-
},
|
|
129
|
-
"integrity": "sha512-dPyZofqggxuvSf7WXvNjuRfnsOk1YazkVP8FdxH4tcH2c37wc79/Yl6Bhr7Lsu00KMgy2ql/qCMuNu8xctZM8g==",
|
|
130
|
-
"license": "MIT",
|
|
131
|
-
"resolved": "https://registry.npmjs.org/console.table/-/console.table-0.10.0.tgz",
|
|
132
|
-
"version": "0.10.0"
|
|
133
|
-
},
|
|
134
|
-
"node_modules/defaults": {
|
|
135
|
-
"dependencies": {
|
|
136
|
-
"clone": "^1.0.2"
|
|
137
|
-
},
|
|
138
|
-
"funding": {
|
|
139
|
-
"url": "https://github.com/sponsors/sindresorhus"
|
|
140
|
-
},
|
|
141
|
-
"integrity": "sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==",
|
|
142
|
-
"license": "MIT",
|
|
143
|
-
"optional": true,
|
|
144
|
-
"resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.4.tgz",
|
|
145
|
-
"version": "1.0.4"
|
|
146
|
-
},
|
|
147
|
-
"node_modules/delayed-stream": {
|
|
148
|
-
"engines": {
|
|
149
|
-
"node": ">=0.4.0"
|
|
150
|
-
},
|
|
151
|
-
"integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==",
|
|
152
|
-
"license": "MIT",
|
|
153
|
-
"resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz",
|
|
154
|
-
"version": "1.0.0"
|
|
22
|
+
"version": "0.2.2"
|
|
155
23
|
},
|
|
156
24
|
"node_modules/detect-libc": {
|
|
157
25
|
"engines": {
|
|
@@ -162,324 +30,6 @@
|
|
|
162
30
|
"resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz",
|
|
163
31
|
"version": "2.1.2"
|
|
164
32
|
},
|
|
165
|
-
"node_modules/dunder-proto": {
|
|
166
|
-
"dependencies": {
|
|
167
|
-
"call-bind-apply-helpers": "^1.0.1",
|
|
168
|
-
"es-errors": "^1.3.0",
|
|
169
|
-
"gopd": "^1.2.0"
|
|
170
|
-
},
|
|
171
|
-
"engines": {
|
|
172
|
-
"node": ">= 0.4"
|
|
173
|
-
},
|
|
174
|
-
"integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==",
|
|
175
|
-
"license": "MIT",
|
|
176
|
-
"resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz",
|
|
177
|
-
"version": "1.0.1"
|
|
178
|
-
},
|
|
179
|
-
"node_modules/easy-table": {
|
|
180
|
-
"integrity": "sha512-oq33hWOSSnl2Hoh00tZWaIPi1ievrD9aFG82/IgjlycAnW9hHx5PkJiXpxPsgEE+H7BsbVQXFVFST8TEXS6/pA==",
|
|
181
|
-
"license": "MIT",
|
|
182
|
-
"optionalDependencies": {
|
|
183
|
-
"wcwidth": ">=1.0.1"
|
|
184
|
-
},
|
|
185
|
-
"resolved": "https://registry.npmjs.org/easy-table/-/easy-table-1.1.0.tgz",
|
|
186
|
-
"version": "1.1.0"
|
|
187
|
-
},
|
|
188
|
-
"node_modules/es-define-property": {
|
|
189
|
-
"engines": {
|
|
190
|
-
"node": ">= 0.4"
|
|
191
|
-
},
|
|
192
|
-
"integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==",
|
|
193
|
-
"license": "MIT",
|
|
194
|
-
"resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz",
|
|
195
|
-
"version": "1.0.1"
|
|
196
|
-
},
|
|
197
|
-
"node_modules/es-errors": {
|
|
198
|
-
"engines": {
|
|
199
|
-
"node": ">= 0.4"
|
|
200
|
-
},
|
|
201
|
-
"integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==",
|
|
202
|
-
"license": "MIT",
|
|
203
|
-
"resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz",
|
|
204
|
-
"version": "1.3.0"
|
|
205
|
-
},
|
|
206
|
-
"node_modules/es-object-atoms": {
|
|
207
|
-
"dependencies": {
|
|
208
|
-
"es-errors": "^1.3.0"
|
|
209
|
-
},
|
|
210
|
-
"engines": {
|
|
211
|
-
"node": ">= 0.4"
|
|
212
|
-
},
|
|
213
|
-
"integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==",
|
|
214
|
-
"license": "MIT",
|
|
215
|
-
"resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz",
|
|
216
|
-
"version": "1.1.1"
|
|
217
|
-
},
|
|
218
|
-
"node_modules/es-set-tostringtag": {
|
|
219
|
-
"dependencies": {
|
|
220
|
-
"es-errors": "^1.3.0",
|
|
221
|
-
"get-intrinsic": "^1.2.6",
|
|
222
|
-
"has-tostringtag": "^1.0.2",
|
|
223
|
-
"hasown": "^2.0.2"
|
|
224
|
-
},
|
|
225
|
-
"engines": {
|
|
226
|
-
"node": ">= 0.4"
|
|
227
|
-
},
|
|
228
|
-
"integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==",
|
|
229
|
-
"license": "MIT",
|
|
230
|
-
"resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz",
|
|
231
|
-
"version": "2.1.0"
|
|
232
|
-
},
|
|
233
|
-
"node_modules/follow-redirects": {
|
|
234
|
-
"engines": {
|
|
235
|
-
"node": ">=4.0"
|
|
236
|
-
},
|
|
237
|
-
"funding": [
|
|
238
|
-
{
|
|
239
|
-
"type": "individual",
|
|
240
|
-
"url": "https://github.com/sponsors/RubenVerborgh"
|
|
241
|
-
}
|
|
242
|
-
],
|
|
243
|
-
"integrity": "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ==",
|
|
244
|
-
"license": "MIT",
|
|
245
|
-
"peerDependenciesMeta": {
|
|
246
|
-
"debug": {
|
|
247
|
-
"optional": true
|
|
248
|
-
}
|
|
249
|
-
},
|
|
250
|
-
"resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.11.tgz",
|
|
251
|
-
"version": "1.15.11"
|
|
252
|
-
},
|
|
253
|
-
"node_modules/form-data": {
|
|
254
|
-
"dependencies": {
|
|
255
|
-
"asynckit": "^0.4.0",
|
|
256
|
-
"combined-stream": "^1.0.8",
|
|
257
|
-
"es-set-tostringtag": "^2.1.0",
|
|
258
|
-
"hasown": "^2.0.2",
|
|
259
|
-
"mime-types": "^2.1.12"
|
|
260
|
-
},
|
|
261
|
-
"engines": {
|
|
262
|
-
"node": ">= 6"
|
|
263
|
-
},
|
|
264
|
-
"integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==",
|
|
265
|
-
"license": "MIT",
|
|
266
|
-
"resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz",
|
|
267
|
-
"version": "4.0.5"
|
|
268
|
-
},
|
|
269
|
-
"node_modules/function-bind": {
|
|
270
|
-
"funding": {
|
|
271
|
-
"url": "https://github.com/sponsors/ljharb"
|
|
272
|
-
},
|
|
273
|
-
"integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==",
|
|
274
|
-
"license": "MIT",
|
|
275
|
-
"resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz",
|
|
276
|
-
"version": "1.1.2"
|
|
277
|
-
},
|
|
278
|
-
"node_modules/get-intrinsic": {
|
|
279
|
-
"dependencies": {
|
|
280
|
-
"call-bind-apply-helpers": "^1.0.2",
|
|
281
|
-
"es-define-property": "^1.0.1",
|
|
282
|
-
"es-errors": "^1.3.0",
|
|
283
|
-
"es-object-atoms": "^1.1.1",
|
|
284
|
-
"function-bind": "^1.1.2",
|
|
285
|
-
"get-proto": "^1.0.1",
|
|
286
|
-
"gopd": "^1.2.0",
|
|
287
|
-
"has-symbols": "^1.1.0",
|
|
288
|
-
"hasown": "^2.0.2",
|
|
289
|
-
"math-intrinsics": "^1.1.0"
|
|
290
|
-
},
|
|
291
|
-
"engines": {
|
|
292
|
-
"node": ">= 0.4"
|
|
293
|
-
},
|
|
294
|
-
"funding": {
|
|
295
|
-
"url": "https://github.com/sponsors/ljharb"
|
|
296
|
-
},
|
|
297
|
-
"integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==",
|
|
298
|
-
"license": "MIT",
|
|
299
|
-
"resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz",
|
|
300
|
-
"version": "1.3.0"
|
|
301
|
-
},
|
|
302
|
-
"node_modules/get-proto": {
|
|
303
|
-
"dependencies": {
|
|
304
|
-
"dunder-proto": "^1.0.1",
|
|
305
|
-
"es-object-atoms": "^1.0.0"
|
|
306
|
-
},
|
|
307
|
-
"engines": {
|
|
308
|
-
"node": ">= 0.4"
|
|
309
|
-
},
|
|
310
|
-
"integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==",
|
|
311
|
-
"license": "MIT",
|
|
312
|
-
"resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz",
|
|
313
|
-
"version": "1.0.1"
|
|
314
|
-
},
|
|
315
|
-
"node_modules/glob": {
|
|
316
|
-
"dependencies": {
|
|
317
|
-
"minimatch": "^10.2.0",
|
|
318
|
-
"minipass": "^7.1.2",
|
|
319
|
-
"path-scurry": "^2.0.0"
|
|
320
|
-
},
|
|
321
|
-
"engines": {
|
|
322
|
-
"node": "20 || >=22"
|
|
323
|
-
},
|
|
324
|
-
"funding": {
|
|
325
|
-
"url": "https://github.com/sponsors/isaacs"
|
|
326
|
-
},
|
|
327
|
-
"integrity": "sha512-/g3B0mC+4x724v1TgtBlBtt2hPi/EWptsIAmXUx9Z2rvBYleQcsrmaOzd5LyL50jf/Soi83ZDJmw2+XqvH/EeA==",
|
|
328
|
-
"license": "BlueOak-1.0.0",
|
|
329
|
-
"resolved": "https://registry.npmjs.org/glob/-/glob-13.0.3.tgz",
|
|
330
|
-
"version": "13.0.3"
|
|
331
|
-
},
|
|
332
|
-
"node_modules/gopd": {
|
|
333
|
-
"engines": {
|
|
334
|
-
"node": ">= 0.4"
|
|
335
|
-
},
|
|
336
|
-
"funding": {
|
|
337
|
-
"url": "https://github.com/sponsors/ljharb"
|
|
338
|
-
},
|
|
339
|
-
"integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==",
|
|
340
|
-
"license": "MIT",
|
|
341
|
-
"resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz",
|
|
342
|
-
"version": "1.2.0"
|
|
343
|
-
},
|
|
344
|
-
"node_modules/has-symbols": {
|
|
345
|
-
"engines": {
|
|
346
|
-
"node": ">= 0.4"
|
|
347
|
-
},
|
|
348
|
-
"funding": {
|
|
349
|
-
"url": "https://github.com/sponsors/ljharb"
|
|
350
|
-
},
|
|
351
|
-
"integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==",
|
|
352
|
-
"license": "MIT",
|
|
353
|
-
"resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz",
|
|
354
|
-
"version": "1.1.0"
|
|
355
|
-
},
|
|
356
|
-
"node_modules/has-tostringtag": {
|
|
357
|
-
"dependencies": {
|
|
358
|
-
"has-symbols": "^1.0.3"
|
|
359
|
-
},
|
|
360
|
-
"engines": {
|
|
361
|
-
"node": ">= 0.4"
|
|
362
|
-
},
|
|
363
|
-
"funding": {
|
|
364
|
-
"url": "https://github.com/sponsors/ljharb"
|
|
365
|
-
},
|
|
366
|
-
"integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==",
|
|
367
|
-
"license": "MIT",
|
|
368
|
-
"resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz",
|
|
369
|
-
"version": "1.0.2"
|
|
370
|
-
},
|
|
371
|
-
"node_modules/hasown": {
|
|
372
|
-
"dependencies": {
|
|
373
|
-
"function-bind": "^1.1.2"
|
|
374
|
-
},
|
|
375
|
-
"engines": {
|
|
376
|
-
"node": ">= 0.4"
|
|
377
|
-
},
|
|
378
|
-
"integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==",
|
|
379
|
-
"license": "MIT",
|
|
380
|
-
"resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz",
|
|
381
|
-
"version": "2.0.2"
|
|
382
|
-
},
|
|
383
|
-
"node_modules/jackspeak": {
|
|
384
|
-
"dependencies": {
|
|
385
|
-
"@isaacs/cliui": "^9.0.0"
|
|
386
|
-
},
|
|
387
|
-
"engines": {
|
|
388
|
-
"node": "20 || >=22"
|
|
389
|
-
},
|
|
390
|
-
"funding": {
|
|
391
|
-
"url": "https://github.com/sponsors/isaacs"
|
|
392
|
-
},
|
|
393
|
-
"integrity": "sha512-ykkVRwrYvFm1nb2AJfKKYPr0emF6IiXDYUaFx4Zn9ZuIH7MrzEZ3sD5RlqGXNRpHtvUHJyOnCEFxOlNDtGo7wg==",
|
|
394
|
-
"license": "BlueOak-1.0.0",
|
|
395
|
-
"resolved": "https://registry.npmjs.org/jackspeak/-/jackspeak-4.2.3.tgz",
|
|
396
|
-
"version": "4.2.3"
|
|
397
|
-
},
|
|
398
|
-
"node_modules/lru-cache": {
|
|
399
|
-
"engines": {
|
|
400
|
-
"node": "20 || >=22"
|
|
401
|
-
},
|
|
402
|
-
"integrity": "sha512-ESL2CrkS/2wTPfuend7Zhkzo2u0daGJ/A2VucJOgQ/C48S/zB8MMeMHSGKYpXhIjbPxfuezITkaBH1wqv00DDQ==",
|
|
403
|
-
"license": "BlueOak-1.0.0",
|
|
404
|
-
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.2.6.tgz",
|
|
405
|
-
"version": "11.2.6"
|
|
406
|
-
},
|
|
407
|
-
"node_modules/math-intrinsics": {
|
|
408
|
-
"engines": {
|
|
409
|
-
"node": ">= 0.4"
|
|
410
|
-
},
|
|
411
|
-
"integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==",
|
|
412
|
-
"license": "MIT",
|
|
413
|
-
"resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz",
|
|
414
|
-
"version": "1.1.0"
|
|
415
|
-
},
|
|
416
|
-
"node_modules/mime-db": {
|
|
417
|
-
"engines": {
|
|
418
|
-
"node": ">= 0.6"
|
|
419
|
-
},
|
|
420
|
-
"integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==",
|
|
421
|
-
"license": "MIT",
|
|
422
|
-
"resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz",
|
|
423
|
-
"version": "1.52.0"
|
|
424
|
-
},
|
|
425
|
-
"node_modules/mime-types": {
|
|
426
|
-
"dependencies": {
|
|
427
|
-
"mime-db": "1.52.0"
|
|
428
|
-
},
|
|
429
|
-
"engines": {
|
|
430
|
-
"node": ">= 0.6"
|
|
431
|
-
},
|
|
432
|
-
"integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==",
|
|
433
|
-
"license": "MIT",
|
|
434
|
-
"resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz",
|
|
435
|
-
"version": "2.1.35"
|
|
436
|
-
},
|
|
437
|
-
"node_modules/minimatch": {
|
|
438
|
-
"dependencies": {
|
|
439
|
-
"brace-expansion": "^5.0.2"
|
|
440
|
-
},
|
|
441
|
-
"engines": {
|
|
442
|
-
"node": "20 || >=22"
|
|
443
|
-
},
|
|
444
|
-
"funding": {
|
|
445
|
-
"url": "https://github.com/sponsors/isaacs"
|
|
446
|
-
},
|
|
447
|
-
"integrity": "sha512-ugkC31VaVg9cF0DFVoADH12k6061zNZkZON+aX8AWsR9GhPcErkcMBceb6znR8wLERM2AkkOxy2nWRLpT9Jq5w==",
|
|
448
|
-
"license": "BlueOak-1.0.0",
|
|
449
|
-
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-10.2.0.tgz",
|
|
450
|
-
"version": "10.2.0"
|
|
451
|
-
},
|
|
452
|
-
"node_modules/minipass": {
|
|
453
|
-
"engines": {
|
|
454
|
-
"node": ">=16 || 14 >=14.17"
|
|
455
|
-
},
|
|
456
|
-
"integrity": "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==",
|
|
457
|
-
"license": "ISC",
|
|
458
|
-
"resolved": "https://registry.npmjs.org/minipass/-/minipass-7.1.2.tgz",
|
|
459
|
-
"version": "7.1.2"
|
|
460
|
-
},
|
|
461
|
-
"node_modules/package-json-from-dist": {
|
|
462
|
-
"integrity": "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==",
|
|
463
|
-
"license": "BlueOak-1.0.0",
|
|
464
|
-
"resolved": "https://registry.npmjs.org/package-json-from-dist/-/package-json-from-dist-1.0.1.tgz",
|
|
465
|
-
"version": "1.0.1"
|
|
466
|
-
},
|
|
467
|
-
"node_modules/path-scurry": {
|
|
468
|
-
"dependencies": {
|
|
469
|
-
"lru-cache": "^11.0.0",
|
|
470
|
-
"minipass": "^7.1.2"
|
|
471
|
-
},
|
|
472
|
-
"engines": {
|
|
473
|
-
"node": "20 || >=22"
|
|
474
|
-
},
|
|
475
|
-
"funding": {
|
|
476
|
-
"url": "https://github.com/sponsors/isaacs"
|
|
477
|
-
},
|
|
478
|
-
"integrity": "sha512-oWyT4gICAu+kaA7QWk/jvCHWarMKNs6pXOGWKDTr7cw4IGcUbW+PeTfbaQiLGheFRpjo6O9J0PmyMfQPjH71oA==",
|
|
479
|
-
"license": "BlueOak-1.0.0",
|
|
480
|
-
"resolved": "https://registry.npmjs.org/path-scurry/-/path-scurry-2.0.1.tgz",
|
|
481
|
-
"version": "2.0.1"
|
|
482
|
-
},
|
|
483
33
|
"node_modules/prettier": {
|
|
484
34
|
"bin": {
|
|
485
35
|
"prettier": "bin/prettier.cjs"
|
|
@@ -491,56 +41,12 @@
|
|
|
491
41
|
"funding": {
|
|
492
42
|
"url": "https://github.com/prettier/prettier?sponsor=1"
|
|
493
43
|
},
|
|
494
|
-
"integrity": "sha512-
|
|
495
|
-
"license": "MIT",
|
|
496
|
-
"resolved": "https://registry.npmjs.org/prettier/-/prettier-3.8.1.tgz",
|
|
497
|
-
"version": "3.8.1"
|
|
498
|
-
},
|
|
499
|
-
"node_modules/proxy-from-env": {
|
|
500
|
-
"integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==",
|
|
501
|
-
"license": "MIT",
|
|
502
|
-
"resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz",
|
|
503
|
-
"version": "1.1.0"
|
|
504
|
-
},
|
|
505
|
-
"node_modules/rimraf": {
|
|
506
|
-
"bin": {
|
|
507
|
-
"rimraf": "dist/esm/bin.mjs"
|
|
508
|
-
},
|
|
509
|
-
"dependencies": {
|
|
510
|
-
"glob": "^13.0.3",
|
|
511
|
-
"package-json-from-dist": "^1.0.1"
|
|
512
|
-
},
|
|
513
|
-
"engines": {
|
|
514
|
-
"node": "20 || >=22"
|
|
515
|
-
},
|
|
516
|
-
"funding": {
|
|
517
|
-
"url": "https://github.com/sponsors/isaacs"
|
|
518
|
-
},
|
|
519
|
-
"integrity": "sha512-LKg+Cr2ZF61fkcaK1UdkH2yEBBKnYjTyWzTJT6KNPcSPaiT7HSdhtMXQuN5wkTX0Xu72KQ1l8S42rlmexS2hSA==",
|
|
520
|
-
"license": "BlueOak-1.0.0",
|
|
521
|
-
"resolved": "https://registry.npmjs.org/rimraf/-/rimraf-6.1.3.tgz",
|
|
522
|
-
"version": "6.1.3"
|
|
523
|
-
},
|
|
524
|
-
"node_modules/tunnel": {
|
|
525
|
-
"engines": {
|
|
526
|
-
"node": ">=0.6.11 <=0.7.0 || >=0.7.3"
|
|
527
|
-
},
|
|
528
|
-
"integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==",
|
|
529
|
-
"license": "MIT",
|
|
530
|
-
"resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz",
|
|
531
|
-
"version": "0.0.6"
|
|
532
|
-
},
|
|
533
|
-
"node_modules/wcwidth": {
|
|
534
|
-
"dependencies": {
|
|
535
|
-
"defaults": "^1.0.3"
|
|
536
|
-
},
|
|
537
|
-
"integrity": "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==",
|
|
44
|
+
"integrity": "sha512-7igPTM53cGHMW8xWuVTydi2KO233VFiTNyF5hLJqpilHfmn8C8gPf+PS7dUT64YcXFbiMGZxS9pCSxL/Dxm/Jw==",
|
|
538
45
|
"license": "MIT",
|
|
539
|
-
"
|
|
540
|
-
"
|
|
541
|
-
"version": "1.0.1"
|
|
46
|
+
"resolved": "https://registry.npmjs.org/prettier/-/prettier-3.8.3.tgz",
|
|
47
|
+
"version": "3.8.3"
|
|
542
48
|
}
|
|
543
49
|
},
|
|
544
50
|
"requires": true,
|
|
545
|
-
"version": "0.
|
|
51
|
+
"version": "0.2.2"
|
|
546
52
|
}
|
package/package.json
CHANGED
|
@@ -1,23 +1,19 @@
|
|
|
1
1
|
{
|
|
2
2
|
"artifactDownloadUrls": [
|
|
3
|
-
"https://github.com/akesson/figma-explorer/releases/download/v0.
|
|
3
|
+
"https://github.com/akesson/figma-explorer/releases/download/v0.2.2"
|
|
4
4
|
],
|
|
5
5
|
"bin": {
|
|
6
6
|
"figma-explorer": "run-figma-explorer.js"
|
|
7
7
|
},
|
|
8
8
|
"dependencies": {
|
|
9
|
-
"
|
|
10
|
-
"axios-proxy-builder": "^0.1.2",
|
|
11
|
-
"console.table": "^0.10.0",
|
|
12
|
-
"detect-libc": "^2.1.2",
|
|
13
|
-
"rimraf": "^6.1.3"
|
|
9
|
+
"detect-libc": "^2.1.2"
|
|
14
10
|
},
|
|
15
11
|
"description": "High-level CLI on top of the Figma REST API: name-based navigation, asset extraction, design tokens, and bundled context export.",
|
|
16
12
|
"devDependencies": {
|
|
17
|
-
"prettier": "^3.8.
|
|
13
|
+
"prettier": "^3.8.3"
|
|
18
14
|
},
|
|
19
15
|
"engines": {
|
|
20
|
-
"node": ">=14",
|
|
16
|
+
"node": ">=14.14",
|
|
21
17
|
"npm": ">=6"
|
|
22
18
|
},
|
|
23
19
|
"glibcMinimum": {
|
|
@@ -99,7 +95,7 @@
|
|
|
99
95
|
"zipExt": ".tar.xz"
|
|
100
96
|
}
|
|
101
97
|
},
|
|
102
|
-
"version": "0.
|
|
98
|
+
"version": "0.2.2",
|
|
103
99
|
"volta": {
|
|
104
100
|
"node": "18.14.1",
|
|
105
101
|
"npm": "9.5.0"
|