Skip to content

Getting started

Emendant tells you which call sites a known API or SDK change affects. It starts from the packages your repository actually declares, then reports only structurally verified uses.

  • Node.js 20 or later.
  • A TypeScript or JavaScript repository.
  • A supported manifest such as package.json.
  • For exact version placement, a supported lockfile.

Emendant supports declared monorepo workspaces. Run it once from the repository root; each workspace is detected and reported separately.

From the repository root:

Terminal window
npx emendant scan

Emendant then:

  1. Reads manifests and lockfiles to identify packages and installed versions.
  2. Selects relevant changes from the feed, which is the one bundled with the CLI until a newer snapshot is fetched.
  3. Filters out ignored, generated, oversized, and irrelevant files.
  4. Parses candidate TypeScript and JavaScript files and traces package values across local modules.
  5. Prints findings grouped by workspace, package, and change.

The scan is read-only. It does not execute your project, and it makes no network request unless you have turned automatic feed updates on.

The first time you run Emendant at a terminal, it asks four short questions before it scans, and never asks them again.

1) codex, using the login your Codex CLI already has (no API key, no extra billing)
2) Claude Code (local), using the login your Claude Code CLI already has (no API key, no extra billing)
3) Claude (API key), billed per token to the ANTHROPIC_API_KEY in this environment
Which provider should write those patches? [1-3, or return for none]
Check for feed updates automatically? [y/N]
Send that when a patch fails? [Y/n]
Supported SDKs in this repository
openai installed 4.104.0, 12 changes to check
Scan this workspace for these 12 changes now? [Y/n]

None of these is asked anywhere but at a terminal. A run in CI, a run in a pipe and a run under --json are byte for byte what they were before this existed, and a machine that was never asked behaves as though every answer were no.

Most patches are written on your machine by a transform. A few changes have no mechanical rewrite, and emendant fix can ask a model you name to write those. Press return to decline. Only providers whose credential is already in your environment are offered, the key is read when a request is made and never stored, and what Emendant records is the provider name. A project’s own emendant.json overrides it, and emendant fix offers the choice again at the moment a finding needs one.

The third question is the only one whose default sends anything. When a patch fails its typecheck or tests against a new release, the errors say what that release broke that the feed did not describe, and Emendant can send that back so the feed covers it next time: the package, the two versions, the error codes and the names the new release’s own type declarations contain. No path, no line, no code and nothing that says which repository it is. The record is written to .emendant/contribution.json before it is sent, so you can read exactly what left. Type n to decline, or emendant feed contribute --disable later. The privacy notice is the full statement of it.

If your organisation permits only its own hosts, azure sends the excerpt to an Azure AI Foundry resource in your tenant instead of to a vendor. It appears in this list once AZURE_OPENAI_ENDPOINT and a credential are exported, and picking it asks one more question: the name of the deployment that should write the patches. Nothing can detect that name, because the resource holding it is yours. Export AZURE_OPENAI_DEPLOYMENT to answer it in advance. The configuration reference has the flags and the two authentication modes.

The supported SDK list costs no scanning: it comes from your manifests and the feed, so it is ready before the walk starts. The count is how many changes this scan is about to look for.

The last question defaults to yes, because you already typed scan. All of this needs a terminal, so a scan in CI or under --json goes straight to the report.

A finding looks broadly like this:

openai declared 4.104.0 → 5.0.0
1 change affects this repository
────────────────────────────────────────────────────────────────
× breaking fileFromPath helper removed
filefrompath-removed assisted fix
src/upload.ts:2:10
2 │ import { fileFromPath } from 'openai/uploads';
│ ^
src/upload.ts:4:59
4 │ export const attach = (path: string): Promise<unknown> => fileFromPath(path);
│ ^
1 finding · 2 call sites in 1 file
→ emendant explain openai-npm-5.0.0-filefrompath-removed the sources and the migration guidance

The heading reads from what you have installed to the release that changes it, and the arrow is drawn only when the upgrade is still ahead of you. Under the title is the tail of the change ID, and beside it what emendant fix would do with this change here, so you can tell a deterministic rewrite from one that needs a model without running anything. Only the tail prints, because the package, the ecosystem and the release in front of it are already in the heading above. emendant explain takes the tail back, and names the candidates when one tail belongs to two packages. The call site is a terminal-clickable path:line:column, and the caret under the source line marks the column it names:

Terminal window
npx emendant explain openai-npm-5.0.0-filefrompath-removed
Code Meaning
0 The scan completed with no findings.
1 The scan completed and found affected code.
2 Emendant could not complete the scan.

Exit code 1 is a result, not a crash. This distinction matters when you run Emendant in CI.