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
2 changes: 1 addition & 1 deletion .mise.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[tools]
actionlint = "1.7.7"
ginkgo = '2.22.2'
ginkgo = '2.23.4'
golang = '1.24'
golangci-lint = "2.1.6"
"go:golang.org/x/tools/cmd/goimports" = "0.33.0"
Expand Down
112 changes: 112 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
# CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

## Development Commands

### Prerequisites Setup

```bash
mise trust
mise install # Installs all dependencies including go, docker, kubectl, etc.
```

### Core Development

```bash
make help # Show all available make targets
make build # Build manager binary
make run # Run controller locally
make test # Run unit tests with coverage
make test-e2e # Run end-to-end tests
make watch # Watch tests continuously
make lint # Run golangci-lint and yamllint
make lint-fix # Run linters with auto-fix
```

Once the project has been built at least once, you can also run `ginkgo`
directly to execute individual tests. See the @Makefile for how to run it.

### Code Generation

```bash
make manifests # Generate CRDs, webhooks, ClusterRoles
make generate # Generate DeepCopy methods
make docs # Generate CRD documentation (PrefectServer.md, PrefectWorkPool.md)
```

### Kubernetes Operations

```bash
make install # Install CRDs to cluster
make uninstall # Remove CRDs from cluster
make deploy # Deploy operator via Helm
make undeploy # Remove operator deployment
kubectl apply -k deploy/samples/ # Apply sample resources
```

### Docker Operations

```bash
make docker-build IMG=<registry>/prefect-operator:tag
make docker-push IMG=<registry>/prefect-operator:tag
```

## Architecture

This is a Kubernetes operator built with Kubebuilder that manages Prefect infrastructure components.

### Core Custom Resources

- **PrefectServer**: Manages Prefect server deployments with configurable storage backends (ephemeral, SQLite, PostgreSQL) and optional Redis messaging
- **PrefectWorkPool**: Manages Prefect work pools for different execution environments (Kubernetes, process-based, external)
- **PrefectDeployment**: Manages Prefect deployments (not Kubernetes ones) of Python flows

### Key Components

- **Controllers** (`internal/controller/`): Reconciliation logic for CRDs
- **API Types** (`api/v1/`): CRD definitions and helper methods
- **Utils** (`internal/utils/`): Hash utilities for detecting resource changes
- **Conditions** (`internal/conditions/`): Status condition management
- **Constants** (`internal/constants/`): Shared constants

### Deployment Architecture

- Main controller runs as a deployment in cluster
- Uses controller-runtime for Kubernetes API interactions
- Supports namespace-scoped operation via `WATCH_NAMESPACES` env var
- Health checks on `:8081`, metrics on `:8080`
- Leader election enabled for HA deployments

### Storage Backend Configuration

PrefectServer supports three storage modes:

1. **Ephemeral**: In-memory SQLite (no persistence)
2. **SQLite**: Persistent SQLite with PVC storage
3. **PostgreSQL**: External PostgreSQL database with connection details

Each backend generates appropriate environment variables for the Prefect server container.

### Testing Strategy

- Unit tests use Ginkgo/Gomega with envtest for Kubernetes API simulation
- E2E tests require actual Kubernetes cluster
- Coverage includes API types, controllers, and utilities
- Tests run against Kubernetes v1.29.0 via envtest

The typically manual testing approach is to run a local cluster like `minikube`
and run the `prefect-operator` locally pointing to that cluster. That means
that for many testing scenarios, we can't assume that the operator is running
in the same cluster it is operating on. Use port-forwarding where appropriate
to support these cases.

### Code Generation Workflow

The operator uses controller-gen for:

- CRD generation from Go types → `deploy/charts/prefect-operator/crds/`
- DeepCopy method generation for all API types
- RBAC manifest generation

Always run `make manifests generate` after modifying API types in `api/v1/`.
1 change: 1 addition & 0 deletions CLAUDE.md
3 changes: 3 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,8 @@ manifests: tools ## Generate WebhookConfiguration, ClusterRole and CustomResourc
.PHONY: generate
generate: tools ## Generate code containing DeepCopy, DeepCopyInto, and DeepCopyObject method implementations.
$(CONTROLLER_GEN) object:headerFile="hack/boilerplate.go.txt" paths="./..."
@echo "Adding coverage ignore directive to generated files..."
@sed -i '1a\\n//go:coverage ignore' api/v1/zz_generated.deepcopy.go

.PHONY: fmt
fmt: ## Run go fmt against code.
Expand Down Expand Up @@ -139,6 +141,7 @@ run: manifests generate fmt vet ## Run a controller from your host.
docs: tools
crdoc --resources deploy/charts/prefect-operator/crds/prefect.io_prefectservers.yaml --output PrefectServer.md
crdoc --resources deploy/charts/prefect-operator/crds/prefect.io_prefectworkpools.yaml --output PrefectWorkPool.md
crdoc --resources deploy/charts/prefect-operator/crds/prefect.io_prefectdeployments.yaml --output PrefectDeployment.md

# If you wish to build the manager image targeting other platforms you can use the --platform flag.
# (i.e. docker build --platform linux/arm64). However, you must enable docker buildKit for it.
Expand Down
Loading