minmaxkey

CLI

CLI

Two CLIs, two sides of the product:

  • mmk-admin (Python, server-side) — administration and automation: create products, issue/reset/revoke licenses, configure webhooks. This page.
  • mmk (Go, client-side, single binary) — for your users' machines: fingerprint, activate, verify offline tokens, offline-first checks. See SDKs.

Setup (mmk-admin)

# from the repo:
alias mmk-admin="python scripts/mmk-admin.py"

export MMK_URL=http://localhost:8080
export MMK_ADMIN_TOKEN=<your MMK_ADMIN_TOKEN>

(The token lives in your .env/deployment secrets — never in client apps. Whatever process runs mmk-admin (your webhook handler, a cron) needs MMK_URL and MMK_ADMIN_TOKEN set.)

Commands

Products

mmk-admin products create "PixelForge Pro" pixelforge-pro
# {"id": 1, "name": "PixelForge Pro", ..., "api_key": "...", "public_key": "..."}
mmk-admin products list
# #1  PixelForge Pro         /pixelforge-pro

Policies

mmk-admin policies create 1 pro-monthly subscription --max-seats 1 --days 30
mmk-admin policies list 1
# #1  pro-monthly        subscription  seats=1  30d

Licenses

mmk-admin licenses issue 1 1 --email [email protected]
# 9TMC-5TS9-0MKQ-VS8A-87Q0   (license #1)

mmk-admin licenses list 1
# #1  9TMC-5TS9-0MKQ-VS8A-87Q0  active  seats=0/1  [email protected]

mmk-admin licenses revoke 1
# license #1 revoked

Webhooks

mmk-admin webhook set 1 https://your-server.dev/hook
# {"url": "...", "secret": "..."}
# secret (keep server-side; used to verify webhook signatures): ...

Offline verification

Client-side: the Go mmk binary (SDKs) or python scripts/mmk-admin.py verify:

mmk verify --pubkey product.pub.pem --token "<token>" --fingerprint 9f86d081884c7d659a2feaa0c55ad015
# VALID

Recipes

Issue a license when someone pays (Stripe)

# in your Stripe webhook handler:
if event["type"] == "checkout.session.completed":
    subprocess.run([
        "mmk-admin", "licenses", "issue", "1", "1",
        "--email", event["data"]["object"]["customer_email"],
    ])

Revoke on refund (Lemon Squeezy / Gumroad / Stripe)

if event["type"] in ("order.refunded", "charge.refunded"):
    subprocess.run(["mmk-admin", "licenses", "revoke", str(license_id)])

Audit a product before shipping a release

mmk-admin licenses list 1 | grep -c revoked

Anything the CLI doesn't cover, the raw API does — see the API reference. The CLI is a thin wrapper; the server is the source of truth.