The edsnx command line
Every designer command from a shell, with JSON output, transactions and a session log; MCP, JSON-RPC and scripts.
edsnx (Electronics Designer; sk is an alias) runs every designer command from a shell: the same command
registry as the editor, applied to the files with the editor’s own minimal-diff writer. It ships as
out/cli.js in the extension (bin in package.json): npm i -g the repository, or
node path/to/extension/out/cli.js, or alias edsnx="node …/out/cli.js".
edsnx <category> <command> [path] [--flag value …] [global flags]
edsnx project new blinky --template 2layer --size 50x35 # .kicad_pro/.kicad_sch/.kicad_pcb/.kicad_prl + lib tables
cd blinky
edsnx pcb place-footprint blinky.kicad_pcb --lib Resistor_SMD --name R_0603_1608Metric --at 110,110 --ref R1 --pad-nets '{"1":"VIN","2":"GND"}'
edsnx pcb add-track blinky.kicad_pcb --layer F.Cu --net GND --width 0.25 --pts 110,110 120,110
edsnx pcb fill-zones blinky.kicad_pcb
edsnx pcb drc blinky.kicad_pcb --json # alias of `edsnx check drc`
edsnx project checks # ERC + DRC summary, exit 1 on errors
edsnx check blinky.kicad_pcb --check --watch # native DRC, re-run on changes, exit 1 on errors
edsnx project fab --out fab # Gerbers, drill and position filesHelp. edsnx help lists the categories and global flags, edsnx help pcb (or edsnx pcb help) the commands
of a category, edsnx pcb add-track --help one command: its arguments, units, defaults and examples, all
generated from the registry.
Arguments. The first positional is the document path. Flags are the command’s arguments in kebab-case:
numbers (--width 0.25, mm), points (--at 30,20), point lists (--pts 10,10 20,10 30,10, or repeat the
flag), lists (--layers F.Cu,B.Cu), booleans (--locked, --no-locked), enums (checked), objects as JSON
(--zone '{"layers":["B.Cu"],"net":"GND"}') or field by field (--zone.net GND --zone.min-thickness 0.25).
--args-json '{…}' and --args-file args.json give all arguments as JSON (flags given too win).
Global flags.
| Flag | |
|---|---|
--json | machine output; errors as {"error":{"code","message","data"}} |
--dry-run | apply in memory, print the unified diff, write nothing |
--check | run the DRC/ERC after the edit (library rules included: footprints and symbols checked against the library tables); refuse it (nothing written) when it adds violations |
--revision <hash> | refuse unless the file’s hash matches (from edsnx pcb describe; a 7+ character prefix is enough) |
--batch <file.jsonl> | run {"id": "pcb.addTrack", "args": {…}} lines as one transaction: everything or nothing; "$2.newIds[0]" in args is an id created by step 2 ("$prev.newIds[0]": the previous step) |
--attach | run in the open VS Code editor (live, with undo and review; see below); headless with a warning when no editor listens |
--actor <name> | who edits (log, editor history); default cli |
--cwd <dir>, --quiet, --log <file>, --no-log | working folder, ids and errors only, log file, no log |
Edits print a summary (label, revision, hash) and then the created ids, one per line (--quiet: the ids
only; --json: the result with newIds). Exit codes: 0 done, 1 refused (invalid arguments, stale
revision, failed check, missing service such as kicad-cli, errors found by project checks), 2 unknown
command or flag (with a “did you mean”).
Session log and replay. Every command appends one line to .edsnx/session.jsonl next to the project:
sequence, time, actor, command id, arguments (paths relative to the project), revision and hash before and
after, created ids. Commands run through the editor (--attach, MCP) are logged by the editor into the same
file; a headless edsnx mcp or edsnx serve appends its tool calls there too. The file diffs well in git (one JSON
object per line, stable key order). edsnx session export [--format markdown|json] [--out file] [--since …] [--limit n] (the registry command session.export, also an MCP tool and Electronics Designer: Export session in the
editor) writes the log as a Markdown report (summary, one row per command, the failures) or as one JSON document.
edsnx log [--since 10m|<seq>|<date>] [--limit n] [--json] prints it as equivalent command lines;
edsnx replay .edsnx/session.jsonl [--from n] [--to n] [--dry-run] [--force] [--all] re-executes the edits
(and project new), maps the ids created in the original session to the new ones, and verifies the document
before and after every step with a uuid-insensitive hash: a mismatch stops the replay unless --force.
Projects. edsnx project new <name> --template 2layer|4layer|6layer [--size WxH] [--stackup <preset>] [--out dir] [--title …] [--company …] [--rev …] writes a project whose layer stack, stack-up, design rules and net
classes agree (presets: generic-2l-1.6, generic-2l-0.8, jlc-4l-1.6, generic-4l-1.6), with a board
outline at (100, 100) and library tables (empty when KiCad’s global tables exist, otherwise listing the
installed libraries). project new is the registry command project.new, so agents create projects with the
project_new MCP tool and scripts with project.new(); a sub-sheet added with sch.addSheet gets its (empty)
schematic file on the next save. edsnx query pairs and edsnx query groups list a board’s differential pairs (nets,
width / gap, routed length of each side, skew) and its matched-length groups (target, per-member length, delta and
status). edsnx project update-pcb, edsnx project checks [--engine kicad-cli] [--warnings]
and edsnx project fab [--out fab] cover the rest of the flow; examples/sample-project is generated by
src/cli/sampleProject.ts entirely through these commands.
Design files. The native format of the Electronics Designer, .design.prj / .sch / .pcb / .sym / .fp /
.doc / .panel / .req, is a JSON file holding the consolidated document and, after it, one line per edit
(who, when, what), so saving appends a line and two branches merge line by line. The editors open design files
and keep a design cache next to KiCad files (see Design files); the format, its JSON schemas
(shipped in schemas/design/) and the edsnx design commands are there for scripts, agents and CI: edsnx design validate . (exit 1 on an invalid file: a CI gate),
edsnx design log <file>, edsnx design consolidate <file> (fold the edits into the document),
edsnx design upgrade and edsnx design merge <base> <ours> <theirs> (also a git merge driver). A KiCad project
becomes design files with edsnx design import blinky/ --out design/ (every KiCad 6–10 node mapped; the loss report
lists what is kept as KiCad text or left as a path, --report json for scripts) and comes back with
edsnx design export design/ --out kicad/, byte for byte when nothing was edited; edsnx design roundtrip blinky/
checks that (exit 1 on a difference, kicad-cli judging files whose bytes differ). edsnx design migrate blinky/
converts a project in place (design files authoritative, KiCad files exported on save); edsnx serve and the MCP
session open blinky.design.pcb like a KiCad board. The reference is docs/design-file-format.md (“KiCad mapping”,
“Editors”).
Shell completion. edsnx completion bash > ~/.local/share/bash-completion/completions/edsnx,
edsnx completion zsh > "${fpath[1]}/_edsnx", edsnx completion fish > ~/.config/fish/completions/edsnx.fish.
npm run cli:check checks all three scripts (the shell’s own syntax check when it is installed, else a structural
check of quotes, blocks, headers and every command path).
CI. npm run build && npm run cli:check runs a scripted session with the bundle in a temp folder (new
project, place, route in a batch, fill, DRC, kicad-cli checks, fab, log, replay) and fails on any deviation.
MCP, JSON-RPC and scripts#
The same commands are served to agents and programs (details in docs/agent-protocols.md):
edsnx mcp: a Model Context Protocol server on stdio — every non-UI command as a tool (pcb_addTrack,check_drc, …), board and schematic resources (kicad://board/<path>/items|nets|drc|render.png,kicad://schematic/<path>/sheets|erc) and thedesign-workflowprompt. Clients on protocol 2025-06-18 or newer get each tool’soutputSchema(from the command’s result schema) and the result asstructuredContent. Register it with Claude Code:claude mcp add edsnx -- edsnx mcp(headless, on the files) orclaude mcp add edsnx -- edsnx mcp --attach(the editors open in VS Code, see below), or commit a.mcp.jsonlike examples/mcp.json. Theelectronics-designerskill (.claude/skills/electronics-designer/SKILL.md) teaches Claude the workflow.edsnx serve: JSON-RPC 2.0 on stdio (--stdio) or a Unix socket (--socket <path>, several clients sharing one session): every command as a method,rpc.discover,document.changednotifications, batches, transactions and undo. Nothing is written untilsession.save(or--auto-save).edsnx run script.ts: a TypeScript or JavaScript script with the typed APIimport { board, sch, project, lib, query } from '@softforge/edsnx-api'(types in src/api/edsnx-api.d.ts); the session is saved when the script ends unless it throws or--no-save. A script may import its own modules (./lib/util,../shared/nets.js, folders with anindex.ts): esbuild bundles them when it is installed; otherwise Node strips the types of each module and runs them from a temporary copy of the tree, so multi-file scripts work in the packaged extension too. VS Code add-ons get the same API on the open editors asapi.edsnxwhile the agent server runs.edsnx render png|svg|diff: a PNG of a board or schematic drawn by the editor’s own renderer in headless Chromium (layers, region, highlighted net, 2D or 3D; needs Chrome or Chromium,$CHROME_PATH), an SVG plot with kicad-cli, and a visual diff of two PNGs or two documents.