JSPM

@jiffylabs/jiffy-cli

0.6.0
  • ESM via JSPM
  • ES Module Entrypoint
  • Export Map
  • Keywords
  • License
  • Repository URL
  • TypeScript Types
  • README
  • Created
  • Published
  • Downloads 18
  • Score
    100M100P100Q84152F
  • License Apache-2.0

Jiffy hardening-template CLI. Applies curated baseline bundles (SOC 2, enterprise, finance, managed desktop) to a repo or managed endpoint. Offline-capable on the stable channel.

Package Exports

  • @jiffylabs/jiffy-cli

Readme

@jiffylabs/jiffy-cli

Apply curated Jiffy hardening-template bundles to a repo or a managed endpoint.

Each bundle is a pre-reviewed, tier-bounded configuration for an AI developer tool (Claude Code, Cursor, Amazon Q, Claude Desktop, …). The CLI materializes the bundle's files into your cwd via the Jiffy Config Policy Translator adapters, so the output is deterministic and byte-stable across runs.

Bundles ship embedded in the CLI for offline use on the stable release channel — no network calls required.

Install / run

# Zero-install one-shot:
pnpm dlx @jiffylabs/jiffy-cli list
pnpm dlx @jiffylabs/jiffy-cli apply soc2-claude-code

# Or add to a project:
pnpm add -D @jiffylabs/jiffy-cli

Requires Node.js >= 18.17.

Commands

jiffy list

Print the available bundles. The stable channel (default) returns the embedded seed set.

jiffy list
# Available hardening-template bundles:
#
#   soc2-claude-code@1.0.0  (published, tier 1–2)
#     SOC 2 Baseline — Claude Code
#   cursor-enterprise-restricted@1.0.0  (published, tier 1–2)
#     Cursor — Enterprise Restricted
#   amazonq-finance-regulated@0.9.0  (pending, tier 2–3)
#     Amazon Q — Finance Regulated
#   claude-desktop-locked-down@0.1.0  (draft, tier 1–2) [MDM]
#     Claude Desktop — Locked Down

Add --json for machine-readable output.

jiffy apply <bundle-slug>

Materialize the bundle's files into the current working directory. Files that already exist are skipped unless you pass --force.

cd ~/my-repo
jiffy apply soc2-claude-code
# jiffy: applied soc2-claude-code@1.0.0 — 2 file(s), 1834 bytes
#   WRITE .claude/settings.json (1234 bytes)
#   WRITE .claude/CLAUDE.md (600 bytes)

Flags:

Flag Description
--force Overwrite files that already exist.
--dry-run Show what would change; write nothing.
--json Emit a single-line JSON summary (for CI).

MDM-only bundles (those where mdm_supported: true and no CPT adapter targets are declared) cannot be applied to cwd — use export-mdm instead.

jiffy export-mdm <bundle-slug>

Emit the bundle's Intune and Jamf MDM payloads as JSON. Only bundles flagged mdm_supported: true in their manifest are accepted.

jiffy export-mdm claude-desktop-locked-down --pretty
# { "intune": { ... }, "jamf": { ... } }

Flags:

Flag Description
--format intune | jamf | both Pick one payload or ship both (default both).
--pretty Pretty-print JSON (2-space indent).

jiffy export-agentgateway-bundle <bundle-slug>

Emit a complete agentgateway deployment YAML — Gateway + one or more HTTPRoutes + the Sprint 53 CEL Policy + the Jiffy guardrail Webhook — for bundles whose agentgateway_bundle manifest is set. Kept on the shared 0/1/2/3 exit-code map.

jiffy export-agentgateway-bundle soc2-claude-code
# ---
# apiVersion: gateway.networking.k8s.io/v1
# kind: Gateway
# metadata:
#   name: soc2-claude-code-gateway
# ...
# apiVersion: agentgateway.dev/v1alpha1
# kind: Policy
# ...
# apiVersion: agentgateway.dev/v1alpha1
# kind: Webhook
# spec:
#   url: https://trust.jiffylabs.app/v1/agentgateway/guardrail

The emitted YAML is byte-deterministic — running the command twice on the same bundle produces identical stdout. A snapshot test in packages/jiffy-cli/src/__tests__/export-agentgateway-bundle.test.ts guards this.

Flags:

Flag Description
--webhook-url=<url> Override the Jiffy guardrail webhook URL. Defaults to the bundle's own webhook_url_override when set, else https://trust.jiffylabs.app/v1/agentgateway/guardrail.
--pretty Indent emitted YAML (default 2-space indent is always applied).

Bundles without an agentgateway_bundle manifest (hypothetical legacy bundles) exit 1 with a clear bundle <slug> has no agentgateway variant message.

Related: docs/integrations/agentgateway.md — "Hardening bundle integration" section.

Bundle catalog (stable channel)

The embedded stable catalog ships four seed bundles:

Slug Bundle Tier Targets State
soc2-claude-code SOC 2 Baseline — Claude Code 1–2 claude-code published
cursor-enterprise-restricted Cursor — Enterprise Restricted 1–2 cursor published
amazonq-finance-regulated Amazon Q — Finance Regulated 2–3 amazon-q pending
claude-desktop-locked-down Claude Desktop — Locked Down 1–2 (MDM-only) draft

