Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
94 changes: 28 additions & 66 deletions .github/workflows/compile-ai-docs-from-gcs.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,22 +8,13 @@ on:
types: [ai-docs-source-updated]

workflow_dispatch:
inputs:
create_release:
description: 'Create a GitHub release with the bundle'
required: false
default: 'false'
type: choice
options:
- 'true'
- 'false'

concurrency:
group: compile-ai-docs-${{ github.ref }}
cancel-in-progress: false

permissions:
contents: write # For creating/updating releases
contents: read
id-token: write # For GCP workload identity federation
packages: write # For pushing to GHCR
# TODO: Split into separate compile (read-only) and publish (write) jobs
Expand Down Expand Up @@ -56,15 +47,13 @@ jobs:
objects.githubusercontent.com:443
pypi.org:443
raw.githubusercontent.com:443
release-assets.githubusercontent.com:443
rekor.sigstore.dev:443
run.googleapis.com:443
us-central1-run.googleapis.com:443
sts.googleapis.com:443
storage.googleapis.com:443
timestamp.sigstore.dev:443
tuf-repo-cdn.sigstore.dev:443
uploads.github.com:443

- name: Checkout edu repository
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
Expand Down Expand Up @@ -295,23 +284,45 @@ jobs:
--role "roles/run.invoker" \
--project "$PROJECT_ID" || true

- name: Sign bundle files
if: github.ref == 'refs/heads/main'
run: |
cd static/downloads
cosign sign-blob chainguard-ai-docs.tar.gz \
--yes \
--bundle=chainguard-ai-docs.tar.gz.bundle
cosign sign-blob chainguard-ai-docs.md \
--yes \
--bundle=chainguard-ai-docs.md.bundle
echo "Bundle files signed"

- name: Upload bundle back to GCS for distribution
env:
COMMIT_SHA: ${{ github.sha }}
EVENT_NAME: ${{ github.event_name }}
run: |
echo "Uploading compiled bundle to GCS..."

# Upload the compiled bundle for easy distribution
gcloud storage cp static/downloads/chainguard-ai-docs.tar.gz \
gs://academy-all-docs/compiled/chainguard-ai-docs.tar.gz \
--project=chainguard-academy

# Upload checksums
gcloud storage cp static/downloads/checksums.txt \
gs://academy-all-docs/compiled/checksums.txt \
--project=chainguard-academy


# Upload cosign bundle files for artifact verification (only present on main branch builds)
if [ -f "static/downloads/chainguard-ai-docs.tar.gz.bundle" ]; then
gcloud storage cp static/downloads/chainguard-ai-docs.tar.gz.bundle \
gs://academy-all-docs/compiled/chainguard-ai-docs.tar.gz.bundle \
--project=chainguard-academy
gcloud storage cp static/downloads/chainguard-ai-docs.md.bundle \
gs://academy-all-docs/compiled/chainguard-ai-docs.md.bundle \
--project=chainguard-academy
fi

# Create and upload compilation metadata
python3 -c "
import json, datetime, os
Expand All @@ -324,58 +335,9 @@ jobs:
with open('/tmp/compilation-metadata.json', 'w') as f:
json.dump(meta, f, indent=2)
"

gcloud storage cp /tmp/compilation-metadata.json \
gs://academy-all-docs/compiled/metadata.json \
--project=chainguard-academy

echo "✓ Bundle uploaded to GCS"

- name: Sign bundle files
if: github.ref == 'refs/heads/main'
run: |
cd static/downloads
cosign sign-blob chainguard-ai-docs.tar.gz \
--yes \
--bundle=chainguard-ai-docs.tar.gz.bundle
cosign sign-blob chainguard-ai-docs.md \
--yes \
--bundle=chainguard-ai-docs.md.bundle
echo "Bundle files signed"

- name: Create GitHub Release
if: github.ref == 'refs/heads/main'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
TAG="ai-docs-$(date -u +%Y%m%d-%H%M%S)"

gh release create "$TAG" \
--title "AI Documentation Bundle $TAG" \
--notes "Chainguard AI documentation bundle for use with AI coding assistants." \
--latest \
static/downloads/chainguard-ai-docs.tar.gz \
static/downloads/chainguard-ai-docs.tar.gz.bundle \
static/downloads/chainguard-ai-docs.md \
static/downloads/chainguard-ai-docs.md.bundle \
static/downloads/chainguard-ai-docs.zip \
static/downloads/image-catalog.json \
static/downloads/checksums.txt \
scripts/mcp-server.py \
scripts/mcp-requirements.txt

echo "Release $TAG created"

