Load icons from Figma, a local SVG folder, or later other design tools, clean them into Iconify JSON, and distribute them to every app that already understands Iconify, UnoCSS, or Tailwind.
Docs: https://iconctl.icebreaker.top
pnpm add -D iconctl
pnpm exec iconctl init
pnpm exec iconctl sync<span class="i-brand-arrow-left text-primary"></span>Iconify JSON is the engineering source. Figma is one input, not the product.
| Package | Role |
|---|---|
iconctl |
CLI + public API |
@iconctl/core |
Pipeline library |
| Command | Purpose |
|---|---|
iconctl init |
Create a new config interactively or from explicit options |
iconctl sync |
Load sources, clean, validate, export |
iconctl watch |
Continuously sync local SVG folders and reload config |
iconctl cache diagnose |
Inspect remote Iconify caches, including missing or corrupt entries |
iconctl check |
Validate configured output or --input icons.json |
iconctl preview |
Write a searchable offline gallery from config or --input icons.json |
iconctl diff <before> <after> |
Compare local Iconify JSON and optionally write an offline HTML or Markdown report |
iconctl types |
Generate name types from local Iconify JSON |
For scripts, provide a source, location and prefix:
pnpm exec iconctl init --source directory --input ./raw-svg --prefix brand --no-interactive --jsoninit creates a new iconctl.config.ts without overwriting an existing target. Use --config ./config/brand.config.ts for another .ts target and --json-output ./generated/icons.json to set the generated collection path. --json disables prompts and returns one result object; --dry-run validates without writing any files or directories. Initialization only creates the config; run authentication and sync separately. Relative paths still use the current directory when the config is nested. See scriptable initialization for all six sources, iconfont --url, required options and cancellation.
preview.html works offline: search full Iconify names or utility classes, then copy brand:arrow-left or i-brand-arrow-left. Clipboard restrictions show a selectable manual-copy fallback. All icons remain visible when JavaScript is disabled. Class shortcuts require lowercase letters/digits separated by single hyphens in both prefix and name, and a configured icon utility consumer. Without --input, iconctl preview runs sync and can contact your configured sources.
To browse an existing collection, run iconctl preview --input ./icons.json --output ./reports/preview.html. This uses only local files, executes no config, and preserves source bytes. The default output is preview.html in the current directory. Local --dry-run --json validates without creating files, directories or caches. See local preview.
sync --json prints added, removed, changed, skipped, sources, fileVersion, and outputFiles. Validation failures exit non-zero and do not write a partial set.
sync({ signal }) supports caller cancellation. Individual import/processing failures now also block output replacement by default. Explicit continueOnError: true exports available icons with complete: false, diagnostic issues, and diff.deletionsReliable: false; removals and changelog updates are suppressed. Outputs are staged before commit. Cancellation before commit preserves old outputs; cancellation after commit starts waits for successful completion. Shared OAuth refresh finishes safely before cancellation returns. Cross-path atomic publication is not guaranteed; see cancellation and integrity for the full contract.
For local development, iconctl watch performs an initial sync and watches SVG edits. Keep inputs such as raw-svg separate from generated SVG/package directories. It supports local directory, jsdesign.dir, iconfont.dir and iconify.file sources; remote sources still use sync. watch --json emits NDJSON events. See local watch for configuration recovery, cancellation and the API.
Add optional output.sprite: 'icons.svg' to export one SVG symbol collection alongside Iconify JSON. Reference an icon with <use href="/icons.svg#iconctl-brand-home">; symbol IDs are stable and aliases retain their transforms. For an existing local collection, run iconctl sprite --input collection.json --output icons.svg without config or credentials. See SVG sprites for inline use, accessibility and the supported static SVG format.
Local Iconify JSON can be mixed with SVG or remote sources: { type: 'iconify', file: './vendor/icons.json', include: ['home'], namePrefix: 'vendor-' }. Aliases, rotations and inherited dimensions are resolved before the usual processing. See Iconify JSON sources.
Local Iconify collection files are read as UTF-8. One leading UTF-8 BOM is accepted; malformed UTF-8 is rejected instead of being replaced. Valid Unicode, including non-ASCII names and a literal replacement character, is preserved. HTTPS Iconify URLs use the same strict parsing and conditional ETag/Last-Modified cache; remote sources are fetched by sync and excluded from local watch roots.
Remote Iconify collections and cached collection bodies are limited to 25 MiB of UTF-8 data, measured after HTTP decompression. The request's 30-second deadline and caller cancellation remain active while reading the response. An oversized response fails without replacing the cache or outputs. iconctl cache diagnose --strict reports oversized caches as invalid; online sync refetches them and offline sync fails. This limit does not apply to local Iconify files. See remote limits and cache diagnostics.
To check a standalone collection, run iconctl check --input ./icons.json --width 24 --height 24 --json. This does not load configuration, contact sources or write files. Dimensions are optional; --name overrides the naming regex. Failure reports include import, SVG processing and validation issues and exit with status 1. See artifact checks.
Review two exported collections with iconctl diff before.json after.json --html diff.html. It resolves aliases, inherited dimensions and transforms, reports prefix changes, and needs no configuration or credentials. Use --markdown diff.md for a deterministic review table that is easy to attach to a change. Add --check --json for CI; --check exits 1 when icons or their prefix differ. See offline comparison for the report, dry-run and API.
Generate types from an existing collection with iconctl types --input ./icons.json. The default icons.d.ts is for type checking; use --output ./icon-names.ts for a runtime prefix export. No config or credentials are needed. See local type generation.
import { defineConfig } from 'iconctl'
export default defineConfig({
prefix: 'brand',
sources: [
{
type: 'figma',
file: 'https://www.figma.com/design/<fileKey>/Icons',
pages: ['Icons'],
},
{
type: 'directory',
dir: './raw-svg',
},
{
type: 'mastergo',
file: 'https://mastergo.com/file/<fileId>?layer_id=<pageId>',
},
{
type: 'iconfont',
url: 'https://at.alicdn.com/t/c/font_123456_abcdef.js',
},
{
type: 'jsdesign',
dir: './jsdesign-svg',
},
],
output: {
json: 'icons.json',
svg: 'svg',
sprite: 'icons.svg', // Optional SVG symbol sprite
jsonPackage: 'packages/icons',
preview: 'preview.html',
},
validate: {
width: 24,
height: 24,
},
})Figma supports OAuth with automatic renewal: configure your app, run iconctl auth figma login, and sync / preview refresh tokens as needed. See the OAuth setup guide. Local credentials stay outside the repository; CI uses an independent authorization and three OAuth Secrets. Personal tokens via FIGMA_TOKEN remain supported with manual renewal; MasterGo uses MASTERGO_TOKEN. Directory, iconfont Symbol URLs, and 即时设计 export folders need no token. MasterGo requires Team edition and a team-project file. 即时设计 has no public REST for CLI — export SVG first.
- uses: icelib/iconctl@v1
with:
figma-client-id: ${{ secrets.FIGMA_CLIENT_ID }}
figma-client-secret: ${{ secrets.FIGMA_CLIENT_SECRET }}
figma-refresh-token: ${{ secrets.FIGMA_REFRESH_TOKEN }}
mastergo-token: ${{ secrets.MASTERGO_TOKEN }}
commit: trueMIT
OAuth workflows must serialize jobs sharing an authorization with a fixed concurrency group and cancel-in-progress: false. See github-publish.yml.
The owner-only Vue/Hono console lives at /app alongside the public documentation. See setup, GitHub App, OAuth and deployment.
Console projects can import an Iconify JSON file from each task's pinned repository commit or a local upload of up to 10 MiB, select original icon/alias names and add a literal name prefix. Uploads take effect after saving the project and remain fixed to each task. See repository or uploaded Iconify JSON.
Console snapshots also offer complete Iconify JSON downloads, including check/dry-run results without generated files and historical failed attempts. The export preserves the stored processed collection; diagnostics remain in the review.