diff --git a/.github/styles/Google/Headings.yml b/.github/styles/Google/Headings.yml index b2b7b397..4ecf49ac 100644 --- a/.github/styles/Google/Headings.yml +++ b/.github/styles/Google/Headings.yml @@ -29,4 +29,6 @@ exceptions: - JSON - vCluster - \bPro\b - - OpenCost \ No newline at end of file + - OpenCost + - Helm + - FIPS \ No newline at end of file diff --git a/.github/styles/Google/WordList.yml b/.github/styles/Google/WordList.yml index a9346f3e..fb09a340 100644 --- a/.github/styles/Google/WordList.yml +++ b/.github/styles/Google/WordList.yml @@ -57,7 +57,6 @@ swap: HTTPs: HTTPS in order to: to ingest: import|load - k8s: Kubernetes long press: touch & hold network IP address: internal IP address omnibox: address bar diff --git a/platform/_partials/install/base-prerequisites.mdx b/platform/_partials/install/base-prerequisites.mdx index 091f39be..80e7d11e 100644 --- a/platform/_partials/install/base-prerequisites.mdx +++ b/platform/_partials/install/base-prerequisites.mdx @@ -6,4 +6,5 @@ Your current kube-context must have administrative privileges, which you can ver To obtain a kube-context with admin access, ensure you have the necessary credentials and permissions for your Kubernetes cluster. This typically involves using `kubectl config` commands or authenticating through your cloud provider's CLI tools. ::: - `helm` installed: Helm v3.10 is required for deploying the platform. Refer to the [Helm Installation Guide](https://Helm.sh/docs/intro/install/) if you need to install it. + - `kubectl` installed: Kubernetes command-line tool for interacting with the cluster. See [Install and Set Up kubectl](https://kubernetes.io/docs/tasks/tools/#kubectl) for installation instructions. diff --git a/vcluster/_partials/deploy/fips-config.mdx b/vcluster/_partials/deploy/fips-config.mdx new file mode 100644 index 00000000..9d43199e --- /dev/null +++ b/vcluster/_partials/deploy/fips-config.mdx @@ -0,0 +1,55 @@ +```yaml title="vcluster.yaml configuration for FIPS compliant environment" +controlPlane: + advanced: + defaultImageRegistry: ghcr.io + virtualScheduler: + enabled: true + backingStore: + etcd: + embedded: + enabled: true + coredns: + embedded: true + distro: + k8s: # FIPS support is only available for the k8s distribution + version: v1.28.14 + enabled: true + apiServer: + image: + repository: loft-sh/kubernetes-fips + controllerManager: + image: + repository: loft-sh/kubernetes-fips + scheduler: + image: + repository: loft-sh/kubernetes-fips + hostPathMapper: + enabled: true + statefulSet: + image: + repository: loft-sh/vcluster-pro-fips + resources: + limits: + cpu: 2 + memory: 4Gi + requests: + cpu: 0 + memory: 0 + scheduling: + podManagementPolicy: OrderedReady +external: + platform: + apiKey: + secretName: license +policies: + limitRange: + enabled: false + podSecurityStandard: privileged + resourceQuota: + enabled: false +pro: true +external: + platform: + apiKey: + secretName: vcluster-platform-api-key +``` diff --git a/vcluster/_partials/deploy/license_key.mdx b/vcluster/_partials/deploy/license_key.mdx new file mode 100644 index 00000000..c1dc65f8 --- /dev/null +++ b/vcluster/_partials/deploy/license_key.mdx @@ -0,0 +1,3 @@ + + +Contact sales@loft.sh to purchase an offline license key or request a trial license key for offline use. diff --git a/vcluster/deploy/topologies/air-gapped.mdx b/vcluster/deploy/topologies/air-gapped.mdx new file mode 100644 index 00000000..5a06544a --- /dev/null +++ b/vcluster/deploy/topologies/air-gapped.mdx @@ -0,0 +1,378 @@ +--- +title: vCluster Pro air-gapped install +sidebar_label: Air-gapped +sidebar_position: 5 +description: Learn how to install vCluster Pro in an air-gapped Kubernetes cluster without the vCluster Platform agent. +sidebar_class_name: pro +--- + +import Tabs from '@theme/Tabs'; +import TabItem from '@theme/TabItem'; +import Flow, { Step } from "@site/src/components/Flow"; +import BasePrerequisites from '../../../platform/_partials/install/base-prerequisites.mdx'; + +import FipsConfig from '../../_partials/deploy/fips-config.mdx'; + +import LicenseKey from '../../_partials/deploy/license_key.mdx'; + +# vCluster Pro air-gapped install + +This document details the prerequisites and steps to install vCluster Pro into +an `air-gapped` Kubernetes cluster without the platform agent running on the host +cluster. + +## Prerequisites + + + - `docker` (check with `docker version`) + - An offline license key for vCluster Pro (provided by Loft) + :::info + + ::: +- Optionally: private docker registry that the installer computer and the +air-gapped Kubernetes cluster can access (e.g. x-private-registry:5000 or +gcr.io/x-team) +
+ Example Local Registry Setup + + ### Local Docker Registry Configuration + + It is easy to setup a private Docker registry for testing purposes using KIND + cluster. The + following steps show how to set up a Docker registry locally: + + **Basic Setup**: +Execute the [setup script](https://kind.sigs.k8s.io/docs/user/local-registry/) from the KIND webpage: + + **Verify & Use**: + ```bash + # Verify registry + curl http://localhost:5001/v2/_catalog + ``` + +
+ +### Download vCluster Helm chart + +Download the `vCluster` Helm chart from the Loft Helm repository. + +:::tip +To retrieve all available versions of the vCluster Helm chart, run the following command: + +```bash title="Show latest 10 vCluster chart versions" +helm repo update +helm search repo loft/vcluster --versions | grep "^loft/vcluster" | head +``` +::: + +```bash title="Download vCluster Helm chart" +export CHART_VERSION="0.21.1" # Replace with the desired version +curl -O https://charts.loft.sh/charts/vcluster-"${CHART_VERSION}".tgz +``` + +:::info +The `vCluster` Helm chart is a tarball that contains all the necessary images +to deploy the vCluster control plane. +::: + +### Download and push required container images + +For clusters unable to pull images from Docker Hub, you need to push the +platform images to your private registry. Each vCluster release includes a +`vcluster-images.txt` file that lists the necessary images. + +:::warning +When using virtual clusters in air-gapped environments, the +`config.experimental.deploy.vcluster.helm` [configuration setting](/docs/vcluster/configure/vcluster-yaml/#experimental-deploy-vcluster) does not work with external Helm repositories since they cannot be accessed. This means custom Helm charts from repositories like `charts.bitnami.com` cannot be used for virtual cluster deployments. +::: + +Follow these instructions to download all vCluster images and import them to your private registry: + + + + +Set environment variables for the setup process: + + ```bash title="Export environment variables" + export VCLUSTER_SERVICE="vcluster" + export VCLUSTER_NAMESPACE="vcluster" + export REGISTRY=ecr.io/myteam # This should be a prefix; do not include any LOFT_IMAGE paths + ``` + + + + Retrieve the vCluster version and set the `VERSION` variable: + ```bash title="Retrieve and set VERSION" + CHART=$(kubectl get service "${VCLUSTER_SERVICE}" -n "${VCLUSTER_NAMESPACE}" -o jsonpath={.metadata.labels.chart}) + export VERSION=${CHART#vcluster-} # Remove 'vcluster-' prefix + ``` + + + Set the `VERSION` variable to the latest vCluster version you want to install: + + + ```bash title="Set VERSION variable for fresh installation" + export VERSION= # e.g., "0.21.1" + ``` + + + + + + + +Download the `vcluster-images.txt` file and the required scripts +`download-images.sh` and `push-images.sh`, then make them executable. + +:::tip +Note that the +`vcluster-images.txt` contains all the distros and versions. You can edit the +file and remove images you do not need. +Each release also has a corresponding `vcluster-images-k8s-[version].txt` file, +use it to download k8s distro images for the desired version. +::: + +```bash title="Download and prepare scripts" +wget https://github.com/loft-sh/vcluster/releases/download/v"${VERSION}"/vcluster-images.txt +wget https://github.com/loft-sh/vcluster/releases/download/v"${VERSION}"/download-images.sh +wget https://github.com/loft-sh/vcluster/releases/download/v"${VERSION}"/push-images.sh + +chmod +x ./download-images.sh +chmod +x ./push-images.sh +``` + + + + +Run `download-images.sh` to download all images locally: + +```bash title="Download images" +./download-images.sh --image-list vcluster-images.txt +``` + +:::tip +This creates a tarball with all the images and push them to your private registry. +::: + + + + +Run `push-images.sh` to push all downloaded images to your private registry: + +```bash title="Push images to private registry" +./push-images.sh --registry ${REGISTRY} +``` + +:::info +vCluster prepends the image registry to all images used by vCluster, such as syncer and Kubernetes. For example, `registry.k8s.io/kube-apiserver:v1.30.2` becomes `my-private-registry:5000/vcluster/kube-apiserver:v1.30.2`. +::: + + + + +## Configure vCluster for air-gapped install + +The `vcluster.yaml` file holds your vCluster configuration and allows overriding the vCluster Helm chart default values. + +Edit your existing `vcluster.yaml` file or create a new one with the following content: + +:::tip +To retrieve supported Kubernetes versions: + +```bash title="Show supported Kubernetes versions" +curl http://"${REGISTRY}"/v2/kube-controller-manager/tags/list +``` + +```bash title="create vcluster.yaml configuration" +export KUBERNETES_VERSION="v1.31.1" # Replace with the desired version +cat < vcluster.yaml +controlPlane: + advanced: + defaultImageRegistry: ${REGISTRY} + distro: + k8s: + version: ${KUBERNETES_VERSION} +EOF +``` + +:::info Example of a fully formed registry path +If your `REGISTRY` is set to `ecr.io/myteam`, a fully formed registry path might look like: +`ecr.io/myteam/ghcr.io/loft-sh/vcluster:0.21.0` +::: + + +:::info Note on alpine image replacement +The `alpine` image may be replaced with any similar image with the following `vcluster.yaml` configuration: + +```yaml title="vcluster.yaml configuration for custom image" +sync: + toHost: + pods: + rewriteHosts: + initContainer: + image: your-registry/your-image:1.0.0 +``` + +The image that is used to replace the default image must be able to run the following command: + +```yaml +Command: []string{"sh"}, +Args: []string{"-c", "sed -E -e 's/^(\\d+.\\d+.\\d+.\\d+\\s+)" + fromHost + "$/\\1 " + toHostnameFQDN + " " + toHostname + "/' /etc/hosts > /hosts/hosts"} +``` +::: + +## Optionally create image pull secret + + The `imagePullSecrets` setting defines extra image pull secrets for the vCluster control plane `ServiceAccount`. + +:::info +This configuration is only necessary if your registry requires +authentication. +::: + +```yaml title="Image Pull Secrets configuration" +controlPlane: + advanced: + serviceAccount: + imagePullSecrets: + - name-of-your-image-pull-secret +``` + +## Configure API key + +The `apiKey` provides a way to deploy vCluster with Pro features without the platform agent installed on the host cluster. + +:::note +Although the config appears similar to when using the platform, the `apiKey` secret's actual value is your air-gapped license key. +::: + +```bash title="API Key configuration" +cat < platform-api-key.yaml +external: + platform: + apiKey: + # The air-gapped license key provided by Loft has to be the data + # under the first key (name does not matter) of the secret. + secretName: + # Namespace to search for the secret. If undefined, + # it searches the namespace that the vCluster is deployed in. + # If different than the namespace of the vCluster deployment, + # then vCluster needs access to that namespace. + namespace: + # Default enabled to create the necessary RBAC roles + # and role bindings in order to find the secret + createRBAC: true +EOF +``` + +## Deploy vCluster Pro + + + +License Setup + +Create a Kubernetes `Secret` from the License Key provided by Loft in the `Namespace` where you are installing the air-gapped vCluster instance: + +```bash title="Create Kubernetes Secret" +# Create license key file +cat < vcluster-pro-air-gapped-license.txt +YOUR_LICENSE_KEY_HERE +EOF + +# Create namespace and secret +kubectl create namespace vcluster-ns +kubectl create secret generic vcluster-platform-api-key -n vcluster-ns \ + --from-file=license-key=./vcluster-pro-air-gapped-license.txt +``` + + + +Configuration File + +At this point, you should have a `vcluster.yaml` file with the necessary +configuration for your air-gapped vCluster Pro installation. It could look +something like this: + +Create a `vcluster.yaml` file (Helm chart values file) based on the configuration examples from above: + +```yaml title="vcluster.yaml configuration" +controlPlane: + advanced: + defaultImageRegistry: my-private-registry:5000/vcluster/ + serviceAccount: + imagePullSecrets: + - name-of-your-image-pull-secret + backingStore: + etcd: + embedded: + enabled: true + coredns: + embedded: true + +external: + platform: + apiKey: + secretName: vcluster-platform-api-key +``` + + + + +Install vCluster Pro + +Use Helm to install the vCluster Pro instance into the `namespace` where you installed the license `secret`: + +```bash title="Install vCluster Pro with Helm" +export VCLUSTER_PRO_NAME="vcluster-pro" +helm upgrade --install "${VCLUSTER_PRO_NAME}" vcluster-${VERSION}.tgz \ + --version ${VERSION} \ + --values vcluster.yaml \ + --namespace vcluster-ns +``` + +:::tip Optionally increase resource limits +If necessary, increase resources limits on the vCluster Pro syncer (control plane `StatefulSet`) pod: + +```bash title="vCluster Pro syncer pod resource requirements" +kubectl patch statefulset my-vcluster -n team-x --type='json' -p='[ + { + "op": "test", + "path": "/spec/template/spec/containers/0/name", + "value": "syncer" + }, + { + "op": "replace", + "path": "/spec/template/spec/containers/0/resources", + "value": { + "requests": { + "memory": "256Mi", + "cpu": "200m", + "ephemeral-storage": "400Mi" + }, + "limits": { + "memory": "2Gi", + "ephemeral-storage": "8Gi" + } + } + } +]' +``` +::: + + + + +## Air-gapped vCluster Pro with FIPS images + +To run vCluster in a FIPS compliant environment, the `vcluster.yaml` needs to be configured to use the Loft GitHub Container Registry with the FIPS compliant images for the syncer (vCluster control plane `StatefulSet`) and the Kubernetes distro images and configured to use the vCluster Pro embedded CoreDNS. + +:::info +Refer to the [FIPS configuration guide](/vcluster/deploy/security/fips) for more details. +::: + +The following is an example `vcluster.yaml` configuration of air-gapped vCluster Pro with FIPS compliant images and assumes you have created a `Secret` named `vcluster-platform-api-key` with the air-gapped license key provided by Loft in the same `Namespace` where you are deploying the vCluster instance + +
+ FIPS configuration + +