Skip to main content

metaphi

The Metaphi AI command line. Sign in and twin agent traces.

Install

brew install metaphi-labs/tap/metaphi    # macOS and Linux

No Homebrew? Download the binary for your platform from the latest release, unpack it and put metaphi on your PATH. Each release lists its checksums.txt.

Calling it from Python instead: pip install metaphi-ai gives you the same command and the library (see below).

Quickstart (2 minutes)

metaphi login                  # opens the browser; confirm the code you see in the terminal
metaphi twin trace.json        # writes trace.twin.json

metaphi login signs you in as yourself and hands this machine your organization's keys: a live key (mai_sk_...) and a test key (mai_sk_test_...). They are kept in the OS keychain when there is one (macOS Keychain, Windows Credential Locker, Secret Service on Linux), otherwise in the config file, and are never printed. Logging in again replaces them; metaphi logout revokes them. If your organization has no twinning access yet, the sign-in still works and says why no key was saved.

metaphi twin trace.json --test runs on the test key. Test runs go through the same pipeline but cost nothing; files can be at most 256 KiB and an organization gets 20 runs a day. Test twins and live twins never see each other.

Keys, members and billing are managed in the console at https://app.metaphi.ai/keys, not from the CLI.

Use it from your servers

A server or CI job has no browser: make it a key of its own in the console and hand it over as a secret.

export METAPHI_API_KEY=mai_sk_...
metaphi twin trace.json -o out.json --json

METAPHI_API_KEY overrides whatever is saved. A key you already have can also be saved with metaphi login --with-api-key, which reads it from stdin (or prompts without echo), so it never lands in your shell history or the process list.

One trace file in, one twinned file out, in the same format. --json prints {"output"} on stdout, with progress on stderr. Or from Python:

from pathlib import Path
from metaphi.twin import twin

result = twin(Path("trace.json"), Path("out.json"), api_key="mai_sk_...")
result["output"]   # where the twinned trace was written

One key per environment (prod, staging) or per customer is a good default. Revoking one stops only that key.

Twin options

Flag What it does
-o, --output Where the twinned trace goes. Default: <name>.twin<ext>.
--key <64 hex> Keys the stand-in values. The same key gives a person the same stand-in in every trace, so a corpus stays consistent. Default: a fresh key per trace.
--confidential <org> Replaces an organization even though it is public, e.g. your customer. Repeatable.
--test Runs on the test key metaphi login saved: free, small, apart from live twins.

The organization key comes from METAPHI_API_KEY, then the saved key. (--api-key still works but is deprecated: an argument is visible in shell history and to other processes.)

People, private organizations, accounts and secrets are always replaced, each with one consistent synthetic value of the same kind, and the trace keeps its structure. An adversarial pass then reads the output for anything still real.

Errors

Every error from the service carries a stable code. Switch on the code or the exception class, never on the message. On a failure the CLI exits 1 and prints:

error: This organization's prepaid balance is used up; add credits to continue. Nothing was started. (code: out_of_credit, request: req_5f1c...)

With --json, stdout also gets the error object: {"error": {"type", "code", "message", "retryable", "request_id"}}, plus run_id when a run failed and action_url when a page fixes it. Quote the request_id to support.

From Python, each error type raises its own class from metaphi.errors. All of them subclass MetaphiError:

from pathlib import Path
from metaphi.errors import BillingError, MetaphiError, RateLimitError
from metaphi.twin import twin

try:
    twin(Path("trace.json"))
except BillingError:            # out_of_credit
    ...                         # add credit: `metaphi credits buy`
except RateLimitError as e:     # rate_limited_concurrent, rate_limited_daily
    ...                         # e.retryable is True: try again when a run ends
except MetaphiError as e:
    print(e.code, e.request_id, e.retryable)
Class type Codes, for example
BillingError billing_error out_of_credit
AuthError auth_error no_organization
RateLimitError rate_limit_error rate_limited_concurrent, rate_limited_daily
InvalidRequestError invalid_request_error invalid_key, upload_already_run, task_not_found
RunError run_error twin_unclean, not_text, too_large, session_failed, budget_exceeded
IdempotencyError idempotency_error idempotency_key_reused, idempotency_key_in_use
APIError api_error unavailable, balance_unavailable, run_unavailable

