A production-ready Kubernetes operator that automates deployment, scaling, and management of Frappe Framework applications (including ERPNext) on Kubernetes.
π Complete Documentation | π Examples | π¬ Discussions
- One-Command Deployment - Deploy Frappe/ERPNext with a single kubectl command
- Multi-Tenancy - Run hundreds of sites on shared infrastructure
- Site-Specific Apps - Install different apps per site with graceful degradation
- Secure by Default - Auto-generated credentials, per-site DB isolation
- Production-Ready - Provider-agnostic auto-scaling (KEDA/HPA), zero-downtime updates, automated backups
- Multi-Platform - ARM64/AMD64 support
- Enterprise-Grade - Fully compatible with OpenShift
restricted-v2SCCs
- Kubernetes cluster (v1.19+)
kubectlconfiguredhelm(recommended)
# Install via Operator Lifecycle Manager (OLM) / OperatorHub (Recommended)
kubectl create -f https://operatorhub.io/install/frappe-operator.yaml
# Or install with Helm
helm repo add frappe-operator https://vyogotech.github.io/frappe-operator/helm-repo
helm install frappe-operator frappe-operator/frappe-operator \
--namespace frappe-operator-system \
--create-namespace
# Or install with kubectl
kubectl apply -f https://github.com/vyogotech/frappe-operator/releases/latest/download/install.yaml# 1. Create MariaDB instance
kubectl apply -f examples/mariadb-shared-instance.yaml
# 2. Deploy a basic site
kubectl apply -f examples/basic-bench.yaml
kubectl apply -f examples/basic-site.yaml
# 3. Monitor deployment
kubectl get frappebench,frappesite -w
# 4. Get admin password
kubectl get secret basic-site-admin -o jsonpath='{.data.password}' | base64 -d
# 5. Access (local testing)
kubectl port-forward svc/basic-bench-nginx 8080:8080
# Open http://localhost:8080If you have updated the image in your FrappeBench (e.g. pushed a new tag to the registry) and need the operator to re-run the initialization job to pick it up, simply update or increment the frappe.io/site-version annotation on your FrappeSite:
kubectl annotate frappesite basic-site frappe.io/site-version="sha-1db505941e7bbe6c47f79ca805e007e20a638aa2" --overwriteThis signals the operator to delete the old bench-init job and spin up a new one using the updated ImageConfig.
That's it! You now have a running Frappe site.
If you are just testing and want to clean up your cluster, delete your site and bench resources first, then clean up the CRDs and operator resources.
1. Clean up Frappe resources and CRDs:
Bash / Zsh:
kubectl delete CustomResourceDefinition $(kubectl get CustomResourceDefinition | grep -F ".vyogo.tech" | awk '{print $1}')PowerShell:
kubectl get crd | Select-String -SimpleMatch ".vyogo.tech" | ForEach-Object {
($_.ToString().Split()[0])
} | ForEach-Object {
kubectl delete crd $_
}2. Uninstall the Operator itself:
Depending on how you installed the operator, use one of the following methods to remove the controller manager, RBAC, and namespace:
If installed via OLM:
kubectl delete subscription my-frappe-operator -n operators
kubectl delete clusterserviceversion $(kubectl get csv -n operators | grep frappe-operator | awk '{print $1}') -n operatorsIf installed via Helm:
helm uninstall frappe-operator --namespace frappe-operator-system
kubectl delete namespace frappe-operator-systemIf installed via kubectl (install.yaml):
kubectl delete -f https://github.com/vyogotech/frappe-operator/releases/latest/download/install.yamlFor detailed guides, visit vyogotech.github.io/frappe-operator:
- Getting Started - Comprehensive installation guide
- Concepts - Understand benches, sites, and architecture
- Examples - Production-ready deployment patterns
- Operations Guide - Scaling, backups, updates, monitoring
- API Reference - Complete CRD specifications
- Troubleshooting - Common issues and solutions
- Site App Installation - Install specific apps per site
- OpenShift Installation - Step-by-step OpenShift guide
- OpenShift Technical Guide - Deep dive into compatibility & SCCs
- MariaDB Integration Guide - Database isolation & credentials
Check the examples/ directory for ready-to-use configurations:
- basic-bench.yaml - Simple development setup
- basic-site.yaml - Basic site configuration
- site-with-apps.yaml - Site with specific apps installed
- hybrid-bench.yaml - FPM + Git + Image sources
- worker-autoscaling.yaml - KEDA-based autoscaling
- scheduled-sitebackup.yaml - Automated backups
- advanced-pod-config.yaml - Custom labels, geo-tagging, and affinity
- test-keda-bench.yaml - Generated KEDA test manifest
- test-hpa-bench.yaml - Generated HPA test manifest
- And many more...
Note: Test manifests are generated from configuration. See CONFIGURATION.md for customization.
| Resource | Purpose | Documentation |
|---|---|---|
| FrappeBench | Shared infrastructure for sites | API Docs |
| FrappeSite | Individual Frappe site | API Docs |
| SiteBackup | Automated backups | API Docs |
| SiteJob | Run bench commands | API Docs |
Minimum:
- Kubernetes 1.19+
- 2 CPU cores, 4GB RAM
Recommended:
- Kubernetes 1.24+
- MariaDB Operator or external database
- Ingress controller (nginx, Traefik)
- cert-manager for TLS
- Dynamic storage provisioning
- π¬ GitHub Discussions - Ask questions
- π GitHub Issues - Report bugs
- π Documentation - Complete guides
- π Frappe Forum - Frappe community
# Run unit tests
make test
# Run integration tests
make integration-test
# Test autoscaling functionality (configurable)
./test-autoscaling-helm.sh all
# Customize test configuration
cp test-config.conf my-config.conf
./test-autoscaling-helm.sh --config my-config.conf kedaThe project uses a flexible configuration system for testing that eliminates hardcoded values. See CONFIGURATION.md for complete documentation.
We welcome contributions! See CONTRIBUTING.md for guidelines.
Apache License 2.0 - see LICENSE for details.
Built with β€οΈ by Vyogo Technologies
β Star this project if you find it useful!