Home · Commands · Automation & CI/CD · Troubleshooting
trustpin-cli
├── configure Configure API credentials
├── user
│ └── info Show current user and organizations
├── projects
│ ├── list List projects
│ ├── get Show project details
│ ├── config Get configuration as JWS payload (JSON)
│ ├── upsert Add or update a certificate pin
│ ├── cleanup Remove expired certificate pins
│ ├── sign Sign and publish configuration as JWS
│ ├── refresh-certs Fetches updated certificate pins for a domain
│ └── jws Fetch the published JWS from the CDN
└── domains
└── certificates Look up certificates and pins for a domain
Available on every command:
| Flag | Description |
|---|---|
--verbose |
Verbose output: config file location, API URLs, HTTP status codes |
--debug |
Debug output |
--log-http |
Log HTTP requests and responses |
--version |
Print the CLI version |
Most commands also accept --output json for machine-readable output (see Automation & CI/CD).
Configure the CLI with your TrustPin API credentials. Runs interactively when flags are omitted.
trustpin-cli configure [--api-base-url <url>] [--api-token <token>]
$ trustpin-cli configure
API Base URL (https://api.trustpin.cloud): https://api.trustpin.cloud
API Token: tp_your_token_here
Configuration saved successfully!
Credentials are stored in ~/.trustpin/cli/config.properties. You can also configure the CLI entirely through environment variables — see Automation & CI/CD.
Show the authenticated user and their organizations. Useful as a quick credentials check, and for finding your organization ID.
trustpin-cli user info [--output json]
$ trustpin-cli user info
═══ User Information ═══
ID: 6f0c1a2b-3d4e-5f60-7182-93a4b5c6d7e8
Name: Jane Developer
Email: jane@example.com
── Organizations ──
• Example Org (0a1b2c3d-4e5f-6071-8293-a4b5c6d7e8f9)
List all projects you have access to, with their IDs, type, domain count, and publish status.
trustpin-cli projects list [--output json]
# Extract project names for scripting
trustpin-cli projects list --output json | jq -r '.data.projects[].name'
Show detailed information about one project: configuration and published versions, public key, and per-domain pin counts. Warns when the latest configuration version has not been published yet.
trustpin-cli projects get <organization-id> <project-id> [--output json]
$ trustpin-cli projects get 0a1b2c3d-4e5f-6071-8293-a4b5c6d7e8f9 9f8e7d6c-5b4a-3928-1706-f5e4d3c2b1a0
═══ Project Details ═══
Name: Example Mobile App
Type: Managed CDN with Cloud Keys
Configuration Version: 3
Published Version: 2
⚠️ Warning: Latest configuration (v3) is not yet published (v2)
Domains: 2
• Domain: example.com (1 pin)
• Domain: api.example.com (1 pin)
Print the project’s current (stored, not necessarily published) configuration in JWS payload format. Output is always JSON.
trustpin-cli projects config <organization-id> <project-id>
Add a certificate pin to a domain in a project, or update an existing pin’s expiration. If the domain does not exist in the project yet, it is added.
trustpin-cli projects upsert <organization-id> <project-id> \
--domain <fqdn> \
--pin <type>:<value> \
[--expires <ISO8601-datetime>] \
[--dry-run] \
[--output json]
| Flag | Description |
|---|---|
--domain |
Domain name (FQDN) — required |
--pin |
Pin as <type>:<value> — required |
--expires |
Pin expiration (ISO 8601, e.g. 2026-04-13T08:37:02Z) |
--dry-run |
Show the request that would be sent without submitting it |
Pin types
| Type | Meaning |
|---|---|
spki-sha256 |
SPKI SHA-256 fingerprint (recommended) |
spki-sha512 |
SPKI SHA-512 fingerprint |
sha256 |
Certificate SHA-256 fingerprint |
sha512 |
Certificate SHA-512 fingerprint |
SPKI pins are recommended because they pin the public key rather than a specific certificate, so they survive certificate renewals that reuse the same key pair.
$ trustpin-cli projects upsert $ORG_ID $PROJECT_ID \
--domain api.example.com \
--pin spki-sha256:oxVSdCLgthL3M5Vnnzepq8WWlkUfRPYkpjLpm+wn+1o= \
--expires 2026-04-13T08:37:02Z
✓ Domain: api.example.com
• Added pin: spki-sha256:oxVSdCLgth... (expires 2026-04-13T08:37:02Z)
✓ Project updated successfully
Configuration version: 5 → 6
⚠️ Remember to sign and publish: trustpin-cli projects sign ...
Note:
upsertupdates the stored configuration only. Changes are not live until you runprojects sign.
Combine with domains certificates to pin a discovered certificate in one step:
SPKI=$(trustpin-cli domains certificates api.example.com --output json | \
jq -r '.data.certificates[0].spkiSha256')
trustpin-cli projects upsert $ORG_ID $PROJECT_ID \
--domain api.example.com \
--pin spki-sha256:$SPKI \
--expires 2026-04-13T08:37:02Z
Remove already-expired certificate pins from every domain in a project.
trustpin-cli projects cleanup <organization-id> <project-id> [--dry-run] [--output json]
--dry-run to see how many pins would be removed without changing anything, and add --verbose for a per-domain breakdown.$ trustpin-cli projects cleanup $ORG_ID $PROJECT_ID --dry-run
Dry run: 2 expired pin(s) would be removed (no changes made)
Run without --dry-run to remove them: trustpin-cli projects cleanup ...
$ trustpin-cli projects cleanup $ORG_ID $PROJECT_ID
Removed 2 expired pin(s)
⚠️ Remember to sign and publish: trustpin-cli projects sign ...
Note: like
upsert,cleanupupdates the stored configuration only — runprojects signafterwards to publish.
Refresh the certificate pins for one domain from the certificates TrustPin can currently see.
trustpin-cli projects refresh-certs <organization-id> <project-id> \
--domain <fqdn> [--remove-expired] [--dry-run] [--output json]
| Flag | Description |
|---|---|
--domain |
Domain name (FQDN) to refresh — required |
--remove-expired |
Also drop pins for this domain whose expiry is in the past |
--dry-run |
Show the PATCH request without submitting it |
Where upsert requires you to supply a pin by hand, refresh-certs looks the certificates up for you: the live certificate presented in a TLS handshake, plus every unexpired issuance found in the public Certificate Transparency logs. If the domain is not yet in the project, it is added.
upsert using a different digest type. A pin the lookup did not return is left alone.$ trustpin-cli projects refresh-certs $ORG_ID $PROJECT_ID --domain api.example.com
Domain: api.example.com
7 certificate(s) returned by TrustPin
+ Added spki-sha256:heXXXV6YUWtMPE... (expires 2027-01-14T00:00:00Z)
~ Updated spki-sha256:Ab12Cd34Ef56Gh... (expiry 2026-07-01T00:00:00Z -> 2027-03-02T00:00:00Z)
= 4 pin(s) already up to date
Project updated successfully
Configuration version: 12 -> 13
Remember to sign and publish: trustpin-cli projects sign ...
Note:
--remove-expiredis scoped to the domain you name. To sweep expired pins across every domain in the project, useprojects cleanupinstead.
Note: like
upsertandcleanup,refresh-certsupdates the stored configuration only — runprojects signafterwards to publish.
Sign the project’s current configuration as a JWS and publish it to the TrustPin CDN. This is what makes staged changes live for your apps.
trustpin-cli projects sign <organization-id> <project-id> \
[--private-key <path>] [--password <password>] [--output json]
| Flag | Description |
|---|---|
-k, --private-key |
Path to a PEM private key file — required for BYOK projects |
-p, --password |
Master password for private key decryption (prompted interactively if omitted) |
--dry-run |
Sign and verify locally without publishing — nothing is uploaded |
--dry-run--dry-run performs every step of a real run — loads the configuration, reads and decrypts the private key, checks it against the project’s public key, signs the payload and verifies the resulting signature — and then stops before the upload. Nothing about the project changes.
That makes it the way to confirm a key file and master password are correct, and that they belong to this project, before committing to a publish. A mismatched key still fails with INVALID_KEY_PAIR; a wrong password still fails with INCORRECT_PASSWORD.
$ trustpin-cli projects sign $ORG_ID $PROJECT_ID --private-key key.pem --dry-run
[1/4] Getting project information
[2/4] Loading project configuration
[3/4] Preparing private key
Key pair validation successful
[4/4] Creating and signing JWT
JWS signature verified successfully
Dry run: signature verified locally, nothing was uploaded
Dry run successful - nothing was published
═══ Dry Run Summary ═══
Project: my-app
Signature Valid: Yes
Key Source: BYOK
Published: No (dry run)
Domains: 2
A dry run reports four steps rather than five, because the upload step does not happen.
Both --dry-run and --verbose print the signed token, so you can inspect or verify it yourself:
═══ Signed JWS ═══
Header: eyJhbGciOiJFUzI1NiIsImtpZCI6...
Payload: eyJkb21haW5zIjpbeyJkb21haW4i (354 chars)
Signature: uwgnUpsq42OXoTnS2ZfY9fmeDI0y...
Length: 533 chars
eyJhbGciOiJFUzI1NiIs....eyJkb21haW5zIjpb....uwgnUpsq42OXoTnS2Zf
The full compact serialization is printed on its own line so it can be copied or piped into a verifier. In --output json the same value appears as data.jws. It is only included when asked for, because it is long — it is not a secret, since the identical token is served from the public CDN once published.
Cloud-managed keys — for projects of type Managed CDN with Cloud Keys, no key file is needed; you’ll be prompted for your master password:
$ trustpin-cli projects sign $ORG_ID $PROJECT_ID
Master password: ****
[1/5] Getting project information
[2/5] Loading project configuration
[3/5] Preparing private key
[4/5] Creating and signing JWT
[5/5] Uploading signed configuration
Configuration published successfully!
Bring Your Own Key (BYOK) — for BYOK projects, supply your private key:
trustpin-cli projects sign $ORG_ID $PROJECT_ID --private-key ./my-private-key.pem
Fetch the currently published JWS configuration from the CDN — the exact payload your mobile apps are fetching.
trustpin-cli projects jws <organization-id> <project-id> \
[--verify] [--decode] [--output-file <path>]
| Flag | Description |
|---|---|
--verify |
Verify the JWS signature using the public key from the CDN |
--decode |
Decode and display the JWS header and payload |
--output-file |
Save the raw JWS to a file |
$ trustpin-cli projects jws $ORG_ID $PROJECT_ID --decode
JWS Header:
Algorithm: ES256
Type: JWT
Payload:
Spec: v1.0.0
Version: 3
Issued At: 2026-06-11T13:24:44Z
Domains: 1
- api.example.com (2 pins)
Current DB Version: 3
Published Version: 3
Published version is up to date
Use cases:
projects sign actually published--output-file) or compliance archivesLook up all known SSL/TLS certificates for a domain: the live certificate plus any discovered via Certificate Transparency logs. Every certificate is reported with all four pin formats, its validity window, subject alternative names, key and signature details, CAA issuer, and CT log information — ready to use with projects upsert, or applied automatically by projects refresh-certs.
trustpin-cli domains certificates <domain-name> [--output json]
Each entry is labelled with where it was observed — (live) for the certificate the server actually presents in a TLS handshake, (Certificate Transparency) for one found in the public logs — and a summary line counts each.
$ trustpin-cli domains certificates api.example.com
═══ Certificates for api.example.com ═══
Total certificates: 2
Sources: 1 live, 1 from Certificate Transparency
── Certificate 1 (live) ──
Common Name: api.example.com
Issuer: CN=R11,O=Let's Encrypt,C=US
Subject Alt Names: api.example.com, www.example.com
Valid From: 2026-03-01T00:00:00Z
Expires At: 2026-12-31T23:59:59Z
Public Key: EC 256 bits
Signature Algorithm: SHA256-RSA
SHA-256: heXXXV6YUWtMPE/dUyZ6ESBpkOibPSeHseRAnp4dQJg=
SPKI SHA-256: oxVSdCLgthL3M5Vnnzepq8WWlkUfRPYkpjLpm+wn+1o=
CAA Issuer: letsencrypt.org
CT SCT Logs: 2
── Certificate 2 (Certificate Transparency) ──
Common Name: api.example.com
Issuer: CN=R10,O=Let's Encrypt,C=US
Expires At: 2027-01-31T23:59:59Z
SHA-256: (not available for this record)
SHA-512: (not available for this record)
SPKI SHA-256: fFq2hLnpGYtMuP8wR3vKdN7xZaQcEj5TbVm1oXsY9Uk=
Two things worth knowing when reading the output:
(not available for this record) is expected, not an error. A CT log entry that holds only the precertificate has no usable certificate digest — a precertificate’s hash never matches what a server sends, so the API withholds it rather than offering an unpinnable value. The SPKI digest is shared between a certificate and its precertificate, which is why it is always present and why it is the pin TrustPin recommends.Valid From may be flagged (not yet valid). A certificate issued ahead of its deployment can be pinned before the server starts serving it, so it is shown rather than hidden.--output json returns every field of the API response verbatim, including source, subjectAlternativeNames, notBefore, keyAlgorithm, keySize and signatureAlgorithm.