retryable says whether making the same call again later may succeed. For a failed run, it means uploading the same trace again. An error the CLI says itself, such as a missing key, is a plain MetaphiError with code set to None.

Your organization

metaphi whoami shows who you are signed in as and the keys saved on this machine. People, roles and keys are managed in the console at https://app.metaphi.ai/keys.

Credits

Each completed trace draws your organization's prepaid credit; a run that fails costs nothing. When the balance reaches zero, new runs are refused until credit is added.

metaphi credits                       # the balance (owners, admins and billing members)
metaphi credits buy --amount 200      # pay through Stripe Checkout in the browser; waits until it lands

Only owners and billing members can buy; a billing member sees the balance and buys credit, nothing else.

Running out of credit

When metaphi twin is refused with out_of_credit at a terminal, and you may buy for your organization, it offers to add credit there and then, opens Stripe Checkout, and carries on with the same run once the payment lands:

$ metaphi twin trace.json
acme is out of prepaid credit.
Add credit now? Amount in $ [100]:
Pay in the browser:
  https://checkout.stripe.com/c/pay/...
Paid. acme: $100.00 prepaid credit
uploaded trace.json (48,112 bytes)

Enter takes $100; n or Ctrl-C declines. The run is retried once, under the Idempotency-Key of the first attempt, so it can never start twice. If you may not buy, it names who can and where.

In CI, a pipe or with --json nothing is asked. The command exits 1 with the error and one more line on stderr:

Add credit: https://app.metaphi.ai/console?add=credit  or run: metaphi credits buy --amount <amount>

The library never prompts: twin() raises BillingError, whose action_url is the add-credit page when the service sent one.

Configuration

Variable Default
METAPHI_API_KEY the key saved by metaphi login (or metaphi login --with-api-key)
METAPHI_API https://api.metaphi.ai/v1/kennet, the Kennet API
METAPHI_HOME ~/.config/metaphi (directory mode 700, config file mode 600)
METAPHI_TWIN_TIMEOUT 7200: seconds metaphi twin waits for its twin to end (--timeout per call)
METAPHI_NO_KEYRING unset: secrets go to the OS keychain when one is available; 1 keeps them in the config file
METAPHI_ALLOW_CUSTOM_HOST unset: the CLI talks only to https://*.metaphi.ai; 1 allows another https host

Sign out with metaphi logout. It ends this sign-in everywhere it is used, revokes the keys metaphi login handed out, and clears the saved keys from this machine.

Metadata

Release files for metaphi-ai 0.1.5

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for metaphi-ai 0.1.5
File Size Uploaded
metaphi_ai-0.1.5.tar.gz 19.7 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for metaphi-ai 0.1.5
File Interpreter ABI Platform
metaphi_ai-0.1.5-py3-none-any.whl Python 3 none any Details

Total release size: 43.3 kB

Release files / metaphi_ai-0.1.5.tar.gz

Download URL metaphi_ai-0.1.5.tar.gz
Size 19.7 kB
Tags Source
SHA-256 checksum
How to use checksums
1f12a02d16833738177326b4c27a534c6e8d537c9c0c43b2aa7f9460449d1846
BLAKE2b-256 checksum
How to use checksums
4f84f2a3587da310266fbd631084c5636db5b83ed9bd0d1dd40567670ec371d8
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.

Transparency log

Release files / metaphi_ai-0.1.5-py3-none-any.whl

Download URL metaphi_ai-0.1.5-py3-none-any.whl
Size 23.6 kB
Tags Python 3
SHA-256 checksum
How to use checksums
1aa1a3c4e62df42c48778da6cea3b093015b359d1a491a7a7aca4984cb8cc962
BLAKE2b-256 checksum
How to use checksums
d44834b18acb41d51cecabfee8e594b30762d86e84044391bbe596a8f7b2c237
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.

Transparency log

Release history Release notifications | RSS feed

0.1.8

2 release files

0.1.7

2 release files

0.1.6

2 release files

This release

0.1.5 This release

2 release files

0.1.4

2 release files

0.1.3

2 release files

0.1.2

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page