Tier bounds refer to the Jiffy attestation tier range within which the bundle is considered appropriate; they are advisory, not enforced at apply time. Deploying a bundle onto an artifact whose attested tier later drifts outside the bundle's declared range emits an advisory hardening_template.tier_drift audit event from the Jiffy platform — the bundle itself is not mutated.

Auto-scan via Claude Code (Sprint W.8)

Register a PostToolUse hook so Jiffy scans every artifact the moment Claude Code writes it:

# global (all Claude Code projects on this machine)
jiffy hook install

# or per-project (commit with your team)
jiffy hook install --project

Idempotent. Preserves existing hook entries. Backs up prior settings.json on first install. Opt out per-shell with JIFFY_AUTO_SCAN=off. Full details + fail-soft invariants in docs/auto-scan-setup.md.

Release channels

The CLI honors the JIFFY_CLI_RELEASE_CHANNEL environment variable:

Value Behavior
stable (default) Uses embedded seed bundles. Fully offline.
beta Reserved for a future remote-manifest lookup. Currently falls back to stable with a stderr notice.
JIFFY_CLI_RELEASE_CHANNEL=stable jiffy list

MDM export schemas

Both MDM payloads share the Jiffy MDM schema URI https://jiffylabs.app/schemas/hardening-template-mdm/v1.

Microsoft Intune — DeviceConfigurationProfile

Field Type Description
$schema string Schema URI. Identifies the payload as Jiffy-emitted.
displayName string Shown in the Intune Endpoint Manager portal; prefixed with Jiffy · .
description string Free-text description copied from the bundle's description field.
platforms 'macOS' | 'windows10' | 'ios' Target OS family. Today only macOS is emitted (Claude Desktop).
roleScopeTagIds string[] Intune role-scope tags. Defaults to ["0"] (no scope).
settings[] IntuneSetting[] Ordered list of settings — see below.

Each settings[] entry:

Field Type Description
name string Fully qualified preference key, e.g. com.anthropic.ClaudeDesktop.ClipboardHistoryEnabled.
value string | number | boolean Preference value.
type 'string' | 'integer' | 'boolean' Intune payload type hint.
description string? Optional human-readable rationale, surfaced to Intune admins.

Jamf — ConfigurationProfile

Field Type Description
$schema string Same Jiffy MDM schema URI.
general.name string Display name; prefixed with Jiffy · .
general.description string Free-text description.
general.category string Always Security & Compliance.
general.distribution_method 'install_automatically' | 'make_available_in_self_service' Deployment mode. Current bundles emit install_automatically.
scripts[] JamfScript[] Optional post/pre-install scripts for approvals that plain settings can't express.
settings[] JamfSetting[] Machine- or user-scope custom preferences.

Each scripts[] entry:

Field Type Description
name string Script filename registered in Jamf.
script_contents string Full bash contents. Non-zero exit aborts the install.
priority 'before' | 'after' Run before or after the profile settings are applied.

Each settings[] entry:

Field Type Description
key string Preference key (unprefixed; Jamf scopes via scope).
value string | number | boolean Preference value.
scope 'user' | 'machine' User-level or device-level preference.

Example (claude-desktop-locked-down)

{
  "intune": {
    "$schema": "https://jiffylabs.app/schemas/hardening-template-mdm/v1",
    "displayName": "Jiffy · Claude Desktop — Locked Down",
    "platforms": "macOS",
    "roleScopeTagIds": ["0"],
    "settings": [
      { "name": "com.anthropic.ClaudeDesktop.UpdateChannel",
        "value": "enterprise", "type": "string" },
      { "name": "com.anthropic.ClaudeDesktop.ClipboardHistoryEnabled",
        "value": false, "type": "boolean" },
      { "name": "com.anthropic.ClaudeDesktop.RequireApprovalForShellExec",
        "value": true, "type": "boolean" }
    ]
  },
  "jamf": {
    "$schema": "https://jiffylabs.app/schemas/hardening-template-mdm/v1",
    "general": {
      "name": "Jiffy · Claude Desktop — Locked Down",
      "category": "Security & Compliance",
      "distribution_method": "install_automatically"
    },
    "scripts": [ { "name": "jiffy-install-shell-exec-gate.sh", "priority": "after", "script_contents": "..." } ],
    "settings": [
      { "key": "ClipboardHistoryEnabled", "value": false, "scope": "user" },
      { "key": "UpdateChannel", "value": "enterprise", "scope": "machine" }
    ]
  }
}

Exit codes

Code Meaning
0 Command succeeded.
1 Generic failure (e.g. applying an MDM-only bundle to cwd).
2 Unknown bundle slug.
3 Malformed CLI input (missing command, unknown flag, bad --format value).

Programmatic use

The package also exports its primitives so you can apply bundles from a Node script without spawning the CLI:

import {
  findBundle,
  emitBundleFiles,
  applyCommand,
  SEED_BUNDLES,
} from '@jiffylabs/jiffy-cli';

const bundle = findBundle('soc2-claude-code');
if (!bundle) throw new Error('bundle not found');

const files = emitBundleFiles(bundle);
for (const f of files) {
  console.log(`${f.path} (${f.bytes} bytes)`);
}

License

Apache-2.0. Copyright Jiffy Labs.