{"id":21428084,"url":"https://github.com/redhat-developer-demos/hybrid-cloud","last_synced_at":"2025-07-30T21:33:40.440Z","repository":{"id":41241644,"uuid":"304337748","full_name":"redhat-developer-demos/hybrid-cloud","owner":"redhat-developer-demos","description":"Hybrid Cloud Demo using OpenShift on Multiple Clouds (Public/Private)","archived":false,"fork":false,"pushed_at":"2022-10-13T07:40:29.000Z","size":554,"stargazers_count":79,"open_issues_count":1,"forks_count":54,"subscribers_count":11,"default_branch":"main","last_synced_at":"2025-07-08T06:05:34.761Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/redhat-developer-demos.png","metadata":{"files":{"readme":"README.adoc","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-10-15T13:38:07.000Z","updated_at":"2024-06-06T01:47:13.000Z","dependencies_parsed_at":"2023-01-19T23:47:22.932Z","dependency_job_id":null,"html_url":"https://github.com/redhat-developer-demos/hybrid-cloud","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/redhat-developer-demos/hybrid-cloud","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/redhat-developer-demos%2Fhybrid-cloud","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/redhat-developer-demos%2Fhybrid-cloud/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/redhat-developer-demos%2Fhybrid-cloud/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/redhat-developer-demos%2Fhybrid-cloud/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/redhat-developer-demos","download_url":"https://codeload.github.com/redhat-developer-demos/hybrid-cloud/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/redhat-developer-demos%2Fhybrid-cloud/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":267945189,"owners_count":24170215,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-07-30T02:00:09.044Z","response_time":70,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"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":[],"created_at":"2024-11-22T22:10:19.378Z","updated_at":"2025-07-30T21:33:40.416Z","avatar_url":"https://github.com/redhat-developer-demos.png","language":"Java","funding_links":[],"categories":[],"sub_categories":[],"readme":"= Hybrid Cloud\n\nimage:https://github.com/redhat-developer-demos/hybrid-cloud/workflows/backend/badge.svg[]\nimage:https://github.com/redhat-developer-demos/hybrid-cloud/workflows/frontend/badge.svg[]\n\n*Tested with skupper 1.0.2*\n\n== TL;DR\n\n*Hybrid Cloud demo*: Quarkus backends distributed in different OpenShift clusters installed on public clouds, controlled by link:https://skupper.io/[Skupper] and consumed by a Frontend.\n\nYou find the guide on how to install such clusters inside link:installation/README.adoc[installation] dir.\n\nhttps://youtu.be/Y0g4tQ8Prs0\n\n\n=== Install Skupper\n\n[source, shell-session]\n----\n# Windows\ncurl -fL https://github.com/skupperproject/skupper/releases/download/1.0.2/skupper-cli-1.0.2-windows-amd64.zip\n\nunzip skupper-cli-1.0.2-windows-amd64.zip\n\nmkdir %UserProfile%\\bin\nmove skupper.exe %UserProfile%\\bin\nset PATH=%PATH%;%UserProfile%\\bin\n\n# Linux\ncurl -fL https://github.com/skupperproject/skupper/releases/download/1.0.2/skupper-cli-1.0.2-linux-amd64.tgz | tar -xzf -\nmkdir $HOME/bin\nmv skupper $HOME/bin\nexport PATH=$PATH:$HOME/bin\n\n# MacOs\ncurl -fL https://github.com/skupperproject/skupper/releases/download/1.0.2/skupper-cli-1.0.2-mac-amd64.tgz | tar -xzf -\nmkdir $HOME/bin\nmv skupper $HOME/bin\nexport PATH=$PATH:$HOME/bin\n----\n\n=== Deploy Services\n\nIMPORTANT: If you are using `minikube` as one cluster, run `minikube tunnel` in a new terminal.\n\nAs Kubernetes enables you to have cloud portability, the workload can be deployed on any Kubernetes context.\nDeploy the backend using the following three commands on all clusters and change only `WORKER_CLOUD_ID` value to differentiate between them.  The name of the cloud or the location/geography are useful to illustrate where the work is being conducted/transacted. \n\n[source, shell-session]\n----\nkubectl create namespace hybrid\nkubectl -n hybrid apply -f backend.yml\nkubectl -n hybrid set env deployment/hybrid-cloud-backend WORKER_CLOUD_ID=\"localhost\" # aws, azr, gcp\n----\n\nThe annotation has already been applied in the backend.yml file but if wish to apply it manually, use the following command.\n\n[source, shell-session]\n----\nkubectl annotate service hybrid-cloud-backend skupper.io/proxy=http\n----\n\nDeploy the frontend to your *main* cluster:\n\nThe Kubernetes service is of type `LoadBalancer`.\nIf you are deploying the frontend in your public cluster open `frontend.yml` file and modify Ingress configuration with your host:\n\n[source, yaml]\n----\nspec:\n  rules:\n  - host: \"\"\n----\n\nIn your *main* cluster, deploy the frontend by calling:\n\n[source, shell-session]\n----\nkubectl apply -f frontend.yml\n----\n\nTIP: In case of OpenShift you can run: `oc expose service hybrid-cloud-frontend` after deploying frontend resource, and it is not required to modify the Ingress configuration. But of course, the first approach works as well in OpenShift.\n\nTo find the frontend URL, on OpenShift use the Route\n\n[source, shell-session]\n----\nkubectl get routes | grep frontend\n----\n\nOn vanilla Kubernetes, try the external IP of the Service\n\n[source, shell-session]\n----\n#AWS\nkubectl get service hybrid-cloud-frontend -o jsonpath=\"{.status.loadBalancer.ingress[0].hostname}\"\n\n#Azure, GCP\nkubectl get service hybrid-cloud-frontend -o jsonpath=\"{.status.loadBalancer.ingress[0].ip}\"\n----\n\n\n\nIn your *main* cluster, init `skupper` and create the `connection-token`:\n\n[source, shell-session]\n----\nskupper init --console-auth unsecured # \u003c1\u003e\n\nSkupper is now installed in namespace 'hybrid'.  Use 'skupper status' to get more information.\n\nskupper status\n\nSkupper is installed in namespace '\"hybrid\"'. Status pending...\n----\n\u003c1\u003e This makes anyone be able to access the Skupper UI to visualize the clouds. Fine for demos, not to be used in production.\n\nSee the status of the skupper pods.\nIt takes a bit of time (usually around 2 minutes) until the pods are running:\n\n[source, shell-session]\n----\nkubectl get pods \n\nNAME                                        READY   STATUS    RESTARTS   AGE\nhybrid-cloud-backend-5cbd67d789-mfvbz       1/1     Running   0          3m55s\nhybrid-cloud-frontend-55bdf64c95-gk2tf      1/1     Running   0          3m27s\nskupper-router-dd7dfff55-tklgg              2/2     Running   0          59s\nskupper-service-controller-dc779b7c-5prhc   1/1     Running   0          56s\n----\n\nFinally create a token:\n\n----\nskupper token create token.yaml -t cert\n\nConnection token written to token.yaml\n----\n\nIn *all the other clusters*, use the connection token created in the previous step:\n\n[source, shell-session]\n----\nskupper init\nskupper link create token.yaml\n----\n\nCheck the service status on all clusters\n\n[source, shell-session]\n----\nskupper service status\nServices exposed through Skupper:\n╰─ hybrid-cloud-backend (http port 8080)\n   ╰─ Targets:\n      ╰─ app.kubernetes.io/name=hybrid-cloud-backend,app.kubernetes.io/version=1.0.0 name=hybrid-cloud-backend\n----\n\nCheck the link status on the 2nd/3rd cluster\n\n[source, shell-session]\n----\nskupper link status\nLink link1 is active\n----\n\nThis has been the short-version to get started, continue reading if you want to learn how to build the Docker images, deply them , etc.\n\n\n\n=== Skupper UI\n\nIf you run:\n\n[source, shell-session]\n----\nkubectl get services \n\nNAME                    TYPE           CLUSTER-IP      EXTERNAL-IP                                                              PORT(S)               AGE\nhybrid-cloud-backend    ClusterIP      172.30.157.62   \u003cnone\u003e                                                                   8080/TCP              10m\nhybrid-cloud-frontend   LoadBalancer   172.30.70.80    acf3bee14b0274403a6f02dc062a3784-405180745.eu-west-1.elb.amazonaws.com   8080:32156/TCP        10m\nskupper                 ClusterIP      172.30.128.55   \u003cnone\u003e                                                                   8080/TCP,8081/TCP     7m50s\nskupper-router          ClusterIP      172.30.7.7      \u003cnone\u003e                                                                   55671/TCP,45671/TCP   7m53s\nskupper-router-local    ClusterIP      172.30.8.239    \u003cnone\u003e                                                                   5671/TCP              7m53s                                                               5671/TCP              34m\n----\n\n== Services\n\n=== Backend\n\nIf you want to build, push and deploy the service:\n\n[source, shell-session]\n----\ncd backend\n./mvnw clean package -DskipTests -Dquarkus.kubernetes.deploy=true -Pazure\n----\n\nIf service is already pushed in quay.io, so you can skip the push part:\n\n[source, shell-session]\n----\ncd backend\n\n./mvnw clean package -DskipTests -Pazure -Dquarkus.kubernetes.deploy=true -Dquarkus.container-image.build=false -Dquarkus.container-image.push=false\n---- \n\n=== Frontend\n\nIf you want to build, push and deploy the service:\n\n[source, shell-session]\n----\ncd backend\n./mvnw clean package -DskipTests -Dquarkus.kubernetes.deploy=true -Pazure -Dquarkus.kubernetes.host=\u003cyour_public_host\u003e\n----\n\nIf service is already pushed in quay.io, so you can skip the push part:\n\n[source, shell-session]\n----\ncd backend\n\n./mvnw clean package -DskipTests -Pazr -Dquarkus.kubernetes.deploy=true -Dquarkus.container-image.build=false -Dquarkus.container-image.push=false\n----\n\n=== Cloud Providers\n\nThe next profiles are provided: `-Pazr`, `-Paws`, `-Pgcp` and `-Plocal`, this just sets an environment variable to identify the cluster.\n\n=== Setting up Skupper\n\nMake sure you have a least the `backend` project deployed on 2 different clusters. The `frontend` project can be deployed to just one cluster.\n\nHere, we will make the assumption that we have it deployed in a local cluster *local* and a public cluster *public*.\n\nMake sure to have 2 terminals with separate sessions logged into each of your cluster with the correct namespace context (but within the same folder).\n\n==== Install the Skupper CLI \n\nFollow the instructions provided https://skupper.io/start/index.html#step-1-install-the-skupper-command-line-tool-in-your-environment[here].\n\n==== Skupper setup\n\n. In your *public* terminal session : \n\n```\nskupper init --id public\nskupper connection-token private-to-public.yaml\n```\n\n. In your *local* terminal session : \n\n```\nskupper init --id private\nskupper connect private-to-public.yaml\n```\n\n==== Annotate the services to join to the Virtual Application Network\n\n. In the terminal for the *local* cluster, annotate the hybrid-cloud-backend service:\n\n```\nkubectl annotate service hybrid-cloud-backend skupper.io/proxy=http\n```\n\n. In the terminal for the *public* cluster, annotate the hybrid-cloud-backend service:\n\n```\nkubectl annotate service hybrid-cloud-backend skupper.io/proxy=http\n```\n\nBoth services are now connected, if you scale one to 0 or it gets overloaded it will transparently load-balance to the other cluster.\n\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fredhat-developer-demos%2Fhybrid-cloud","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fredhat-developer-demos%2Fhybrid-cloud","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fredhat-developer-demos%2Fhybrid-cloud/lists"}