gitops-playground
Creates a complete GitOps-based operational stack that can be used as an internal developer platform (IDP) on your Kubernetes clusters:
- Deployment: GitOps via Argo CD with a ready-to-use repo structure
- Monitoring: Prometheus and Grafana
- Secrets Management: Vault and External Secrets Operator
- Notifications/Alerts: Grafana and ArgoCD can be predefined with either an external mailserver or MailHog for demo purposes.
- Pipelines: Example applications using Jenkins with the gitops-build-lib and SCM-Manager
- Ingress Controller: ingress
- Certificate Management: cert-manager
- Content Loader: Completely customize what is pushed to Git during installation. This allows for adding your own end-user or IDP apps, creating repos, adding Argo CD tenants, etc.
- Runs on:
- local cluster (try it with only one command),
- in the public cloud,
- and even air-gapped environments.
The gitops-playground is derived from our experiences in consulting, operating our internal developer platform (IDP) at Cloudogu and is used in our GitOps trainings.
TL;DR
You can try the GitOps Playground on a local Kubernetes cluster by running a single command:
https://raw.githubusercontent.com/cloudogu/gitops-playground/main/scripts/init-cluster.sh) \
&& docker run --rm -t --pull=always -u $(id -u) \
-v ~/.config/k3d/kubeconfig-gitops-playground.yaml:/home/.kube/config \
--net=host \
ghcr.io/cloudogu/gitops-playground --yes --argocd --ingress --base-url=http://localhost
# More IDP-features: --mail --monitoring --vault=dev --cert-manager
# More features for developers: --jenkins --registry --content-examples
Note that on some linux distros like debian do not support subdomains of localhost.
There you might have to use --base-url=http://local.gd (see local ingresses).
See the list of applications to get started.
We recommend running this command as an unprivileged user, that is inside the docker group.
Table of contents
- What is the GitOps Playground?
- Installation
- Overview
- Create Cluster
- Apply playground
- Apply via Docker (local cluster)
- Apply via kubectl (remote cluster)
- Configuration
- Overview of all CLI and config options
- Configuration file
- Print all CLI parameters
- Deploy Ingress Controller
- Deploy Ingresses
- Deploy GitOps operators
- Deploy with local Cloudogu Ecosystem
- Deploy with productive Cloudogu Ecosystem and GCR
- Override default images
- Argo CD-Notifications
- Monitoring
- Mail server
- MailHog
- External Mailserver
- Secrets Management
- Certificate Management
- Profiles
- Remove playground
- Running on Windows or Mac
- Mac and Windows WSL
- Windows Docker Desktop
- Stack
- Credentials
- Argo CD
- Why not use argocd-autopilot?
- cluster-resources
- Jenkins
- SCMs
- SCM-Manager
- Gitlab
- Monitoring tools
- Secrets Management Tools
- dev mode
- prod mode
- Example app
- Example Applications
- PetClinic with plain k8s resources
- PetClinic with helm
- 3rd Party app (NGINX) with helm, templated in Jenkins
- 3rd Party app (NGINX) with helm, using Helm dependency mechanism
- Development
- License
- Written Offer
What is the GitOps Playground?
The GitOps Playground provides a reproducible environment for setting up a complete GitOps-based operational stack that can be used as an internal developer platform (IDP) on your Kubernetes clusters. It provides an image for automatically setting up a Kubernetes Cluster including CI-server (Jenkins), source code management (SCM-Manager), Monitoring and Alerting (Prometheus, Grafana, MailHog), Secrets Management (Hashicorp Vault and External Secrets Operator) and of course, Argo CD as GitOps operator.
The playground also deploys a number of example applications.
The GitOps Playground lowers the barriers for operating your application on Kubernetes using GitOps.
It creates a complete GitOps-based operational stack on your Kubernetes clusters.
No need to read lots of books and operator
docs, getting familiar with CLIs, ponder about GitOps Repository folder structures and promotion to different environments, etc.
The GitOps Playground is a pre-configured environment to see GitOps in motion, including more advanced use cases like
notifications, monitoring and secret management.
In addition to creating an operational stack in production, you can run the playground locally, for learning and developing new features.
We aim to be compatible with various environments, we even run in an air-gapped networks.
Installation
There a several options for running the GitOps playground
- on a local k3d cluster Works best on Linux, but is possible on Windows and Mac.
- on a remote k8s cluster
- each with the option
- to use an external Jenkins, SCM-Manager and registry (this can be run in production, e.g. with a Cloudogu Ecosystem) or
- to run everything inside the cluster (for demo only)
The diagrams below show an overview of the playground's architecture and three scenarios for running the playground. For a simpler overview including all optional features such as monitoring and secrets management see intro at the very top.
Note that running Jenkins inside the cluster is meant for demo purposes only. The third graphic shows our production scenario with the Cloudogu EcoSystem (CES). Here better security and build performance is achieved using ephemeral Jenkins build agents spawned in the cloud.
Overview
| Playground on local machine | Production environment with Cloudogu EcoSystem |
|---|---|
Create Cluster
You can apply the GitOps playground to
- a local k3d cluster (see docs or script for more details):
bash <(curl -s \
https://raw.githubusercontent.com/cloudogu/gitops-playground/main/scripts/init-cluster.sh) - a remote k8s cluster on Google Kubernetes Engine (e.g. via Terraform, see our docs),
- or almost any k8s cluster.
Note that if you want to deploy Jenkins inside the cluster, you either need Docker as container runtime or set Jenkins up to run its build on an agent that provides Docker.
For the local cluster, you can avoid hitting DockerHub's rate limiting by using a mirror via the --docker-io-registry-mirror parameter.
For example:
https://raw.githubusercontent.com/cloudogu/gitops-playground/main/scripts/init-cluster.sh) --docker-io-registry-mirror https://mirror.gcr.io
This parameter is passed on the containerd used by k3d.
In addition, the Jobs run by Jenkins are using the host's Docker daemon.
To avoid rate limits there, you might have to configure a mirror there as well.
This can be done in the /etc/docker/daemon.json or in the config of Docker Desktop.
For example:
"registry-mirrors": ["https://mirror.gcr.io"]
}
Apply playground
You can apply the playground to your cluster using our container image ghcr.io/cloudogu/gitops-playground.
On success, the container prints a little intro on how to get started with the GitOps playground.
There are several options for running the container:
- For local k3d cluster, we recommend running the image as a local container via
docker - For remote clusters (e.g. on GKE) you can run the image inside a pod of the target cluster via
kubectl.
All options offer the same parameters, see below.
Apply via Docker (local cluster)
When connecting to k3d it is easiest to apply the playground via a local container in the host network and pass k3d's kubeconfig.
docker pull ghcr.io/cloudogu/gitops-playground
docker run --rm -t -u $(id -u) \
-v ~/.config/k3d/kubeconfig-${CLUSTER_NAME}.yaml:/home/.kube/config \
--net=host \
ghcr.io/cloudogu/gitops-playground # additional parameters go here
Note:
docker pullin advance makes sure you have the newest image, even if you ran this command before.
Of course, you could also specify a specific version of the image.- Using the host network makes it possible to determine
localhostand to use k3d's kubeconfig without altering, as it access the API server via a port bound to localhost. - We run as the local user in order to avoid file permission issues with the
kubeconfig-${CLUSTER_NAME}.yaml. - If you experience issues and want to access the full log files, use the following command while the container is running:
$(docker ps -q --filter ancestor=ghcr.io/cloudogu/gitops-playground) \
bash -c -- 'tail -f -n +1 /tmp/playground-log-*'
Apply via kubectl (remote cluster)
For remote clusters it is easiest to apply the playground via kubectl. You can find info on how to install kubectl here.
# This is needed to install CRDs, etc.
kubectl create serviceaccount gitops-playground-job-executer -n default
kubectl create clusterrolebinding gitops-playground-job-executer \
--clusterrole=cluster-admin \
--serviceaccount=default:gitops-playground-job-executer
# Then start apply the playground with the following command:
# To access services on remote clusters, add either --remote or --ingress --base-url=$yourdomain
kubectl run gitops-playground -i --tty --restart=Never \
--overrides='{ "spec": { "serviceAccount": "gitops-playground-job-executer" } }' \
--image ghcr.io/cloudogu/gitops-playground \
-- --yes --argocd # additional parameters go here.
# If everything succeeded, remove the objects
kubectl delete clusterrolebinding/gitops-playground-job-executer \
sa/gitops-playground-job-executer pods/gitops-playground -n default
In general docker run should work here as well. But GKE, for example, uses gcloud and python in their kubeconfig.
Running inside the cluster avoids these kinds of issues.
Configuration
The following describes how to configure GOP.
You can configure GOP using CLI params, config file and/or config map. Config file and map have the same format and offer a schema file. See here. You can also find a list of all CLI/config options here.
Configuration precedence (highest to lowest):
- Command-line parameters
- Configuration files (
--config-file) - Config maps (
--config-map)
That is, if you pass a param via CLI, for example, it will overwrite the corresponding value in the configuration.
Overview of all CLI and config options
- Application
- Registry
- Jenkins
- SCM
- SCMM
- GITLAB
- Images
- Features
- ArgoCD
- Monitoring
- Secrets
- Ingress
- Cert Manager
- Content
- Multitenant
- SCMM
- GITLAB
Application
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--config-file |
- | '' |
String | Config file path |
--config-map |
- | '' |
String | Config map name |
-d, --debug |
application.debug |
- | Boolean | Enable debug mode |
-x, --trace |
application.trace |
- | Boolean | Enable trace mode |
--output-config-file |
application.outputConfigFile |
false |
Boolean | Output configuration file |
-v, --version |
application.versionInfoRequested |
false |
Boolean | Display version and license info |
-h, --help |
application.usageHelpRequested |
false |
Boolean | Display help message |
--insecure |
application.insecure |
false |
Boolean | Sets insecure-mode in cURL which skips cert validation |
--openshift |
application.openshift |
false |
Boolean | When set, openshift specific resources and configurations are applied |
--username |
application.username |
'admin' |
String | Set initial admin username |
--password |
application.password |
'admin' |
String | Set initial admin passwords |
-y, --yes |
application.yes |
false |
Boolean | Skip confirmation |
--name-prefix |
application.namePrefix |
'' |
String | Set name-prefix for repos, jobs, namespaces |
--destroy |
application.destroy |
false |
Boolean | Unroll playground |
--pod-resources |
application.podResources |
false |
Boolean | Write kubernetes resource requests and limits on each pod |
--git-name |
application.gitName |
'Cloudogu' |
String | Sets git author and committer name used for initial commits |
--git-email |
application.gitEmail |
'hello@cloudogu.com' |
String | Sets git author and committer email used for initial commits |
--base-url |
application.baseUrl |
'' |
String | The external base url (TLD) for all tools |
--url-separator-hyphen |
application.urlSeparatorHyphen |
false |
Boolean | Use hyphens instead of dots to separate application name from base-url |
--mirror-repos |
application.mirrorRepos |
false |
Boolean | Changes the sources of deployed tools so they work in air-gapped environments |
--skip-crds |
application.skipCrds |
false |
Boolean | Skip installation of CRDs |
--namespace-isolation |
application.namespaceIsolation |
false |
Boolean | Configure tools to work with given namespaces only |
--netpols |
application.netpols |
false |
Boolean | Sets Network Policies |
-p, --profile |
application.profile |
'' |
String | Sets a profile for pre-defined parameter |
Registry
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--registry |
registry.active |
false |
Boolean | Installs a simple cluster-local registry for demonstration purposes. Warning: Registry does not provide authentication! |
--internal-registry-port |
registry.internalPort |
30000 |
Integer | Port of registry registry. Ignored when a registry*url params are set |
--registry-url |
registry.url |
'' |
String | The url of your external registry, used for pushing images |
--registry-path |
registry.path |
'' |
String | Optional when registry-url is set |
--registry-username |
registry.username |
'' |
String | Optional when registry-url is set |
--registry-password |
registry.password |
'' |
String | Optional when registry-url is set |
--registry-proxy-url |
registry.proxyUrl |
'' |
String | The url of your proxy-registry. Used in pipelines to authorize pull base images |
--registry-proxy-path |
registry.proxyPath |
'' |
String | Optional when registry-proxy-url is set and the registry is running on a non root web path. |
--registry-proxy-username |
registry.proxyUsername |
'' |
String | Use with registry-proxy-url, added to Jenkins as credentials and created as pull secrets |
--registry-proxy-password |
registry.proxyPassword |
'' |
String | Use with registry-proxy-url, added to Jenkins as credentials and created as pull secrets |
--registry-username-read-only |
registry.readOnlyUsername |
'' |
String | Optional alternative username for registry-url with read-only permissions |
--registry-password-read-only |
registry.readOnlyPassword |
'' |
String | Optional alternative password for registry-url with read-only permissions |
--create-image-pull-secrets |
registry.createImagePullSecrets |
false |
Boolean | Create image pull secrets for registry and proxy-registry for all GOP namespaces |
| - | registry.helm.chart |
'docker-registry' |
String | Name of the Helm chart |
| - | registry.helm.repoURL |
'https://helm.twun.io' |
String | Repository url from which the Helm chart should be obtained |
| - | registry.helm.version |
'2.2.3' |
String | The version of the Helm chart to be installed |
| - | registry.helm.values |
[:] |
Map | Helm values of the chart |
Jenkins
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--jenkins |
jenkins.active |
false |
Boolean | Installs Jenkins as CI server |
--jenkins-skip-restart |
jenkins.skipRestart |
false |
Boolean | Skips restarting Jenkins after plugin installation |
--jenkins-skip-plugins |
jenkins.skipPlugins |
false |
Boolean | Skips plugin installation |
--jenkins-url |
jenkins.url |
'' |
String | The url of your external jenkins |
--jenkins-username |
jenkins.username |
'admin' |
String | Mandatory when jenkins-url is set |
--jenkins-password |
jenkins.password |
'admin' |
String | Mandatory when jenkins-url is set |
--jenkins-metrics-username |
jenkins.metricsUsername |
'metrics' |
String | Mandatory when jenkins-url is set and monitoring enabled |
--jenkins-metrics-password |
jenkins.metricsPassword |
'metrics' |
String | Mandatory when jenkins-url is set and monitoring enabled |
--maven-central-mirror |
jenkins.mavenCentralMirror |
'' |
String | URL for maven mirror, used by applications built in Jenkins |
--jenkins-additional-envs |
jenkins.additionalEnvs |
[:] |
Map | Set additional environments to Jenkins |
| - | jenkins.helm.chart |
'jenkins' |
String | Name of the Helm chart |
| - | jenkins.helm.repoURL |
'https://charts.jenkins.io' |
String | Repository url from which the Helm chart should be obtained |
| - | jenkins.helm.version |
'5.8.43' |
String | The version of the Helm chart to be installed |
| - | jenkins.helm.values |
[:] |
Map | Helm values of the chart |
Scm(Tenant)
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--scm-provider |
scmTenant.scmProviderType |
SCM_MANAGER |
ScmProviderType | Specifies the SCM provider type. Possible values: SCM_MANAGER, GITLAB. |
scmTenant.gitOpsUsername |
'' |
String | The username for the GitOps user. | |
scmTenant.gitlab |
'' |
GitlabTenantConfig | Configuration for GitLab, including URL, username, token, and parent group ID. | |
scmTenant.scmManager |
'' |
ScmManagerTenantConfig | Configuration for SCM Manager, such as internal setup or plugin handling. |
SCMM(Tenant)
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--scmm-skip-restart |
scmm.skipRestart |
false |
Boolean | Skips restarting SCM-Manager after plugin installation |
--scmm-skip-plugins |
scmm.skipPlugins |
false |
Boolean | Skips plugin installation |
--scmm-url |
scmm.url |
'' |
String | The host of your external scm-manager |
--scmm-username |
scmm.username |
'admin' |
String | Mandatory when scmm-url is set |
--scmm-password |
scmm.password |
'admin' |
String | Mandatory when scmm-url is set |
--scm-root-path |
scmm.rootPath |
'repo' |
String | Sets the root path for the Git Repositories |
| - | scmm.helm.chart |
'scm-manager' |
String | Name of the Helm chart |
| - | scmm.helm.repoURL |
'https://packages.scm-manager.org/repository/helm-v2-releases/' |
String | Repository url from which the Helm chart should be obtained |
| - | scmm.helm.version |
'3.10.2' |
String | The version of the Helm chart to be installed |
| - | scmm.helm.values |
[:] |
Map | Helm values of the chart |
Gitlab(Tenant)
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--gitlab-url |
gitlabTenant.url |
'' |
String | Base URL for the GitLab instance. |
--gitlab-username |
gitlabTenant.username |
'oauth2.0' |
String | Defaults to: oauth2.0 when a PAT token is provided. |
--gitlab-token |
gitlabTenant.password |
'' |
String | PAT token for the account. |
--gitlab-group-id |
gitlabTenant.parentGroupId |
'' |
String | The numeric ID for the GitLab Group where repositories and subgroups should be created. |
gitlabTenant.internal |
false |
Boolean | Indicates if GitLab is running in the same Kubernetes cluster. Currently only external URLs are supported. |
Images
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--kubectl-image |
images.kubectl |
"bitnamilegacy/kubectl:1.29" |
String | Sets image for kubectl |
--helm-image |
images.helm |
"ghcr.io/cloudogu/helm:3.16.4-1" |
String | Sets image for helm |
--kubeval-image |
images.kubeval |
"ghcr.io/cloudogu/helm:3.16.4-1" |
String | Sets image for kubeval |
--helmkubeval-image |
images.helmKubeval |
"ghcr.io/cloudogu/helm:3.16.4-1" |
String | Sets image for helmkubeval |
--yamllint-image |
images.yamllint |
"cytopia/yamllint:1.25-0.7" |
String | Sets image for yamllint |
--nginx-image |
images.nginx |
'' |
String | Sets image for nginx |
--petclinic-image |
images.petclinic |
'eclipse-temurin:17-jre-alpine' |
String | Sets image for petclinic |
--maven-image |
images.maven |
'' |
String | Sets image for maven |
ArgoCD
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--argocd |
features.argocd.active |
false |
Boolean | Installs ArgoCD as GitOps CD tool |
--argocd-operator |
features.argocd.operator |
false |
Boolean | Install ArgoCD operator |
--argocd-url |
features.argocd.url |
'' |
String | The url of your external argocd |
--argocd-email-from |
features.argocd.emailFrom |
'argocd@example.org' |
String | Email from address for ArgoCD notifications |
--argocd-email-to-user |
features.argocd.emailToUser |
'app-team@example.org' |
String | Email to address for user notifications |
--argocd-email-to-admin |
features.argocd.emailToAdmin |
'infra@example.org' |
String | Email to address for admin notifications |
--argocd-resource-inclusions-cluster |
features.argocd.resourceInclusionsCluster |
'' |
String | ArgoCD resource inclusions for cluster |
--argocd-namespace |
features.argocd.namespace |
'argocd' |
String | ArgoCD namespace |
| - | features.argocd.env |
- | List | Environment variables for ArgoCD |
| - | features.argocd.values |
- | Map | To override ArgoCD Operator file |
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--mail |
features.mail.mailServer |
false |
Boolean | Installs a dedicated mail server |
--mail-url |
features.mail.mailUrl |
'' |
String | The url of the mail server's frontend |
--smtp-address |
features.mail.smtpAddress |
'' |
String | SMTP server address |
--smtp-port |
features.mail.smtpPort |
null |
Integer | SMTP server port |
--smtp-user |
features.mail.smtpUser |
'' |
String | SMTP username |
--smtp-password |
features.mail.smtpPassword |
'' |
String | SMTP password |
--mail-image |
features.mail.helm.image |
'ghcr.io/cloudogu/mailhog:v1.0.1' |
String | Container image to use for the mail server |
| - | features.mail.helm.chart |
'mailhog' |
String | Name of the Helm chart |
| - | features.mail.helm.repoURL |
'https://codecentric.github.io/helm-charts' |
String | Repository url from which the Helm chart should be obtained |
| - | features.mail.helm.version |
'5.0.1' |
String | The version of the Helm chart to be installed |
| - | features.mail.helm.values |
[:] |
Map | Helm values of the chart |
Monitoring
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--metrics, --monitoring |
features.monitoring.active |
false |
Boolean | Installs monitoring stack (Prometheus, Grafana) |
--grafana-url |
features.monitoring.grafanaUrl |
'' |
String | The url of your external grafana |
--grafana-email-from |
features.monitoring.grafanaEmailFrom |
'grafana@example.org' |
String | Email from address for Grafana notifications |
--grafana-email-to |
features.monitoring.grafanaEmailTo |
'infra@example.org' |
String | Email to address for Grafana notifications |
--grafana-image |
features.monitoring.helm.grafanaImage |
'' |
String | Grafana container image |
--grafana-sidecar-image |
features.monitoring.helm.grafanaSidecarImage |
'' |
String | Grafana sidecar container image |
--prometheus-image |
features.monitoring.helm.prometheusImage |
'' |
String | Prometheus container image |
--prometheus-operator-image |
features.monitoring.helm.prometheusOperatorImage |
'' |
String | Prometheus operator container image |
--prometheus-config-reloader-image |
features.monitoring.helm.prometheusConfigReloaderImage |
'' |
String | Prometheus config reloader container image |
| - | features.monitoring.helm.chart |
'kube-prometheus-stack' |
String | Name of the Helm chart |
| - | features.monitoring.helm.repoURL |
'https://prometheus-community.github.io/helm-charts' |
String | Repository url from which the Helm chart should be obtained |
| - | features.monitoring.helm.version |
'80.2.2' |
String | The version of the Helm chart to be installed |
| - | features.monitoring.helm.values |
[:] |
Map | Helm values of the chart |
Secrets
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--vault |
features.secrets.vault.mode |
- | VaultMode | Install Vault for secrets management |
--vault-url |
features.secrets.vault.url |
'' |
String | The url of your external vault |
--vault-image |
features.secrets.vault.helm.image |
'' |
String | Vault container image |
--external-secrets-image |
features.secrets.externalSecrets.helm.image |
'' |
String | External secrets operator image |
--external-secrets-certcontroller-image |
features.secrets.externalSecrets.helm.certControllerImage |
'' |
String | External secrets cert controller image |
--external-secrets-webhook-image |
features.secrets.externalSecrets.helm.webhookImage |
'' |
String | External secrets webhook image |
| - | features.secrets.vault.helm.chart |
'vault' |
String | Name of the Helm chart |
| - | features.secrets.vault.helm.repoURL |
'https://helm.releases.hashicorp.com' |
String | Repository url from which the Helm chart should be obtained |
| - | features.secrets.vault.helm.version |
'0.25.0' |
String | The version of the Helm chart to be installed |
| - | features.secrets.externalSecrets.helm.chart |
'external-secrets' |
String | Name of the Helm chart |
| - | features.secrets.externalSecrets.helm.repoURL |
'https://charts.external-secrets.io' |
String | Repository url from which the Helm chart should be obtained |
| - | features.secrets.externalSecrets.helm.version |
'0.9.16' |
String | The version of the Helm chart to be installed |
Ingress
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--ingress |
features.ingress.active |
false |
Boolean | Install Ingress controller |
--ingress-image |
features.ingress.helm.image |
'' |
String | Ingress controller image |
| - | features.ingress.helm.chart |
'traefik' |
String | Name of the Helm chart |
| - | features.ingress.helm.repoURL |
'https://traefik.github.io/charts' |
String | Repository url from which the Helm chart should be obtained |
| - | features.ingress.helm.version |
'39.0.0' |
String | The version of the Helm chart to be installed |
| - | features.ingress.helm.values |
[:] |
Map | Helm values of the chart |
Cert Manager
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--cert-manager |
features.certManager.active |
false |
Boolean | Install cert-manager for TLS certificate management |
--cert-manager-image |
features.certManager.helm.image |
'' |
String | Cert-manager controller image |
--cert-manager-webhook-image |
features.certManager.helm.webhookImage |
'' |
String | Cert-manager webhook image |
--cert-manager-cainjector-image |
features.certManager.helm.cainjectorImage |
'' |
String | Cert-manager CA injector image |
--cert-manager-acme-solver-image |
features.certManager.helm.acmeSolverImage |
'' |
String | Cert-manager ACME solver image |
--cert-manager-startup-api-check-image |
features.certManager.helm.startupAPICheckImage |
'' |
String | Cert-manager startup API check image |
| - | features.certManager.helm.chart |
'cert-manager' |
String | Name of the Helm chart |
| - | features.certManager.helm.repoURL |
'https://charts.jetstack.io' |
String | Repository url from which the Helm chart should be obtained |
| - | features.certManager.helm.version |
'1.16.1' |
String | The version of the Helm chart to be installed |
| - | features.certManager.helm.values |
[:] |
Map | Helm values of the chart |
Content
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--content-examples |
content.examples |
false |
Boolean | Deploy example content: source repos, GitOps repos, Jenkins Job, Argo CD apps/project |
| - | content.namespaces |
[] |
List | Additional kubernetes namespaces |
| - | content.repos |
[] |
List | Content repos to push into target environment |
| - | content.variables |
[:] |
Map | Additional variables to use in custom templates |
| - | content.repos[].url |
'' |
String | URL of the content repo. Mandatory for each type |
| - | content.repos[].path |
'.' |
String | Path within the content repo to process |
| - | content.repos[].ref |
'' |
String | Reference for a specific branch, tag, or commit |
| - | content.repos[].targetRef |
'' |
String | Reference for a specific branch or tag in the target repo |
| - | content.repos[].username |
'' |
String | Username to authenticate against content repo |
| - | content.repos[].password |
'' |
String | Password to authenticate against content repo |
| - | content.repos[].templating |
false |
Boolean | When true, template all files ending in .ftl within the repo |
| - | content.repos[].type |
MIRROR |
ContentRepoType | Content repo type (FOLDER_BASED, COPY, MIRROR) |
| - | content.repos[].target |
'' |
String | Target repo for the repository in the form of namespace/name |
| - | content.repos[].overwriteMode |
INIT |
OverwriteMode | How customer repos will be updated (INIT, RESET, UPGRADE) |
| - | content.repos[].createJenkinsJob |
false |
Boolean | If true, creates a Jenkins job |
MultiTenant
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--dedicated-instance |
multiTenant.useDedicatedInstance |
false |
Boolean | Toggles the Dedicated Instances Mode. See docs for more info |
--central-argocd-namespace |
multiTenant.centralArgocdNamespace |
'argocd' |
String | Namespace for the centralized Argocd |
--central-scm-provider |
multiTenant.scmProviderType |
SCM_MANAGER |
ScmProviderType | The SCM provider type. Possible values: SCM_MANAGER, GITLAB |
multiTenant.gitlab |
`` | GitlabCentralConfig | Config for GITLAB | |
multiTenant.scmManager |
`` | ScmManagerCentralConfig | Config for SCM Manager |
Gitlab(Central)
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--central-gitlab-url |
multiTenant.gitlab.url |
'' |
String | URL for external Gitlab |
--central-gitlab-username |
multiTenant.gitlab.username |
'oauth2.0' |
String | Username for GitLab authentication |
--central-gitlab-token |
multiTenant.gitlab.password |
'' |
String | Password for SCM Manager authentication |
--central-gitlab-group-id |
multiTenant.gitlab.parentGroupId |
'' |
String | Main Group for Gitlab where the GOP creates it's groups/repos |
multiTenant.gitlab.internal |
false |
Boolean | SCM is running on the same cluster (only external supported now) |
Scm-Manager(Central)
| CLI | Config | Default | Type | Description |
|---|---|---|---|---|
--central-scmm-internal |
multiTenant.scmManager.internal |
false |
Boolean | SCM for Central Management is running on the same cluster, so k8s internal URLs can be used for access |
--central-scmm-url |
multiTenant.scmManager.url |
'' |
String | URL for the centralized Management Repo |
--central-scmm-username |
multiTenant.scmManager.username |
'' |
String | CENTRAL SCMM USERNAME |
--central-scmm-password |
multiTenant.scmManager.password |
'' |
String | CENTRAL SCMM Password |
--central-scmm-root-path |
multiTenant.scmManager.rootPath |
'repo' |
String | Root path for SCM Manager |
--central-scmm-namespace |
multiTenant.scmManager.namespace |
'scm-manager' |
String | Namespace where to find the Central SCMM |
Configuration file
You can also use a configuration file to specify the parameters (--config-file or --config-map).
That file must be a YAML file.
Note that the config file is not yet a complete replacement for CLI parameters.
You can use --output-config-file to output the current config as set by defaults and CLI parameters.
In addition, For easier validation and auto-completion, we provide a schema file.
For example in Jetbrains IntelliJ IDEA, you can use the schema for autocompletion and validation when you put the following at the beginning of your config file:
If you work with an older version, you can use a specific git commit ID instead of main in the schema URL.
Then use the context assistant to enable coding assistance or fill in all available properties. See here for the full manual.
Apply via Docker
-v ~/.config/k3d/kubeconfig-gitops-playground.yaml:/home/.kube/config \
-v $(pwd)/gitops-playground.yaml:/config/gitops-playground.yaml \
--net=host \
ghcr.io/cloudogu/gitops-playground --yes --argocd --config-file=/config/gitops-playground.yaml
Apply via kubectl
Create the serviceaccount and clusterrolebinding
features:
monitoring:
active: true
# Convention:
# Find the ConfigMap inside the current namespace for the config map
# From the config map, pick the key "config.yaml"
kubectl create configmap gitops-config --from-file=config.yaml
kubectl run gitops-playground -i --tty --restart=Never \
--overrides='{ "spec": { "serviceAccount": "gitops-playground-job-executer" } }' \
--image ghcr.io/cloudogu/gitops-playground \
-- --yes --argocd --config-map=gitops-config
Afterwards, you might want to do a clean up. In addition, you might want to delete the config-map as well.
Print all CLI parameters
You can get a full list of all CLI options like so:
Deploy Ingress Controller
In the default installation the GitOps-Playground comes without an Ingress-Controller.
We use Traefik as default Ingress-Controller.
It can be enabled via the configfile or parameter --ingress.
In order to make use of the ingress controller, it is recommended to use it in conjunction with --base-url, which will create Ingress objects for all components of the GitOps playground.
The ingress controller is based on the helm chart ingress.
Additional parameters from this chart's values.yaml file can be added to the installation through the gitops-playground configuration file.
Example:
ingress:
active: true
helm:
values:
controller:
replicaCount: 4
In this Example we override the default controller.replicaCount (GOP's default is 2).
This config file is merged with precedence over the defaults set by
- the GOP and
- the charts itself.
Deploy Ingresses
It is possible to deploy Ingress objects for all components. You can either
- set a common base url (
--base-url=https://example.com) or - individual URLS:
--argocd-url https://argocd.example.com
--grafana-url https://grafana.example.com
--vault-url https://vault.example.com
--mail-url https://mail.example.com
--petclinic-base-domain petclinic.example.com
--nginx-base-domain nginx.example.com
- or both, where the individual URLs take precedence.
Note:
jenkins-urlandscmm-urlare for external services and do not lead to ingresses, but you can set them via--base-urlfor now.- In order to make use of the
Ingressyou need an ingress controller. If your cluster does not provide one, the Playground can deploy one for you, via the--ingressparameter. - For this to work, you need to set an
*.example.comDNS record to the externalIP of the ingress controller.
Alternatively, hyphen-separated ingresses can be created, like http://argocd-example.com
Subdomains vs hyphen-separated ingresses
- By default, the ingresses are built as subdomains of
--base-url. - You can change this behavior using the parameter
--url-separator-hyphen. - With this, hyphens are used instead of dots to separate application name from base URL.
- Examples:
--base-url=https://xyz.example.org:argocd.xyz.example.org(default)--base-url=https://xyz.example.org:argocd-xyz.example.org(--url-separator-hyphen)
- This is useful when you have a wildcard certificate for the TLD, but use a subdomain as base URL.
Here, browsers accept the validity only for the first level of subdomains.
Local ingresses
The ingresses can also be used when running the playground on your local machine:
- Ingresses might be easier to remember than arbitrary port numbers and look better in demos
- With ingresses, we can execute our local clusters in higher isolation or multiple playgrounds concurrently
- Ingresses are required for running on Windows/Mac.
To use them locally,
- init your cluster (
init-cluster.sh). - apply your playground with the following parameters
--base-url=http://localhost- this is possible on Windows (tested on 11), Mac (tested on Ventura) or when using Linux with systemd-resolved (default in Ubuntu, not Debian)
As an alternative, you could add all*.localhostentries to yourhostsfile.
Usekubectl get ingress -Ato get a full list - Then, you can reach argocd on
http://argocd.localhost, for example
- this is possible on Windows (tested on 11), Mac (tested on Ventura) or when using Linux with systemd-resolved (default in Ubuntu, not Debian)
--base-url=http://local.gd(or127.0.0.1.nip.io,127.0.0.1.sslip.io, or others)- This should work for all other machines that have access to the internet without further config
- Then, you can reach argocd on
http://argocd.local.gd, for example
- Note that when using port 80, the URLs are shorter, but you run into issues because port 80 is regarded as a privileged port.
Java applications seem not to be able to reach
localhost:80or even127.0.0.1:80(NoRouteToHostException) - You can change the port using
init-cluster.sh --bind-ingress-port=8080.
When you do, make sure to append the same port when applying the playground:--base-url=http://localhost:8080 - If your setup requires you to bind to a specific interface, you can just pass it with e.g.
--bind-ingress-port=127.0.0.1:80
Deploy GitOps operators
--argocd- deploy Argo CD GitOps operator
Note that switching between operators is not supported.
That is, expect errors (for example with cluster-resources) if you apply the playground once with Argo CD and the next time without it. We recommend resetting the cluster withinit-cluster.shbeforehand.
Deploy with local Cloudogu Ecosystem
See our Quickstart Guide on how to set up the instance.
Then set the following parameters.
# * In this case --password only sets the Argo CD admin password (Jenkins and
# SCMM are external)
# * Insecure is needed, because the local instance will not have a valid cert
--jenkins-url=https://192.168.56.2/jenkins \
--scmm-url=https://192.168.56.2/scm \
--jenkins-username=admin \
--jenkins-password=yourpassword \
--scmm-username=admin \
--scmm-password=yourpassword \
--password=yourpassword \
--insecure
Deploy with productive Cloudogu Ecosystem and GCR
Using Google Container Registry (GCR) fits well with our cluster creation example via Terraform on Google Kubernetes Engine (GKE), see our docs.
Note that you can get a free CES demo instance set up with a Kubernetes Cluster as GitOps Playground here.
# and SCMM are external)
--jenkins-url=https://your-ecosystem.cloudogu.net/jenkins \
--scmm-url=https://your-ecosystem.cloudogu.net/scm \
--jenkins-username=admin \
--jenkins-password=yourpassword \
--scmm-username=admin \
--scmm-password=yourpassword \
--password=yourpassword \
--registry-url=eu.gcr.io \
--registry-path=yourproject \
--registry-username=_json_key \
--registry-password="$( cat account.json | sed 's/"/\\"/g' )"
Override default images
gitops-build-lib
Images used by the gitops-build-lib are set in the gitopsConfig in each Jenkinsfile of an application like that:
def gitopsConfig = [
...
buildImages : [
helm: 'ghcr.io/cloudogu/helm:3.10.3-1',
kubectl: 'bitnamilegacy/kubectl:1.29',
kubeval: 'ghcr.io/cloudogu/helm:3.10.3-1',
helmKubeval: 'ghcr.io/cloudogu/helm:3.10.3-1',
yamllint: 'cytopia/yamllint:1.25-0.7'
],...