A container registry that uses the AT Protocol for manifest storage and S3 for blob storage. atcr.io
docker container atproto go
72
fork

Configure Feed

Select the types of activity you want to include in your feed.

at refactor 692 lines 20 kB view raw view rendered
1# ATCR Signature Verification Integration Strategy 2 3## Overview 4 5This document provides a comprehensive overview of how to integrate ATProto signature verification into various tools and workflows. ATCR uses a layered approach that provides maximum compatibility while maintaining ATProto's decentralized philosophy. 6 7## Architecture Layers 8 9``` 10┌─────────────────────────────────────────────────────────┐ 11│ Layer 4: Applications & Workflows │ 12│ - CI/CD pipelines │ 13│ - Kubernetes admission control │ 14│ - Runtime verification │ 15│ - Security scanning │ 16└──────────────────────┬──────────────────────────────────┘ 17 18┌─────────────────────────────────────────────────────────┐ 19│ Layer 3: Integration Methods │ 20│ - Plugins (Ratify, Gatekeeper, Containerd) │ 21│ - CLI tools (atcr-verify) │ 22│ - External services (webhooks, APIs) │ 23│ - (Optional) X.509 certificates (hold-as-CA) │ 24└──────────────────────┬──────────────────────────────────┘ 25 26┌─────────────────────────────────────────────────────────┐ 27│ Layer 2: Signature Discovery │ 28│ - OCI Referrers API (GET /v2/.../referrers/...) │ 29│ - ORAS artifact format │ 30│ - artifactType: application/vnd.atproto.signature... │ 31└──────────────────────┬──────────────────────────────────┘ 32 33┌─────────────────────────────────────────────────────────┐ 34│ Layer 1: ATProto Signatures (Foundation) │ 35│ - Manifests signed by PDS (K-256) │ 36│ - Signatures in ATProto repository commits │ 37│ - Public keys in DID documents │ 38│ - DID-based identity │ 39└─────────────────────────────────────────────────────────┘ 40``` 41 42## Integration Approaches 43 44### Approach 1: Plugin-Based (RECOMMENDED) ⭐ 45 46**Best for:** Kubernetes, standard tooling, production deployments 47 48Integrate through plugin systems of existing tools: 49 50#### Ratify Verifier Plugin 51- **Use case:** Kubernetes admission control via Gatekeeper 52- **Effort:** 2-3 weeks to build 53- **Maturity:** CNCF Sandbox project, growing adoption 54- **Benefits:** 55 - ✅ Standard plugin interface 56 - ✅ Works with existing Ratify deployments 57 - ✅ Policy-based enforcement 58 - ✅ Multi-verifier support (can combine with Notation, Cosign) 59 60**Implementation:** 61```go 62// Ratify plugin interface 63type ReferenceVerifier interface { 64 VerifyReference( 65 ctx context.Context, 66 subjectRef common.Reference, 67 referenceDesc ocispecs.ReferenceDescriptor, 68 store referrerStore.ReferrerStore, 69 ) (VerifierResult, error) 70} 71``` 72 73**Deployment:** 74```yaml 75apiVersion: config.ratify.deislabs.io/v1beta1 76kind: Verifier 77metadata: 78 name: atcr-verifier 79spec: 80 name: atproto 81 artifactType: application/vnd.atproto.signature.v1+json 82 parameters: 83 trustedDIDs: 84 - did:plc:alice123 85``` 86 87See [Ratify Integration Guide](./SIGNATURE_INTEGRATION.md#ratify-plugin) 88 89--- 90 91#### OPA Gatekeeper External Provider 92- **Use case:** Kubernetes admission control with OPA policies 93- **Effort:** 2-3 weeks to build 94- **Maturity:** Very stable, widely adopted 95- **Benefits:** 96 - ✅ Rego-based policies (flexible) 97 - ✅ External data provider API (standard) 98 - ✅ Can reuse existing Gatekeeper deployments 99 100**Implementation:** 101```go 102// External data provider 103type Provider struct { 104 verifier *atproto.Verifier 105} 106 107func (p *Provider) Provide(ctx context.Context, req ProviderRequest) (*ProviderResponse, error) { 108 image := req.Keys["image"] 109 result, err := p.verifier.Verify(ctx, image) 110 return &ProviderResponse{ 111 Data: map[string]bool{"verified": result.Verified}, 112 }, nil 113} 114``` 115 116**Policy:** 117```rego 118package verify 119 120violation[{"msg": msg}] { 121 container := input.review.object.spec.containers[_] 122 startswith(container.image, "atcr.io/") 123 124 response := external_data({ 125 "provider": "atcr-verifier", 126 "keys": ["image"], 127 "values": [container.image] 128 }) 129 130 response.verified != true 131 msg := sprintf("Image %v has no valid ATProto signature", [container.image]) 132} 133``` 134 135See [Gatekeeper Integration Guide](./SIGNATURE_INTEGRATION.md#opa-gatekeeper-external-provider) 136 137--- 138 139#### Containerd 2.0 Image Verifier Plugin 140- **Use case:** Runtime verification at image pull time 141- **Effort:** 1-2 weeks to build 142- **Maturity:** New in Containerd 2.0 (Nov 2024) 143- **Benefits:** 144 - ✅ Runtime enforcement (pull-time verification) 145 - ✅ Works for Docker, nerdctl, ctr 146 - ✅ Transparent to users 147 - ✅ No Kubernetes required 148 149**Limitation:** CRI plugin integration still maturing 150 151**Implementation:** 152```bash 153#!/bin/bash 154# /usr/local/bin/containerd-verifiers/atcr-verifier 155# Binary called by containerd on image pull 156 157# Containerd passes image info via stdin 158read -r INPUT 159 160IMAGE=$(echo "$INPUT" | jq -r '.reference') 161DIGEST=$(echo "$INPUT" | jq -r '.descriptor.digest') 162 163# Verify signature 164if atcr-verify "$IMAGE@$DIGEST" --quiet; then 165 exit 0 # Verified 166else 167 exit 1 # Failed 168fi 169``` 170 171**Configuration:** 172```toml 173# /etc/containerd/config.toml 174[plugins."io.containerd.image-verifier.v1.bindir"] 175 bin_dir = "/usr/local/bin/containerd-verifiers" 176 max_verifiers = 5 177 per_verifier_timeout = "10s" 178``` 179 180See [Containerd Integration Guide](./SIGNATURE_INTEGRATION.md#containerd-20) 181 182--- 183 184### Approach 2: CLI Tool (RECOMMENDED) ⭐ 185 186**Best for:** CI/CD, scripts, general-purpose verification 187 188Use `atcr-verify` CLI tool directly in workflows: 189 190#### Command-Line Verification 191```bash 192# Basic verification 193atcr-verify atcr.io/alice/myapp:latest 194 195# With trust policy 196atcr-verify atcr.io/alice/myapp:latest --policy trust-policy.yaml 197 198# JSON output for scripting 199atcr-verify atcr.io/alice/myapp:latest --output json 200 201# Quiet mode for exit codes 202atcr-verify atcr.io/alice/myapp:latest --quiet && echo "Verified" 203``` 204 205#### CI/CD Integration 206 207**GitHub Actions:** 208```yaml 209- name: Verify image 210 run: atcr-verify ${{ env.IMAGE }} --policy .github/trust-policy.yaml 211``` 212 213**GitLab CI:** 214```yaml 215verify: 216 image: atcr.io/atcr/verify:latest 217 script: 218 - atcr-verify ${IMAGE} --policy trust-policy.yaml 219``` 220 221**Universal Container:** 222```bash 223docker run --rm atcr.io/atcr/verify:latest verify IMAGE 224``` 225 226**Benefits:** 227- ✅ Works everywhere (not just Kubernetes) 228- ✅ Simple integration (single binary) 229- ✅ No plugin installation required 230- ✅ Offline mode support 231 232See [atcr-verify CLI Documentation](./ATCR_VERIFY_CLI.md) 233 234--- 235 236### Approach 3: External Services 237 238**Best for:** Custom admission controllers, API-based verification 239 240Build verification as a service that tools can call: 241 242#### Webhook Service 243```go 244// HTTP endpoint for verification 245func (h *Handler) VerifyImage(w http.ResponseWriter, r *http.Request) { 246 image := r.URL.Query().Get("image") 247 248 result, err := h.verifier.Verify(r.Context(), image) 249 if err != nil { 250 http.Error(w, err.Error(), http.StatusInternalServerError) 251 return 252 } 253 254 json.NewEncoder(w).Encode(map[string]interface{}{ 255 "verified": result.Verified, 256 "did": result.Signature.DID, 257 "signedAt": result.Signature.SignedAt, 258 }) 259} 260``` 261 262#### Usage from Kyverno 263```yaml 264verifyImages: 265- imageReferences: 266 - "atcr.io/*/*" 267 attestors: 268 - entries: 269 - api: 270 url: http://atcr-verify.kube-system/verify?image={{ image }} 271``` 272 273**Benefits:** 274- ✅ Flexible integration 275- ✅ Centralized verification logic 276- ✅ Caching and rate limiting 277- ✅ Can add additional checks (vulnerability scanning, etc.) 278 279--- 280 281### Approach 4: Hold-as-CA (OPTIONAL, ENTERPRISE ONLY) 282 283**Best for:** Enterprise X.509 PKI compliance requirements 284 285⚠️ **WARNING:** This approach introduces centralization trade-offs. Only use if you have specific X.509 compliance requirements. 286 287Hold services act as Certificate Authorities that issue X.509 certificates for users, enabling standard Notation verification. 288 289**When to use:** 290- Enterprise requires standard X.509 PKI 291- Cannot deploy custom plugins 292- Accept centralization trade-off for tool compatibility 293 294**When NOT to use:** 295- Default deployments (use plugins instead) 296- Maximum decentralization required 297- Don't need X.509 compliance 298 299See [Hold-as-CA Architecture](./HOLD_AS_CA.md) for complete details and security implications. 300 301--- 302 303## Tool Compatibility Matrix 304 305| Tool | Discover | Verify | Integration Method | Priority | Effort | 306|------|----------|--------|-------------------|----------|--------| 307| **Kubernetes** | | | | | | 308| OPA Gatekeeper | ✅ | ✅ | External provider | **HIGH** | 2-3 weeks | 309| Ratify | ✅ | ✅ | Verifier plugin | **HIGH** | 2-3 weeks | 310| Kyverno | ✅ | ⚠️ | External service | MEDIUM | 2 weeks | 311| Portieris | ❌ | ❌ | N/A (deprecated) | NONE | - | 312| **Runtime** | | | | | | 313| Containerd 2.0 | ✅ | ✅ | Bindir plugin | **MED-HIGH** | 1-2 weeks | 314| CRI-O | ⚠️ | ⚠️ | Upstream contribution | MEDIUM | 3-4 weeks | 315| Podman | ⚠️ | ⚠️ | Upstream contribution | MEDIUM | 3-4 weeks | 316| **CI/CD** | | | | | | 317| GitHub Actions | ✅ | ✅ | Custom action | **HIGH** | 1 week | 318| GitLab CI | ✅ | ✅ | Container image | **HIGH** | 1 week | 319| Jenkins/CircleCI | ✅ | ✅ | Container image | HIGH | 1 week | 320| **Scanners** | | | | | | 321| Trivy | ✅ | ❌ | N/A (not verifier) | NONE | - | 322| Snyk | ❌ | ❌ | N/A (not verifier) | NONE | - | 323| Anchore | ❌ | ❌ | N/A (not verifier) | NONE | - | 324| **Registries** | | | | | | 325| Harbor | ✅ | ⚠️ | UI integration | LOW | - | 326| **OCI Tools** | | | | | | 327| ORAS CLI | ✅ | ❌ | Already works | Document | - | 328| Notation | ⚠️ | ⚠️ | Hold-as-CA | OPTIONAL | 3-4 weeks | 329| Cosign | ❌ | ❌ | Not compatible | NONE | - | 330| Crane | ✅ | ❌ | Already works | Document | - | 331| Skopeo | ⚠️ | ⚠️ | Upstream contribution | LOW | 3-4 weeks | 332 333**Legend:** 334- ✅ Works / Feasible 335- ⚠️ Partial / Requires changes 336- ❌ Not applicable / Not feasible 337 338--- 339 340## Implementation Roadmap 341 342### Phase 1: Foundation (4-5 weeks) ⭐ 343 344**Goal:** Core verification capability 345 3461. **atcr-verify CLI tool** (Week 1-2) 347 - ATProto signature verification 348 - Trust policy support 349 - Multiple output formats 350 - Offline mode 351 3522. **OCI Referrers API** (Week 2-3) 353 - AppView endpoint implementation 354 - ORAS artifact serving 355 - Integration with existing SBOM pattern 356 3573. **CI/CD Container Image** (Week 3) 358 - Universal verification image 359 - Documentation for GitHub Actions, GitLab CI 360 - Example workflows 361 3624. **Documentation** (Week 4-5) 363 - Integration guides 364 - Trust policy examples 365 - Troubleshooting guides 366 367**Deliverables:** 368- `atcr-verify` binary (Linux, macOS, Windows) 369- `atcr.io/atcr/verify:latest` container image 370- OCI Referrers API implementation 371- Complete documentation 372 373--- 374 375### Phase 2: Kubernetes Integration (3-4 weeks) 376 377**Goal:** Production-ready Kubernetes admission control 378 3795. **OPA Gatekeeper Provider** (Week 1-2) 380 - External data provider service 381 - Helm chart for deployment 382 - Example policies 383 3846. **Ratify Plugin** (Week 2-3) 385 - Verifier plugin implementation 386 - Testing with Ratify 387 - Documentation 388 3897. **Kubernetes Examples** (Week 4) 390 - Deployment manifests 391 - Policy examples 392 - Integration testing 393 394**Deliverables:** 395- `atcr-gatekeeper-provider` service 396- Ratify plugin binary 397- Kubernetes deployment examples 398- Production deployment guide 399 400--- 401 402### Phase 3: Runtime Verification (2-3 weeks) 403 404**Goal:** Pull-time verification 405 4068. **Containerd Plugin** (Week 1-2) 407 - Bindir verifier implementation 408 - Configuration documentation 409 - Testing with Docker, nerdctl 410 4119. **CRI-O/Podman Integration** (Week 3, optional) 412 - Upstream contribution (if accepted) 413 - Policy.json extension 414 - Documentation 415 416**Deliverables:** 417- Containerd verifier binary 418- Configuration guides 419- Runtime verification examples 420 421--- 422 423### Phase 4: Optional Features (2-3 weeks) 424 425**Goal:** Enterprise features (if demanded) 426 42710. **Hold-as-CA** (Week 1-2, optional) 428 - Certificate generation 429 - Notation signature creation 430 - Trust store distribution 431 - **Only if enterprise customers request** 432 43311. **Advanced Features** (Week 3, as needed) 434 - Signature transparency log 435 - Multi-signature support 436 - Hardware token integration 437 438**Deliverables:** 439- Hold co-signing implementation (if needed) 440- Advanced feature documentation 441 442--- 443 444## Decision Matrix 445 446### Which Integration Approach Should I Use? 447 448``` 449┌─────────────────────────────────────────────────┐ 450│ Are you using Kubernetes? │ 451└───────────────┬─────────────────────────────────┘ 452453 ┌────────┴────────┐ 454 │ │ 455 YES NO 456 │ │ 457 ↓ ↓ 458┌──────────────┐ ┌──────────────┐ 459│ Using │ │ CI/CD │ 460│ Gatekeeper? │ │ Pipeline? │ 461└──────┬───────┘ └──────┬───────┘ 462 │ │ 463 ┌────┴────┐ ┌────┴────┐ 464 YES NO YES NO 465 │ │ │ │ 466 ↓ ↓ ↓ ↓ 467External Ratify GitHub Universal 468Provider Plugin Action CLI Tool 469``` 470 471#### Use OPA Gatekeeper Provider if: 472- ✅ Already using Gatekeeper 473- ✅ Want Rego-based policies 474- ✅ Need flexible policy logic 475 476#### Use Ratify Plugin if: 477- ✅ Using Ratify (or planning to) 478- ✅ Want standard plugin interface 479- ✅ Need multi-verifier support (Notation + Cosign + ATProto) 480 481#### Use atcr-verify CLI if: 482- ✅ CI/CD pipelines 483- ✅ Local development 484- ✅ Non-Kubernetes environments 485- ✅ Want simple integration 486 487#### Use Containerd Plugin if: 488- ✅ Need runtime enforcement 489- ✅ Want pull-time verification 490- ✅ Using Containerd 2.0+ 491 492#### Use Hold-as-CA if: 493- ⚠️ Enterprise X.509 PKI compliance required 494- ⚠️ Cannot deploy plugins 495- ⚠️ Accept centralization trade-off 496 497--- 498 499## Best Practices 500 501### 1. Start Simple 502 503Begin with CLI tool integration in CI/CD: 504```bash 505# Add to .github/workflows/deploy.yml 506- run: atcr-verify $IMAGE --policy .github/trust-policy.yaml 507``` 508 509### 2. Define Trust Policies 510 511Create trust policies early: 512```yaml 513# trust-policy.yaml 514policies: 515 - name: production 516 scope: "atcr.io/*/prod-*" 517 require: 518 signature: true 519 trustedDIDs: [did:plc:devops-team] 520 action: enforce 521``` 522 523### 3. Progressive Rollout 524 5251. **Week 1:** Add verification to CI/CD (audit mode) 5262. **Week 2:** Enforce in CI/CD 5273. **Week 3:** Add Kubernetes admission control (audit mode) 5284. **Week 4:** Enforce in Kubernetes 529 530### 4. Monitor and Alert 531 532Track verification metrics: 533- Verification success/failure rates 534- Policy violations 535- Signature coverage (% of images signed) 536 537### 5. Plan for Key Rotation 538 539- Document DID key rotation procedures 540- Test key rotation in non-production 541- Monitor for unexpected key changes 542 543--- 544 545## Common Patterns 546 547### Pattern 1: Multi-Layer Defense 548 549``` 5501. CI/CD verification (atcr-verify) 551 ↓ (blocks unsigned images from being pushed) 5522. Kubernetes admission (Gatekeeper/Ratify) 553 ↓ (blocks unsigned images from running) 5543. Runtime verification (Containerd plugin) 555 ↓ (blocks unsigned images from being pulled) 556``` 557 558### Pattern 2: Trust Policy Inheritance 559 560```yaml 561# Global policy 562trustedDIDs: 563 - did:plc:security-team # Always trusted 564 565# Environment-specific policies 566staging: 567 trustedDIDs: 568 - did:plc:developers # Additional trust for staging 569 570production: 571 trustedDIDs: [] # Only global trust (security-team) 572``` 573 574### Pattern 3: Offline Verification 575 576```bash 577# Build environment (online) 578atcr-verify export $IMAGE -o bundle.json 579 580# Air-gapped environment (offline) 581atcr-verify $IMAGE --offline --bundle bundle.json 582``` 583 584--- 585 586## Migration Guide 587 588### From Docker Content Trust (DCT) 589 590DCT is deprecated. Migrate to ATCR signatures: 591 592**Old (DCT):** 593```bash 594export DOCKER_CONTENT_TRUST=1 595docker push myimage:latest 596``` 597 598**New (ATCR):** 599```bash 600# Signatures created automatically on push 601docker push atcr.io/myorg/myimage:latest 602 603# Verify in CI/CD 604atcr-verify atcr.io/myorg/myimage:latest 605``` 606 607### From Cosign 608 609Cosign and ATCR signatures can coexist: 610 611**Dual signing:** 612```bash 613# Push to ATCR (ATProto signature automatic) 614docker push atcr.io/myorg/myimage:latest 615 616# Also sign with Cosign (if needed) 617cosign sign atcr.io/myorg/myimage:latest 618``` 619 620**Verification:** 621```bash 622# Verify ATProto signature 623atcr-verify atcr.io/myorg/myimage:latest 624 625# Or verify Cosign signature 626cosign verify atcr.io/myorg/myimage:latest --key cosign.pub 627``` 628 629--- 630 631## Troubleshooting 632 633### Signatures Not Found 634 635**Symptom:** `atcr-verify` reports "no signature found" 636 637**Diagnosis:** 638```bash 639# Check if Referrers API works 640curl "https://atcr.io/v2/OWNER/REPO/referrers/DIGEST" 641 642# Check if signature artifact exists 643oras discover atcr.io/OWNER/REPO:TAG 644``` 645 646**Solutions:** 6471. Verify Referrers API is implemented 6482. Re-push image to generate signature 6493. Check AppView logs for signature creation errors 650 651### DID Resolution Fails 652 653**Symptom:** Cannot resolve DID to public key 654 655**Diagnosis:** 656```bash 657# Test DID resolution 658curl https://plc.directory/did:plc:XXXXXX 659 660# Check DID document has verificationMethod 661curl https://plc.directory/did:plc:XXXXXX | jq .verificationMethod 662``` 663 664**Solutions:** 6651. Check internet connectivity 6662. Verify DID is valid 6673. Ensure DID document contains public key 668 669### Policy Violations 670 671**Symptom:** Verification fails with "trust policy violation" 672 673**Diagnosis:** 674```bash 675# Verify with verbose output 676atcr-verify IMAGE --policy policy.yaml --verbose 677``` 678 679**Solutions:** 6801. Add DID to trustedDIDs list 6812. Check signature age vs. maxAge 6823. Verify policy scope matches image 683 684--- 685 686## See Also 687 688- [ATProto Signatures](./ATPROTO_SIGNATURES.md) - Technical foundation 689- [atcr-verify CLI](./ATCR_VERIFY_CLI.md) - CLI tool documentation 690- [Signature Integration](./SIGNATURE_INTEGRATION.md) - Tool-specific guides 691- [Hold-as-CA](./HOLD_AS_CA.md) - X.509 certificate approach (optional) 692- [Examples](../examples/verification/) - Working code examples