NHI Management

Machine Tokens

Machine tokens (secr_mt_) are purpose-built credentials for CI/CD pipelines, services, and automation. Unlike personal CLI tokens, machine tokens have lifecycle management, ownership tracking, environment hints, and optional conditional access rules.

Token Format

Machine tokens follow the format secr_mt_{env}_{hex}, where the environment hint (e.g. prod, ci) is embedded in the prefix for easy identification in logs and audits.

Example token
secr_mt_prod_a1b2c3d4e5f6...

Tokens are hashed with SHA-256 before storage. The plaintext is shown only once at creation time.

Creating Tokens

CLI
# Create a token for production CI
secr token create --name "GitHub Actions prod" --env prod --expires 90d

# Create a non-expiring token (not recommended)
secr token create --name "Legacy deploy" --env ci
API
POST /v1/machine-tokens/:orgId
{
  "name": "GitHub Actions prod",
  "environmentHint": "prod",
  "expiresInDays": 90,
  "projectId": "uuid"        // optional: scope to project
}

The response includes the plaintext token. Store it securely — it cannot be retrieved again.

Lifecycle States

Machine tokens have four lifecycle states:

StateCan AuthenticateDescription
activeYesNormal operating state
disabledNoTemporarily suspended — can be re-enabled
expiredNoPast its expiry date — must be rolled to a new token
revokedNoPermanently deactivated — cannot be restored
CLI
secr token disable <tokenId>    # Temporarily suspend
secr token enable <tokenId>     # Re-enable
secr token revoke <tokenId>     # Permanently revoke

Rolling Tokens

Rolling generates a new token value while preserving the token's metadata, name, and access rules. The old token is immediately revoked.

CLI
secr token roll <tokenId>

# Output:
# ✓ Token rolled successfully
# New token: secr_mt_prod_f7e8d9c0b1a2...
# ⚠ Old token is now revoked. Update your CI/CD secrets.

Ownership

Every machine token is assigned an owner (the creating user by default). When a team member is removed from the org, their tokens are flagged and can be transferred or revoked.

CLI
# List tokens with ownership info
secr token list

# Transfer ownership
secr token transfer <tokenId> --to user@example.com

Conditional Access

Add zero-trust rules to machine tokens: IP allowlists, time windows, and user-agent matching. Requests that don't match are rejected with a 403.

API — Create with conditions
POST /v1/machine-tokens/:orgId
{
  "name": "GitHub Actions",
  "environmentHint": "ci",
  "conditions": {
    "ipAllowlist": ["140.82.112.0/20"],
    "timeWindows": [{
      "days": ["mon","tue","wed","thu","fri"],
      "startUtc": "06:00",
      "endUtc": "22:00"
    }],
    "userAgentPattern": "github-actions/*"
  }
}
ConditionDescription
ipAllowlistArray of CIDR ranges — request IP must match at least one
timeWindowsDay-of-week + UTC hour ranges — requests outside windows are rejected
userAgentPatternGlob pattern matched against the User-Agent header

CI/CD Usage

Use machine tokens in your CI/CD pipeline by setting the SECR_TOKEN environment variable:

GitHub Actions
- name: Pull secrets
  env:
    SECR_TOKEN: ${{ secrets.SECR_TOKEN }}
  run: npx @secr/cli pull --env production
GitLab CI
pull-secrets:
  script:
    - npx @secr/cli pull --env production
  variables:
    SECR_TOKEN: $SECR_TOKEN

API Endpoints

MethodPathDescription
POST/v1/machine-tokens/:orgIdCreate token
GET/v1/machine-tokens/:orgIdList tokens
GET/v1/machine-tokens/:orgId/:tokenIdGet token details
PATCH/v1/machine-tokens/:orgId/:tokenIdUpdate token
DELETE/v1/machine-tokens/:orgId/:tokenIdRevoke token
POST/v1/machine-tokens/:orgId/:tokenId/rollRoll token
POST/v1/machine-tokens/:orgId/:tokenId/disableDisable token
POST/v1/machine-tokens/:orgId/:tokenId/enableEnable token
POST/v1/machine-tokens/:orgId/:tokenId/transferTransfer ownership

Secure your CI/CD pipeline

Replace long-lived secrets with managed machine tokens.