{"id":28412791,"url":"https://github.com/halkyonio/java-platform-operator","last_synced_at":"2026-04-18T00:31:09.721Z","repository":{"id":294898657,"uuid":"988413295","full_name":"halkyonio/java-platform-operator","owner":"halkyonio","description":null,"archived":false,"fork":false,"pushed_at":"2025-06-24T14:06:24.000Z","size":213,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":5,"default_branch":"main","last_synced_at":"2025-07-05T18:41:26.759Z","etag":null,"topics":["controller","java","kind","kubernetes","platform","provision"],"latest_commit_sha":null,"homepage":"","language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/halkyonio.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-05-22T14:07:19.000Z","updated_at":"2025-06-24T14:06:28.000Z","dependencies_parsed_at":null,"dependency_job_id":"52411dc7-1706-4c99-9f33-b205845d317a","html_url":"https://github.com/halkyonio/java-platform-operator","commit_stats":null,"previous_names":["halkyonio/java-package-operator","halkyonio/java-platform-operator"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/halkyonio/java-platform-operator","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/halkyonio%2Fjava-platform-operator","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/halkyonio%2Fjava-platform-operator/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/halkyonio%2Fjava-platform-operator/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/halkyonio%2Fjava-platform-operator/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/halkyonio","download_url":"https://codeload.github.com/halkyonio/java-platform-operator/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/halkyonio%2Fjava-platform-operator/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31951220,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-17T17:29:20.459Z","status":"ssl_error","status_checked_at":"2026-04-17T17:28:47.801Z","response_time":62,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["controller","java","kind","kubernetes","platform","provision"],"created_at":"2025-06-03T00:35:49.008Z","updated_at":"2026-04-18T00:31:09.694Z","avatar_url":"https://github.com/halkyonio.png","language":"Java","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Java Platform Kubernetes operator\n\nThe Java Platform Kubernetes operator projects aims to provision a cluster without the pain to have to deal with scripts locally (bash, python, etc), to manage the dependencies or to wait till services, resources (deployment, pod, ...) are up and running.\n\nWith the help of our `Platform Custom Resource`, you can declare using the section `Packages` what you would like to install (ingress, backstage, gitea, argocd, etc) and the `How` is defined part of a simple Pipeline composed of steps able to perform: init, install, uninstall or something post-installation.\n\nThis project is still a WIP and additional features, improvements will come such as:\n\n- Support to mount script(s) to be executed part of pipeline step(s)\n- Implement a simple mechanism to start a container when the previous finished (mounted volume with shared files, etc)\n\n## Rational of this project\n\nWhile several projects already exist to install and sync resources: Argocd, Kro, Crossplane, ... most of them don't support to define easily steps to be executed, before or after a package is installed, rely heavily on user's scripts to define the scenario to be executed when x packages are installed able to verify if pod, deployment, service are ready, if a health check endpoint returns an HTTP 200 response, etc and don't support to declare the dependencies between the packages/applications: https://github.com/argoproj/argo-cd/issues/7437\n\nTODO: To be continued\n\n## How to play with it\n\nInstall locally a Kubernetes cluster running our `Platform controller` using the [Java Kind client](https://github.com/halkyonio/java-kind-client)\n\nCreate next a `Platform` definition [file](resources/examples/platform-ingress-gitea.yml) packaging by example: `ingress` and `gitea`.\nFor that purpose, you will have to create a custom resource file having the following structure:\n\n```yaml\napiVersion: halkyon.io/v1alpha1\nkind: Platform\nmetadata:\n  name: ingress-gitea\n...  \nspec:\n  packages:\n```\nFor each package, you will declare a pipeline including steps: `init` (optional) or `install`. \n\n**Note**: Until now it is mandatory to adopt this naming convention of the steps as the controller is searching about them !\n\nThe step `install` will be used to perform a task which can be declared part of the `script` field or using tools such as: `helm`, `kubectl` configured respectively with the fields: `helm` and `file`. This is what we have done hereafter using the `helm` and `chart` fields\n\n```yaml\napiVersion: halkyon.io/v1alpha1\nkind: Platform\nmetadata:\n  name: ingress-gitea\n...  \nspec:\n  packages:\n    - name: nginx-ingress\n      description: \"nginx-ingress package\"\n      pipeline:\n        steps:\n          - name: install\n            image: dtzar/helm-kubectl\n            helm:\n              chart:\n```\nThe target namespace where the resources should be deployed is defined using the field: `namespace` and `name`. If not specified, they will be deployed under the `default` namespace.\n\n```yaml\napiVersion: halkyon.io/v1alpha1\nkind: Platform\nmetadata:\n  name: ingress-gitea\n...  \nspec:\n  packages:\n    - name: nginx-ingress\n      description: \"nginx-ingress package\"\n      pipeline:\n        steps:\n          - name: install\n            image: dtzar/helm-kubectl\n            namespace:\n              name: ingress\n            helm:\n              chart:\n```\n\nFor helm, you will configure the parameters such as the url of the chart repository (= index.yaml), its version and the name of the chart to be fetched from the repository and to be deployed. The helm values will be defined using the `values` field.\n\n```yaml\napiVersion: halkyon.io/v1alpha1\nkind: Platform\nmetadata:\n  name: ingress-gitea\n  namespace: platform\nspec:\n  version: 0.1.0\n  description: \"A platform example installing the following packages nginx ingress and gitea and exposing the gitea ui at the address https://gitea.localtest.me:8443\"\n  packages:\n    - name: nginx-ingress\n      description: \"nginx-ingress package\"\n      pipeline:\n        steps:\n          - name: install\n            image: dtzar/helm-kubectl\n            namespace:\n              name: ingress\n            helm:\n              chart:\n                repoUrl: https://kubernetes.github.io/ingress-nginx\n                name: ingress-nginx\n                version: 4.12.2\n              values: |\n                controller:\n                  hostPort:\n                    enabled: true\n                  service:\n                    type: NodePort\n                ingress:\n                  enabled: true\n```\n\nWhen it is needed to process to a step before to install a package, we will use the `init` step. Until now, this step content will be used to configure a pod's init container. The `init` step can be used to generate a configMap, a kubernetes resource not packaged part of the manifest or as helm chart template but can also be used to wait till a service, endpoint is ready, healthy as we will do with the package gitea\n\n```yaml\n    - name: gitea\n      description: \"gitea package\"\n      pipeline:\n        steps:\n          - name: init\n            image: dtzar/helm-kubectl\n            namespace:\n              name: default\n            waitCondition:\n              type: service\n              endpoint:\n                name: ingress-nginx-controller-admission\n                port: 443\n              path: /health\n\n          - name: install\n            image: dtzar/helm-kubectl\n            namespace:\n              name: gitea\n            helm:\n              chart:\n                repoUrl: https://dl.gitea.com/charts/\n                name: gitea\n              values: |\n                redis-cluster:\n                  enabled: false\n                postgresql:\n                  enabled: false\n                postgresql-ha:\n                  enabled: false\n                valkey-cluster:\n                  enabled: false\n                persistence:\n                  enabled: false\n                gitea:\n                  admin:\n                    # existingSecret: \u003cNAME_OF_SECRET\u003e\n                    username: \"giteaAdmin\"\n                    password: \"developer\"\n                    email: \"gi@tea.com\"\n                  config:\n                    database:\n                      DB_TYPE: sqlite3\n                    session:\n                      PROVIDER: memory\n                    cache:\n                      ADAPTER: memory\n                    queue:\n                      TYPE: level\n                service:\n                  ssh:\n                    type: NodePort\n                    nodePort: 32222\n                    externalTrafficPolicy: Local\n                ingress:\n                  enabled: true\n                  className: nginx\n                  hosts:\n                    - host: gitea.localtest.me\n                      paths:\n                        - path: /\n                          pathType: Prefix\n```\n\nDeploy now the platform yaml file using the example file: \n```shell\nkubectl apply -f resources/examples/platform-ingress-gitea.yml\n```\n\nCheck the platform resource and status\n```shell\nkubectl get platform/ingress-gitea -n platform\nNAME            AGE\ningress-gitea   25s\n\nkubectl get platform/ingress-gitea -n platform -ojson | jq -r '.status.conditions'\n[\n  {\n    \"message\": \"Deploying the package: nginx-ingress\",\n    \"type\": \"Deploying\"\n  },\n  {\n    \"message\": \"Deploying the package: nginx-ingress\",\n    \"type\": \"Deploying\"\n  },\n  {\n    \"message\": \"Deploying the package: nginx-ingress\",\n    \"type\": \"Deploying\"\n  },\n  {\n    \"message\": \"Deploying the package: gitea\",\n    \"type\": \"Deploying\"\n  },\n  {\n    \"message\": \"Deploying the package: gitea\",\n    \"type\": \"Deploying\"\n  }\n]\n```\n\nWhen done, access the gitea url: `https://gitea.localtest.me:8443` and log on using as username/password: `giteaAdmin` and `developer`\n\n**Note**: To clean up the cluster, simply delete the platform resource file installed\n```shell\nkubectl delete -f resources/examples/platform-ingress-gitea.yml\n```\n\nEnjoy ;-)\n\n## For the developers\n\nBuild the project and publish the image on a registry where you have write access (example: quay.io)\n```shell\nmvn clean package \\\n  -Dquarkus.kubernetes.output-directory=resources/manifests \\\n  -Dquarkus.operator-sdk.crd.output-directory=resources/crds \\\n  -Dquarkus.operator-sdk.crd.generate-all \\\n  -Dquarkus.kubernetes.rbac.service-accounts.package-operator.namespace=platform \\\n  -Dquarkus.container-image.build=true \\\n  -Dquarkus.container-image.push=true \\\n  -Dquarkus.container-image.image=quay.io/halkyonio/java-package-operator:0.1.0-SNAPSHOT\n```\nWhen it is only needed to build/push a new image\n```shell\nmvn clean package -Dquarkus.container-image.build=true \\\n  -Dquarkus.container-image.push=true \\\n  -Dquarkus.container-image.image=quay.io/halkyonio/java-package-operator:0.1.0-SNAPSHOT\n```\nand to regenerate new CRDs\n```shell\nmvn clean package -Dquarkus.operator-sdk.crd.output-directory=resources/crds \\\n  -Dquarkus.operator-sdk.crd.generate-all\n```\n\n## Work in progress\n\nUse the [Glue Operator](https://github.com/java-operator-sdk/kubernetes-glue-operator) to manage using a workflow the `pre-install`, `post-install` and `installation` steps as jobs\n\nInstall Glue on an existing kind cluster\n```shell\nkubectl apply -f https://github.com/java-operator-sdk/kubernetes-glue-operator/releases/latest/download/glues.io.javaoperatorsdk.operator.glue-v1.yml -f https://github.com/java-operator-sdk/kubernetes-glue-operator/releases/latest/download/glueoperators.io.javaoperatorsdk.operator.glue-v1.yml\nkubectl apply -f https://github.com/java-operator-sdk/kubernetes-glue-operator/releases/latest/download/kubernetes.yml\n```\n\nDeploy our CRDs and Custom resource object of a simple workflow\n```shell\nk rollout status deployment kubernetes-glue-operator --timeout=90s\n\nk delete -f resources/examples/glue/simple-platform.yml\nk delete -f resources/examples/glue/crds/platforms.halkyon.io-v1alpha1.yml\nk delete -f resources/examples/glue/crds/platform-operator.yml\n\nk apply -f resources/examples/glue/crds/platforms.halkyon.io-v1alpha1.yml\nk apply -f resources/examples/glue/crds/platform-operator.yml\nk apply -f resources/examples/glue/simple-platform.yml\n\nk logs -lapp.kubernetes.io/name=kubernetes-glue-operator --tail=-1\n```\n\nYou can also as alternative, launch the Main class of the Glue Operator within your IDE or terminal\n```shell\n// io.javaoperatorsdk.operator.glue.Main\ngit clone https://github.com/java-operator-sdk/kubernetes-glue-operator.git; cd kubernetes-glue-operator\n\nexport KUBECONFIG=\u003cPATH_TO_KUBECONFIG\u003e or set -x KUBECONFIG \u003cPATH_TO_KUBECONFIG\u003e\nmvn clean package -DskipTests\njava -jar target/kubernetes-glue-operator-0.10.1-SNAPSHOT-runner.jar\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhalkyonio%2Fjava-platform-operator","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fhalkyonio%2Fjava-platform-operator","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhalkyonio%2Fjava-platform-operator/lists"}