Skip to content
API Weld

Config and lockfile

apiweld.config.ts says which endpoints you want. apiweld.lock.json records exactly what was built. Commit both.

Updated View as Markdown

Apiweld keeps a project’s state in two files, both committed:

  • apiweld.config.ts says what you want: which APIs, which endpoints, and how to generate them. You (or your agent) edit it.
  • apiweld.lock.json records what was actually built: the exact spec, the endpoints, and the tool versions. Apiweld writes it. Don’t edit it by hand.

This works like package.json and a package-manager lockfile. The config states intent, and the lock makes every build reproducible.

Config

apiweld.config.tsts
import { defineConfig } from "apiweld";

export default defineConfig({
  output: "src/apis",
  generator: {
    name: "hey-api",
    client: "fetch",
    validators: "zod",
  },
  verify: {
    test: "bun run test",
  },
  apis: {
    stripe: {
      source: "https://raw.githubusercontent.com/stripe/openapi/master/latest/openapi.spec3.json",
      operations: [
        "POST /v1/refunds",
        "GET /v1/refunds/{refund}",
      ],
      policy: { autoRegenerate: "safe" },
    },
    github: {
      source: "apisguru:github.com",
      operations: ["GET /repos/{owner}/{repo}/pulls"],
    },
  },
});

The file is TypeScript, so your editor type-checks and autocompletes it, and it can hold functions such as patches. There’s no build step: Apiweld loads it directly.

After the first generate, Apiweld writes apiweld-env.d.ts, which gives you autocomplete for the operations of every API already in the lock.

Top-level options

Option Default Meaning
output "src/apis" Where generated clients go, relative to the config file. Each API gets its own folder, named after its key.
generator.name "hey-api" "hey-api" generates TypeScript with Hey API. "oapi-codegen" generates Go.
generator.client "fetch" The HTTP client for Hey API: fetch, axios, ky, ofetch, next, nuxt, or any other client Hey API supports.
generator.validators off "zod" generates Zod schemas and enables the runtime drift log.
generator.options Extra options passed through to the generator.
verify.test A command for apiweld verify to run after its type-check, such as "bun run test".

Per-API options

Each key under apis becomes a folder under output and the name you import from.

Option Meaning
source Where the spec comes from. See Sources.
operations The endpoints to generate, as METHOD /path. add and remove keep this list up to date.
policy.autoRegenerate "safe" lets apiweld update regenerate by itself when every change is safe. "never" always waits for you. Breaking changes are never applied automatically.
levelOverrides Re-labels specific change types for this API, for example { "response-optional-property-removed": "risky" }. Useful when a provider’s habits make one rule noisy.
allowRemoteHosts Other hosts the spec may load $refs from. By default, only the spec’s own host is allowed.
patch Functions that fix a broken spec before generation. See below.

Sources

Source Where the spec comes from
https://… That URL. GitHub blob links are fetched as the raw file.
file:<path> A spec on disk. Use this for private or internal APIs.
apisguru:<id> The APIs.guru directory entry. When the entry records the provider’s original URL (x-origin), Apiweld fetches from the provider directly, so you see changes as soon as they’re published.
wellknown:<domain> The API catalog the provider publishes at https://<domain>/.well-known/api-catalog (RFC 9727).

Fix a broken spec

Some upstream specs have mistakes that break generation. Add a patch to that API to fix them. The functions go to Hey API’s parser.patch.

github: {
  source: "apisguru:github.com",
  operations: ["GET /repos/{owner}/{repo}/pulls"],
  patch: {
    schemas: {
      "pull-request-simple": (schema) => {
        // fix the schema, then return it
        return schema;
      },
    },
  },
},

Patches are code you wrote in your own config. Apiweld never runs code that comes from a spec.

How add and remove edit the file

apiweld add and remove (and the matching MCP tools) edit apiweld.config.ts in place and keep your formatting, comments, and functions. If the config is built dynamically and can’t be edited safely, Apiweld prints the snippet to paste in instead of rewriting the file.

Lockfile

apiweld.lock.jsonjson
{
  "lockVersion": 1,
  "apis": {
    "stripe": {
      "resolvedUrl": "https://raw.githubusercontent.com/stripe/openapi/master/latest/openapi.spec3.json",
      "specHash": "sha256:9f2c…e41a",
      "specVersion": "2026-08-27",
      "fetchedAt": "2026-09-23T07:40:12Z",
      "etag": "W/\"5d1f…\"",
      "operations": ["GET /v1/refunds/{refund}", "POST /v1/refunds"],
      "sliceHash": "sha256:1b7a…03cd",
      "schemas": 14,
      "generator": "@hey-api/openapi-ts@<version>",
      "engine": "apiweld-engine@<version> (oasdiff <version>)",
      "outputHash": "sha256:c08e…77b2"
    }
  }
}

Keys and operations are sorted, so a change to the lock always means something actually changed, not just the ordering.

The lock has three hashes, and each one answers a different question:

Hash What it covers When it changes
specHash The whole upstream spec The provider changed anything. Apiweld then compares sliceHash to see whether it matters to you.
sliceHash Only your endpoints and the schemas they use Something you use changed. This is the only hash that triggers a drift report.
outputHash The generated files Someone edited the generated code by hand. Apiweld warns you, because the next generate will overwrite the edit.

The other fields: resolvedUrl is the URL that was actually fetched. etag lets the next check skip the download when nothing changed. generator and engine record the tool versions, so a rebuild produces the same output.

Files in your project

apiweld.config.ts
apiweld.lock.json
apiweld-env.d.ts          # operation autocomplete for the config
src/apis/
  stripe/                 # generated: read it, don't edit it
    sdk.gen.ts
    types.gen.ts
    zod.gen.ts
    index.ts
  github/
.apiweld/                 # gitignored
  reports/                # drift reports and heal plans, JSON and Markdown
  drift.log.jsonl         # runtime drift log (shapes only, never values)

Commit the generated clients. That way reviewers see every change, agents can read the code, and CI doesn’t need the network to build.

Machine settings

Apiweld also keeps a cache that all your projects share:

~/.apiweld/
  settings.json           # optional, see below
  catalog.db              # the search index
  specs/
    9f2c…e41a.json        # every spec version fetched, named by its hash
  http-cache.json         # ETags, so unchanged specs aren't downloaded again

Old spec versions stay in specs/, so Apiweld can diff against the version in your lock and rebuild it offline even after the provider has moved on.

settings.json is optional:

~/.apiweld/settings.jsonjson
{
  "offline": false,
  "proxy": "http://proxy.internal:3128",
  "catalogs": [
    { "name": "internal", "path": "/srv/specs" },
    { "name": "partners", "urls": ["https://partner.example.com/openapi.json"] }
  ]
}

catalogs adds your own specs to search, next to the public ones. Each result is labelled with the catalog it came from.

Navigation

Type to search…

↑↓ navigate↵ selectEsc close