Skip to main content
A provider package is an emulator published to npm that the CLI runs the way it runs the built-in providers: in its own process, on its own port, with seed config, saved state, snapshots, faults, and the control API. Anyone can publish one. Users name it in their config with provider:, and the CLI asks them to trust it before it runs. Choose a provider package when an emulator should be shared across projects and versioned on its own. For an emulator that lives in one project, a custom emulator is simpler.

Run a provider package

baseline.config.json
  • provider: is npm:<package>@<range>. The range takes the same forms as version: on a built-in service, and defaults to *.
  • port: is required, because a provider package has no port slot. It must not be another service’s port or the console port.
  • The service name (billing) is yours to choose, but it cannot be a built-in service’s name. seed, baseUrl, and faults work as they do for built-in services.
  • @deploybaseline/* packages are the built-in providers: use emulator: stripe with version: for those.
The package is found the way built-in providers are (Provider versions): from the project’s node_modules, then the version baseline.lock pins, then the provider cache, then a pull from the npm registry your .npmrc names.

Trust

A provider package runs with your permissions: it can read and write your files, reach the network, and start processes. Its own process keeps it from crashing other services, but it is not a sandbox. So it runs only once you have trusted that exact version:
  1. The first start that resolves it prints the package, version, source, integrity, and where it was built, and asks:
  2. Answering yes pins it in baseline.lock before it runs:
  3. Commit the lockfile. Without a terminal, or with CI set, start asks nobody: it refuses a provider package that the lockfile does not trust, and names the command that grants it.
npx @deploybaseline/cli trust [services...] grants trust without a prompt, for every provider: service or the ones named, and prints the same details. Trust covers one version and tarball. A new version, from update or a changed range, is asked about again, and a tarball that does not match the lockfile’s integrity is refused. Built from comes from the version’s npm provenance attestation, and only when it is for that exact tarball. npm checks the attestation’s signature when the version is published; the CLI shows what it says. A version published without provenance shows Provenance: none.

Write a provider package

Start from the template in the repository, examples/provider-template: a notes API with seed config, saved state, and a test that drives the built entry over the provider protocol.

The baseline field

Rules

  • Self-contained entry. The CLI unpacks the tarball and runs entry with nothing installed next to it, and runs no install scripts. Bundle every runtime dependency, @deploybaseline/core included, into dist/ (the template’s tsup.config.ts does, and copies core’s fonts next to the bundle).
  • One port. Listen only on the port the CLI gives you; runProvider does this.
  • State in the store. Everything in the store is saved, restored, and snapshotted by the CLI. Keep stateVersion honest, and migrate or refuse older state.
  • Files. Write only to the system temp directory and to paths your seed config names.
  • Names. baseline-provider-<name> or @scope/baseline-<name>, with the baseline-provider keyword so people can find it. The @deploybaseline scope is for built-in providers.
  • Provenance. Publish from CI with npm publish --provenance, so users see the repository and commit before they trust it.

What you can rely on

  • The protocol version you build against keeps working for at least a year of CLI releases.
  • SDK upgrades are yours to take: your package bundles the core it was built with.
  • The CLI passes your service its seed, tokens, faults, base URL, and saved state, and handles persistence, secrets output, the console, and the control routes.

Test it

The template’s test forks dist/provider.js with spawnProvider from @deploybaseline/core, the same client the CLI uses, and checks the handshake, seed config, HTTP, and a save and restore. To try the package in a project before publishing, install it as a dev dependency: a provider: service resolves from node_modules first, and still asks for trust.