- name: Clean up old releases
if: github.ref == 'refs/heads/main'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
# Keep only the 10 most recent dated releases; delete older ones
gh release list --limit 100 --json tagName,createdAt \
| jq -r '[.[] | select(.tagName | test("^ai-docs-[0-9]{8}-[0-9]{6}$"))] | sort_by(.createdAt) | reverse | .[10:] | .[].tagName' \
| while read -r tag; do
echo "Deleting old release: $tag"
gh release delete "$tag" --yes --cleanup-tag
done
echo "Release cleanup complete"
echo "✓ Bundle uploaded to GCS"
18 changes: 5 additions & 13 deletions content/ai-docs-security.md
Original file line number Diff line number Diff line change
Expand Up @@ -86,22 +86,14 @@ Example patterns we redact:

## Verification Guide

### Direct Download Verification
### Container Image Verification

```bash
# 1. Download files
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/chainguard-ai-docs.tar.gz
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/chainguard-ai-docs.tar.gz.bundle
Verify the container image signature before pulling documentation:

# 2. Verify signature (using cosign v3 bundle format)
cosign verify-blob \
--bundle chainguard-ai-docs.tar.gz.bundle \
```bash
cosign verify ghcr.io/chainguard-dev/ai-docs:latest \
--certificate-identity-regexp ".*github.com/chainguard-dev/edu.*" \
--certificate-oidc-issuer https://token.actions.githubusercontent.com \
chainguard-ai-docs.tar.gz

# 3. Extract contents
tar -xzf chainguard-ai-docs.tar.gz
--certificate-oidc-issuer https://token.actions.githubusercontent.com
```

## Build Frequency
Expand Down
12 changes: 3 additions & 9 deletions content/developer-resources.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ toc: false

## AI-Ready Documentation Bundle

This page provides compiled Chainguard documentation optimized for use with AI coding assistants like Claude, ChatGPT, GitHub Copilot, and others. Choose between our cryptographically signed direct downloads or our secure container distribution.
This page provides compiled Chainguard documentation optimized for use with AI coding assistants like Claude, ChatGPT, GitHub Copilot, and others. Access it through our secure container image or as a standalone Python MCP server.

### What's Included

Expand All @@ -40,12 +40,6 @@ Choose your preferred distribution method:
For enhanced security and verification, we recommend using the Chainguard container image. It includes built-in verification, runs as non-root, and is built on our secure <code>wolfi-base</code> image.
</div>

### GitHub Release

| Format | Description | Verification |
|--------|-------------|-------------|
| [Latest Release](https://github.com/chainguard-dev/edu/releases/latest) | Cryptographically signed documentation bundle | Includes Cosign signatures and certificates |

### Container Distribution

Pull the secure, Chainguard-based container with embedded documentation:
Expand Down Expand Up @@ -119,7 +113,7 @@ Add to your `claude_desktop_config.json`:
- Searchable and queryable documentation
- Perfect for automated workflows
- Works with Claude Desktop, Cursor, and other MCP-compatible tools
- Also available as a [standalone Python script](https://github.com/chainguard-dev/edu/releases/latest) (no Docker required)
- Also available as a [standalone Python script](/mcp-server-ai-docs/#standalone-installation-without-docker) (no Docker required)

[**Full MCP Server Documentation →**](/mcp-server-ai-docs/)

Expand All @@ -137,7 +131,7 @@ docker run --rm -v $(pwd):/output ghcr.io/chainguard-dev/ai-docs:latest extract
<div style="border: 2px solid #4CAF50; padding: 20px; border-radius: 8px; margin: 20px 0;">
<h4>Available Security Features</h4>
<ul>
<li>Signed releases with Sigstore/Cosign</li>
<li>Container image signed with Sigstore/Cosign</li>
<li>Container distribution via GitHub Container Registry</li>
<li>Automated updates via GitHub Actions</li>
<li>Security scanning with gitleaks</li>
Expand Down
14 changes: 8 additions & 6 deletions content/mcp-server-ai-docs.md
Original file line number Diff line number Diff line change
Expand Up @@ -242,14 +242,16 @@ latest, latest-dev, 3.13, 3.13-dev, ...

## Standalone Installation (without Docker)

The MCP server is also available as a standalone Python script from the [latest GitHub release](https://github.com/chainguard-dev/edu/releases/latest):
The MCP server script and its dependencies are available directly from the repository. The documentation files are distributed via the container image.

```bash
# Download the MCP server, requirements, docs, and catalog
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/mcp-server.py
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/mcp-requirements.txt
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/chainguard-ai-docs.md
curl -LO https://github.com/chainguard-dev/edu/releases/latest/download/image-catalog.json
# Download the MCP server script and requirements
curl -LO https://raw.githubusercontent.com/chainguard-dev/edu/main/scripts/mcp-server.py
curl -LO https://raw.githubusercontent.com/chainguard-dev/edu/main/scripts/mcp-requirements.txt

# Extract the documentation bundle from the container image
docker run --rm -v $(pwd):/output ghcr.io/chainguard-dev/ai-docs:latest extract /output
# Writes chainguard-ai-docs.md and image-catalog.json to the current directory

# Install dependencies
pip install -r mcp-requirements.txt
Expand Down