# Packagist {#packagist}

Takumi Guard speaks the [Composer repository protocol](https://getcomposer.org/doc/05-repositories.md#composer), so you can route `composer install` and `composer update` through it the same way you'd point at a [Private Packagist](https://packagist.com/) or Toran Proxy mirror. This page covers setup for local development and CI.

:::info Requires Composer 2.10 or newer
Blocking from an existing `composer.lock` relies on Composer's dependency-policy feature, added in **Composer 2.10** (May 2026). On older Composer versions, blocking applies during `composer update` / `composer require` but **not** during `composer install` from a pre-existing lock file — upgrade Composer, or re-resolve the lock once (see below).
:::

## Setup {#setup}

Takumi Guard offers three ways to get started for Composer:

- **[Anonymous](#setup-anonymous)** — No token required. Configure the repository to enable package blocking.
- **[Email-Verified](#setup-email-verified)** — Use an email-verified token (`tg_anon_…`) for download tracking and breach notifications.
- **[Org User Token](#setup-org-user-token)** — Use an org user token (`tg_org_…`) to track installations across your organization.

:::info Paid Feature
Org user tokens require an active base subscription with Guard enabled. See [Pricing & Billing](/docs/t/guard/billing/index.md) for details.
:::

### Anonymous Usage {#setup-anonymous}

You can use Takumi Guard's package blocking without authentication. Add the proxy as a Composer repository and disable the default Packagist.org so every package resolves through Guard:

```bash
# Add the Guard proxy as a Composer repository (global config).
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech

# Disable the default packagist.org so packages are not loaded twice and
# cannot silently bypass the blocklist.
composer config --global repositories.packagist.org false
```

Composer v2 mirrors packages it would otherwise fetch from packagist.org through Guard. Disabling packagist.org makes the routing explicit and prevents a direct fallback that would skip the blocklist. See [details](#why-disable-packagist).

That's the whole setup — package blocking now applies to `composer install` and `composer update`, **including installs from an existing `composer.lock`** (Composer 2.10+).

**Optional: enable download tracking**

```bash
composer update mirrors
```

`composer update mirrors` is identical to `composer update --lock`: it rewrites the dist URLs in `composer.lock` to route artifact downloads through Guard **without changing any package versions**. This is **not required for blocking** — it only enables version-level download tracking so you can be notified if a package you installed is later flagged (see [Email-Verified Access](#setup-email-verified)). Run it once per project; otherwise it happens automatically the next time you `composer update`.

:::tip Per-project instead of global
If you prefer not to change global config, add the same two `repositories` entries to a project's `composer.json` instead:

```json
{
  "repositories": [
    { "type": "composer", "url": "https://packagist.flatt.tech" },
    { "packagist.org": false }
  ]
}
```

:::

### Email-Verified Access {#setup-email-verified}

Registering your email address enables download tracking and [breach notifications](/docs/t/guard/features/breach-notifications.md) in addition to package blocking. If a security advisory is published for a package you previously downloaded, a notification is sent to your registered email address. No Shisho Cloud account is required, and this is free of charge.

:::info
If you already have an org user token or email-verified token from using Takumi Guard with npm, PyPI, RubyGems, or Go, you don't need to register again — the same token works for Composer.
:::

**Step 1: Register your email**

```bash
curl -X POST https://packagist.flatt.tech/api/v1/tokens \
  -H "Content-Type: application/json" \
  -d '{"email": "you@example.com", "language": "en"}'
```

The `language` field is optional and defaults to `"en"`. Set it to `"ja"` to receive emails in Japanese. This preference is stored with your token and applies to all future emails, including breach notifications.

You'll receive a welcome email within a few seconds.

**Step 2: Get your API key from the email**

Your API key is included directly in the welcome email. The key is ready to use immediately — no link to click.

:::warning
Save this key somewhere secure. If you need a new one, you can regenerate it anytime: `curl -X POST -H 'Authorization: Bearer tg_anon_xxxxxx' https://packagist.flatt.tech/api/v1/tokens/regenerate`
:::

**Step 3: Configure Composer to send the token**

Composer authenticates to repositories with HTTP Basic auth, keyed by host name. The username is ignored; the token goes in the password field.

```bash
# 1. Add the repository (if not already done)
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech
composer config --global repositories.packagist.org false

# 2. Store the token (written to your global auth.json)
composer config --global --auth http-basic.packagist.flatt.tech token tg_anon_xxxxxx

# 3. Route downloads through the proxy so installs are tracked under your token
#    (run once per project; refreshes lock URLs only, no version changes)
composer update mirrors
```

Composer now authenticates with your `tg_anon_` token on every package fetch. With the lock file pointed at the proxy, your installs are tracked and breach notifications cover the exact versions you downloaded.

### Org User Tokens {#setup-org-user-token}

Org user tokens (`tg_org_…`) can be issued from the Takumi / Shisho Cloud console, or by a bot via the Guard API. See [Token Management](/docs/t/guard/features/token-management.md#user-tokens) for details on issuing tokens.

:::info
A single `tg_org_` token works across all Takumi Guard ecosystems (npm, PyPI, RubyGems, Go, Composer). If you have already issued a token for another ecosystem, the same token can be used here.
:::

Once you have a token, configure the repository and store the token. The final `composer update mirrors` is optional — it routes downloads through the proxy so installs are tracked under your token:

```bash
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech
composer config --global repositories.packagist.org false
composer config --global --auth http-basic.packagist.flatt.tech token tg_org_xxxxxx

# Optional (enables install tracking; not required for blocking):
composer update mirrors
```

Your `composer install` commands now authenticate with the org user token, enabling [organization-wide install tracking](/docs/t/guard/features/installation-logs.md) and organization-level breach notifications (Slack, webhook, etc.).

### Why disable packagist.org? {#why-disable-packagist}

Set the Guard proxy as your only public-package repository, and disable `packagist.org`.

If packagist.org remains enabled, Composer treats it as an equal repository and may resolve and download a package **directly from packagist.org / GitHub**, bypassing Guard's blocklist. Disabling it guarantees that every public package is resolved through Takumi Guard.

Your organization's own private packages should **not** be routed through this proxy — declare them as separate `vcs` or `path` repositories, as described in [Using with Private Packages](#private-packages).

## GitHub Actions {#setup-ci}

To integrate Takumi Guard into your GitHub Actions workflow, use the `flatt-security/setup-takumi-guard-packagist` GitHub Action. You can use it anonymously or linked to an organization. The action configures the repository and injects the token; your existing `composer install` is then protected — blocking applies to your committed lock file with no migration step (Composer 2.10+).

### Anonymous Mode {#setup-ci-anonymous}

If you don't have a Shisho Cloud account yet, you can still use Takumi Guard in CI for package blocking. Omit the `bot-id` input:

```yaml
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: shivammathur/setup-php@v2
        with:
          php-version: "8.3"
          tools: composer:v2

      - uses: flatt-security/setup-takumi-guard-packagist@v1
        # No bot-id — anonymous mode, blocking only

      # Your existing install is now protected — blocked packages are rejected
      # even from a committed composer.lock (Composer 2.10+). No migration needed.
      - run: composer install --no-interaction
```

In anonymous mode, the action only configures the Composer repository. Blocked packages are rejected during `composer install`, but download tracking and [breach notifications](/docs/t/guard/features/breach-notifications.md) are not available.

### With Shisho Cloud Organization {#setup-ci-org}

Linking to a Shisho Cloud organization enables organization-level download tracking and [breach notifications](/docs/t/guard/features/breach-notifications.md) (via webhook). **No long-lived secrets need to be stored in your CI environment.** Authentication is performed securely by exchanging a GitHub OIDC token for a short-lived access token via the Shisho Cloud STS service.

**Prerequisites:**

1. A bot identity registered in Shisho Cloud. Copy the **Bot ID** from the registry settings page in the Shisho Cloud console.
2. The `id-token: write` and `contents: read` permissions in your workflow job.

```yaml
jobs:
  build:
    runs-on: ubuntu-latest
    permissions:
      id-token: write # Required for OIDC token exchange
      contents: read
    steps:
      - uses: actions/checkout@v4
      - uses: shivammathur/setup-php@v2
        with:
          php-version: "8.3"
          tools: composer:v2

      - uses: flatt-security/setup-takumi-guard-packagist@v1
        with:
          bot-id: "BT01EXAMPLE..." # Copy from Shisho Cloud console

      # Protected immediately — blocking covers your committed composer.lock.
      # (Add `composer update mirrors` before this if you want version-level
      # download tracking under your bot identity.)
      - run: composer install --no-interaction
```

The action handles the full OIDC exchange automatically:

1. Requests a GitHub OIDC token (with the registry host as audience)
2. Exchanges it for a short-lived Takumi Guard access token via the STS service
3. Configures the Composer repository and writes the token to `COMPOSER_AUTH`

:::info
The Bot ID is not a secret — it is a public reference key used to look up the allowlist during token exchange. You can commit it directly in your workflow file. The Shisho Cloud console provides a ready-to-copy workflow snippet with the Bot ID pre-filled.
:::

The access token expires after 30 minutes by default (configurable up to 24 hours via the `expires-in` input). If authentication fails (invalid `bot-id`, missing OIDC permission, STS unreachable, etc.), the step exits with a clear error message — there is no silent fallback to anonymous mode.

#### Action Inputs Reference {#action-inputs}

| Input            | Required | Default                        | Description                                                                                                                                  |
| ---------------- | -------- | ------------------------------ | -------------------------------------------------------------------------------------------------------------------------------------------- |
| `bot-id`         | No       | —                              | Bot ID from Shisho Cloud. Omit for anonymous blocking-only mode.                                                                             |
| `set-repository` | No       | `true`                         | Set to `false` if you manage the Composer repository yourself.                                                                               |
| `fail-closed`    | No       | `false`                        | When `true`, `composer install` / `update` fail if the Guard proxy is unreachable, instead of proceeding unblocked. Requires Composer 2.10+. |
| `registry-url`   | No       | `https://packagist.flatt.tech` | Custom registry URL. Override only if directed by Shisho Cloud support.                                                                      |
| `sts-url`        | No       | `https://sts.cloud.shisho.dev` | STS service URL used for the OIDC → access-token exchange.                                                                                   |
| `expires-in`     | No       | `1800` (seconds)               | Access token lifetime in seconds. Maximum `86400` (24 hours).                                                                                |

For the full list of inputs and outputs, see the [action repository](https://github.com/flatt-security/setup-takumi-guard-packagist).

:::tip Fail-closed in CI (optional)
By default, if the Guard proxy is unreachable during `composer install`, Composer logs a warning and proceeds (a package is not blocked while we're unreachable). To make CI fail instead — so a transient outage can never let an install through unchecked — set the action's `fail-closed` input:

```yaml
- uses: flatt-security/setup-takumi-guard-packagist@v1
  with:
    fail-closed: true
```

Outside of GitHub Actions, the equivalent manual configuration is:

```bash
composer config --global policy.ignore-unreachable false
```

You can also add `composer audit --locked` to your pipeline as an extra gate; it reports any blocked package in your lock file, including on Composer versions older than 2.10.
:::

## Using with Private Packages {#private-packages}

Takumi Guard is a read-only security proxy for public packages. If your project depends on private packages (e.g. a private GitHub repository or a private Packagist), declare them as their own repositories so they bypass Guard and are fetched directly:

```json
{
  "repositories": [
    { "type": "composer", "url": "https://packagist.flatt.tech" },
    { "type": "vcs", "url": "https://github.com/your-org/private-lib" },
    { "packagist.org": false }
  ]
}
```

Composer resolves each package from the repository that provides it. Public packages flow through Takumi Guard; your `vcs` / `path` repositories are fetched directly using your existing Git credentials.

:::warning
Private packages routed directly via VCS bypass Takumi Guard's security scanning. This is acceptable for your organization's own packages, but be aware that those packages are not checked against the blocklist.
:::

## Verify Your Setup {#verify-setup}

To confirm that Composer is routing through Takumi Guard, inspect the configured repositories and watch a real fetch go through the proxy host:

```bash
# 1. Confirm the Guard repository is configured and packagist.org is disabled.
composer config --global --list | grep -E 'repositories|packagist'

# 2. Confirm blocking works. flatt-security/hola-takumi-php is a harmless test
#    package we publish that is permanently on the blocklist, so this must fail.
#    --dry-run resolves without writing to your project.
composer require --dry-run flatt-security/hola-takumi-php
```

The second command must **fail** — Composer reports that the package cannot be installed because it is flagged. If it instead resolves successfully, requests are not going through Takumi Guard (re-check step 1). A blocklisted package is rejected during `composer install`, `composer update`, and `composer require` (Composer 2.10+ enforces this even for installs from an existing lock file); a blocklisted **version** of an otherwise-allowed package is removed from resolution so Composer won't select it.

## Uninstall {#uninstall}

To stop using Takumi Guard, remove the repository configuration and re-resolve against the default Packagist.

### Local Environment {#uninstall-local}

```bash
# 1. Remove the Guard repository and re-enable packagist.org
composer config --global --unset repositories.takumi-guard
composer config --global --unset repositories.packagist.org

# 2. Remove the stored token
composer config --global --unset --auth http-basic.packagist.flatt.tech

# 3. Re-resolve each project's lock file against the default Packagist
composer update mirrors
```

### Revoking Org User Tokens {#uninstall-org-token}

If you are using org user tokens (`tg_org_…`), revoke them from **Guard** > **Tokens** in Shisho Cloud console in addition to updating your local config. Active tokens continue to be billed. See [Pricing](/docs/t/guard/billing/pricing.md) for details.

## Quick Reference {#quick-reference}

Minimum configuration for each usage tier. Replace `tg_anon_xxxxxx` / `tg_org_xxxxxx` with your actual token. The two `composer config` lines are the complete setup for blocking; the trailing `composer update mirrors` is **optional** and only enables download tracking (run once per project).

### Anonymous {#quick-reference-anonymous}

```bash
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech
composer config --global repositories.packagist.org false
composer update mirrors  # optional: download tracking
```

### Anonymous (email-verified) {#quick-reference-email}

```bash
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech
composer config --global repositories.packagist.org false
composer config --global --auth http-basic.packagist.flatt.tech token tg_anon_xxxxxx
composer update mirrors  # optional: download tracking
```

### Organization {#quick-reference-org}

```bash
composer config --global repositories.takumi-guard composer https://packagist.flatt.tech
composer config --global repositories.packagist.org false
composer config --global --auth http-basic.packagist.flatt.tech token tg_org_xxxxxx
composer update mirrors  # optional: download tracking
```
