From 94fb62d39e5657a1815f8278e52fd529c47182d8 Mon Sep 17 00:00:00 2001 From: Lukas Krejci Date: Fri, 7 May 2021 14:24:13 +0200 Subject: [PATCH] Implements eclipse/che#19449. Defines a new version of the CheCluster custom resource and implements conversion functions that are going to be used by a conversion webhook (not yet implemented). --- deploy/crds/org_v1_che_crd-v1beta1.yaml | 1870 +++++++++-------- deploy/crds/org_v1_che_crd.yaml | 119 ++ .../che-operator.clusterserviceversion.yaml | 10 +- .../manifests/org_v1_che_crd.yaml | 119 ++ .../che-operator.clusterserviceversion.yaml | 10 +- .../manifests/org_v1_che_crd.yaml | 117 ++ pkg/apis/addtoscheme_org_v1.go | 2 + pkg/apis/org/v1/che_types.go | 1 + pkg/apis/org/v2alpha1/checluster.go | 150 ++ pkg/apis/org/v2alpha1/doc.go | 15 + pkg/apis/org/v2alpha1/register.go | 33 + .../org/v2alpha1/zz_generated.deepcopy.go | 148 ++ pkg/webhooks/checluster/conversion.go | 183 ++ pkg/webhooks/checluster/conversion_test.go | 350 +++ 14 files changed, 2251 insertions(+), 876 deletions(-) create mode 100644 pkg/apis/org/v2alpha1/checluster.go create mode 100644 pkg/apis/org/v2alpha1/doc.go create mode 100644 pkg/apis/org/v2alpha1/register.go create mode 100644 pkg/apis/org/v2alpha1/zz_generated.deepcopy.go create mode 100644 pkg/webhooks/checluster/conversion.go create mode 100644 pkg/webhooks/checluster/conversion_test.go diff --git a/deploy/crds/org_v1_che_crd-v1beta1.yaml b/deploy/crds/org_v1_che_crd-v1beta1.yaml index 72a8d41bea..cae3eb6e01 100644 --- a/deploy/crds/org_v1_che_crd-v1beta1.yaml +++ b/deploy/crds/org_v1_che_crd-v1beta1.yaml @@ -22,878 +22,1008 @@ spec: scope: Namespaced subresources: status: {} - validation: - openAPIV3Schema: - description: The `CheCluster` custom resource allows defining and managing a - Che server installation - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - description: Desired configuration of the Che installation. Based on these - settings, the Operator automatically creates and maintains several ConfigMaps - that will contain the appropriate environment variables the various components - of the Che installation. These generated ConfigMaps must NOT be updated - manually. - properties: - auth: - description: Configuration settings related to the Authentication used - by the Che installation. - properties: - externalIdentityProvider: - description: 'Instructs the Operator on whether or not to deploy - a dedicated Identity Provider (Keycloak or RH SSO instance). Instructs - the Operator on whether to deploy a dedicated Identity Provider - (Keycloak or RH-SSO instance). By default, a dedicated Identity - Provider server is deployed as part of the Che installation. When - `externalIdentityProvider` is `true`, no dedicated identity provider - will be deployed by the Operator and you will need to provide - details about the external identity provider you are about to - use. See also all the other fields starting with: `identityProvider`.' - type: boolean - identityProviderAdminUserName: - description: Overrides the name of the Identity Provider administrator - user. Defaults to `admin`. - type: string - identityProviderClientId: - description: Name of a Identity provider, Keycloak or RH-SSO, `client-id` - that is used for Che. Override this when an external Identity - Provider is in use. See the `externalIdentityProvider` field. - When omitted or left blank, it is set to the value of the `flavour` - field suffixed with `-public`. - type: string - identityProviderContainerResources: - description: Identity provider container custom settings. - properties: - limits: - description: Limits describes the maximum amount of compute - resources allowed. - properties: - cpu: - description: CPU, in cores. (500m = .5 cores) - type: string - memory: - description: Memory, in bytes. (500Gi = 500GiB = 500 * 1024 - * 1024 * 1024) - type: string - type: object - request: - description: Requests describes the minimum amount of compute - resources required. - properties: - cpu: - description: CPU, in cores. (500m = .5 cores) - type: string - memory: - description: Memory, in bytes. (500Gi = 500GiB = 500 * 1024 - * 1024 * 1024) - type: string - type: object - type: object - identityProviderImage: - description: Overrides the container image used in the Identity - Provider, Keycloak or RH-SSO, deployment. This includes the image - tag. Omit it or leave it empty to use the default container image - provided by the Operator. - type: string - identityProviderImagePullPolicy: - description: Overrides the image pull policy used in the Identity - Provider, Keycloak or RH-SSO, deployment. Default value is `Always` - for `nightly` or `latest` images, and `IfNotPresent` in other - cases. - type: string - identityProviderIngress: - description: Ingress custom settings. - properties: - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - identityProviderPassword: - description: Overrides the password of Keycloak administrator user. - Override this when an external Identity Provider is in use. See - the `externalIdentityProvider` field. When omitted or left blank, - it is set to an auto-generated password. - type: string - identityProviderPostgresPassword: - description: Password for a Identity Provider, Keycloak or RH-SSO, - to connect to the database. Override this when an external Identity - Provider is in use. See the `externalIdentityProvider` field. - When omitted or left blank, it is set to an auto-generated password. - type: string - identityProviderPostgresSecret: - description: 'The secret that contains `password` for the Identity - Provider, Keycloak or RH-SSO, to connect to the database. When - the secret is defined, the `identityProviderPostgresPassword` - is ignored. When the value is omitted or left blank, the one of - following scenarios applies: 1. `identityProviderPostgresPassword` - is defined, then it will be used to connect to the database. 2. - `identityProviderPostgresPassword` is not defined, then a new - secret with the name `che-identity-postgres-secret` will be created - with an auto-generated value for `password`.' - type: string - identityProviderRealm: - description: Name of a Identity provider, Keycloak or RH-SSO, realm - that is used for Che. Override this when an external Identity - Provider is in use. See the `externalIdentityProvider` field. - When omitted or left blank, it is set to the value of the `flavour` - field. - type: string - identityProviderRoute: - description: Route custom settings. - properties: - domain: - description: 'Operator uses the domain to generate a hostname - for a route. In a conjunction with labels it creates a route, - which is served by a non-default Ingress controller. The generated - host name will follow this pattern: `-.`.' - type: string - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - identityProviderSecret: - description: 'The secret that contains `user` and `password` for - Identity Provider. When the secret is defined, the `identityProviderAdminUserName` - and `identityProviderPassword` are ignored. When the value is - omitted or left blank, the one of following scenarios applies: - 1. `identityProviderAdminUserName` and `identityProviderPassword` - are defined, then they will be used. 2. `identityProviderAdminUserName` - or `identityProviderPassword` are not defined, then a new secret - with the name `che-identity-secret` will be created with default - value `admin` for `user` and with an auto-generated value for - `password`.' - type: string - identityProviderURL: - description: Public URL of the Identity Provider server (Keycloak - / RH-SSO server). Set this ONLY when a use of an external Identity - Provider is needed. See the `externalIdentityProvider` field. - By default, this will be automatically calculated and set by the - Operator. - type: string - initialOpenShiftOAuthUser: - description: For operating with the OpenShift OAuth authentication, - create a new user account since the kubeadmin can not be used. - If the value is true, then a new OpenShift OAuth user will be - created for the HTPasswd identity provider. If the value is false - and the user has already been created, then it will be removed. - If value is an empty, then do nothing. The user's credentials - are stored in the `openshift-oauth-user-credentials` secret in - 'openshift-config' namespace by Operator. Note that this solution - is Openshift 4 platform-specific. - type: boolean - oAuthClientName: - description: Name of the OpenShift `OAuthClient` resource used to - setup identity federation on the OpenShift side. Auto-generated - when left blank. See also the `OpenShiftoAuth` field. - type: string - oAuthSecret: - description: Name of the secret set in the OpenShift `OAuthClient` - resource used to setup identity federation on the OpenShift side. - Auto-generated when left blank. See also the `OAuthClientName` - field. - type: string - openShiftoAuth: - description: 'Enables the integration of the identity provider (Keycloak - / RHSSO) with OpenShift OAuth. Empty value on OpenShift by default. - This will allow users to directly login with their OpenShift user - through the OpenShift login, and have their workspaces created - under personal OpenShift namespaces. WARNING: the `kubeadmin` - user is NOT supported, and logging through it will NOT allow accessing - the Che Dashboard.' - type: boolean - updateAdminPassword: - description: Forces the default `admin` Che user to update password - on first login. Defaults to `false`. - type: boolean - type: object - database: - description: Configuration settings related to the database used by - the Che installation. - properties: - chePostgresContainerResources: - description: PostgreSQL container custom settings - properties: - limits: - description: Limits describes the maximum amount of compute - resources allowed. - properties: - cpu: - description: CPU, in cores. (500m = .5 cores) - type: string - memory: - description: Memory, in bytes. (500Gi = 500GiB = 500 * 1024 - * 1024 * 1024) - type: string - type: object - request: - description: Requests describes the minimum amount of compute - resources required. - properties: - cpu: - description: CPU, in cores. (500m = .5 cores) - type: string - memory: - description: Memory, in bytes. (500Gi = 500GiB = 500 * 1024 - * 1024 * 1024) - type: string - type: object - type: object - chePostgresDb: - description: PostgreSQL database name that the Che server uses to - connect to the DB. Defaults to `dbche`. - type: string - chePostgresHostName: - description: PostgreSQL Database host name that the Che server uses - to connect to. Defaults is `postgres`. Override this value ONLY - when using an external database. See field `externalDb`. In the - default case it will be automatically set by the Operator. - type: string - chePostgresPassword: - description: PostgreSQL password that the Che server uses to connect - to the DB. When omitted or left blank, it will be set to an automatically - generated value. - type: string - chePostgresPort: - description: PostgreSQL Database port that the Che server uses to - connect to. Defaults to 5432. Override this value ONLY when using - an external database. See field `externalDb`. In the default case - it will be automatically set by the Operator. - type: string - chePostgresSecret: - description: 'The secret that contains PostgreSQL`user` and `password` - that the Che server uses to connect to the DB. When the secret - is defined, the `chePostgresUser` and `chePostgresPassword` are - ignored. When the value is omitted or left blank, the one of following - scenarios applies: 1. `chePostgresUser` and `chePostgresPassword` - are defined, then they will be used to connect to the DB. 2. `chePostgresUser` - or `chePostgresPassword` are not defined, then a new secret with - the name `che-postgres-secret` will be created with default value - of `pgche` for `user` and with an auto-generated value for `password`.' - type: string - chePostgresUser: - description: PostgreSQL user that the Che server uses to connect - to the DB. Defaults to `pgche`. - type: string - externalDb: - description: 'Instructs the Operator on whether to deploy a dedicated - database. By default, a dedicated PostgreSQL database is deployed - as part of the Che installation. When `externalDb` is `true`, - no dedicated database will be deployed by the Operator and you - will need to provide connection details to the external DB you - are about to use. See also all the fields starting with: `chePostgres`.' - type: boolean - postgresImage: - description: Overrides the container image used in the PostgreSQL - database deployment. This includes the image tag. Omit it or leave - it empty to use the default container image provided by the Operator. - type: string - postgresImagePullPolicy: - description: Overrides the image pull policy used in the PostgreSQL - database deployment. Default value is `Always` for `nightly` or - `latest` images, and `IfNotPresent` in other cases. - type: string - type: object - devWorkspace: - description: Dev Workspace operator configuration - properties: - controllerImage: - description: Overrides the container image used in the DevWorkspace - controller deployment. This includes the image tag. Omit it or - leave it empty to use the default container image provided by - the Operator. - type: string - enable: - description: Deploys the DevWorkspace Operator in the cluster. Does - nothing when a matching version of the Operator is already installed. - Fails when a non-matching version of the Operator is already installed. - type: boolean - type: object - imagePuller: - description: Kubernetes Image Puller configuration - properties: - enable: - description: "Install and configure the Community Supported Kubernetes - Image Puller Operator. When set to `true` and no spec is provided, - it will create a default KubernetesImagePuller object to be managed - by the Operator. When set to `false`, the KubernetesImagePuller - object will be deleted, and the Operator will be uninstalled, - regardless of whether a spec is provided. - Note that while this - the Operator and its behavior is community-supported, its payload - may be commercially-supported for pulling commercially-supported - images." - type: boolean - spec: - description: A KubernetesImagePullerSpec to configure the image - puller in the CheCluster - properties: - cachingCPULimit: - type: string - cachingCPURequest: - type: string - cachingIntervalHours: - type: string - cachingMemoryLimit: - type: string - cachingMemoryRequest: - type: string - configMapName: - type: string - daemonsetName: - type: string - deploymentName: - type: string - images: - type: string - nodeSelector: - type: string - type: object - type: object - k8s: - description: Configuration settings specific to Che installations made - on upstream Kubernetes. - properties: - ingressClass: - description: 'Ingress class that will define the which controller - will manage ingresses. Defaults to `nginx`. NB: This drives the - `kubernetes.io/ingress.class` annotation on Che-related ingresses.' - type: string - ingressDomain: - description: 'Global ingress domain for a Kubernetes cluster. This - MUST be explicitly specified: there are no defaults.' - type: string - ingressStrategy: - description: 'Strategy for ingress creation. Options are: `multi-host` - (host is explicitly provided in ingress), `single-host` (host - is provided, path-based rules) and `default-host` (no host is - provided, path-based rules). Defaults to `multi-host` Deprecated - in favor of `serverExposureStrategy` in the `server` section, - which defines this regardless of the cluster type. When both are - defined, the `serverExposureStrategy` option takes precedence.' - type: string - securityContextFsGroup: - description: The FSGroup in which the Che Pod and workspace Pods - containers runs in. Default value is `1724`. - type: string - securityContextRunAsUser: - description: ID of the user the Che Pod and workspace Pods containers - run as. Default value is `1724`. - type: string - singleHostExposureType: - description: When the serverExposureStrategy is set to `single-host`, - the way the server, registries and workspaces are exposed is further - configured by this property. The possible values are `native`, - which means that the server and workspaces are exposed using ingresses - on K8s or `gateway` where the server and workspaces are exposed - using a custom gateway based on link:https://doc.traefik.io/traefik/[Traefik]. - All the endpoints whether backed by the ingress or gateway `route` - always point to the subpaths on the same domain. Defaults to `native`. - type: string - tlsSecretName: - description: Name of a secret that will be used to setup ingress - TLS termination when TLS is enabled. When the field is empty string, - the default cluster certificate will be used. See also the `tlsSupport` - field. - type: string - type: object - metrics: - description: Configuration settings related to the metrics collection - used by the Che installation. - properties: - enable: - description: Enables `metrics` the Che server endpoint. Default - to `true`. - type: boolean - type: object - server: - description: General configuration settings related to the Che server - and the plugin and devfile registries - properties: - airGapContainerRegistryHostname: - description: Optional host name, or URL, to an alternate container - registry to pull images from. This value overrides the container - registry host name defined in all the default container images - involved in a Che deployment. This is particularly useful to install - Che in a restricted environment. - type: string - airGapContainerRegistryOrganization: - description: Optional repository name of an alternate container - registry to pull images from. This value overrides the container - registry organization defined in all the default container images - involved in a Che deployment. This is particularly useful to install - Eclipse Che in a restricted environment. - type: string - allowUserDefinedWorkspaceNamespaces: - description: Defines that a user is allowed to specify a Kubernetes - namespace, or an OpenShift project, which differs from the default. - It's NOT RECOMMENDED to set to `true` without OpenShift OAuth - configured. The OpenShift infrastructure also uses this property. - type: boolean - cheClusterRoles: - description: A comma-separated list of ClusterRoles that will be - assigned to Che ServiceAccount. Be aware that the Che Operator - has to already have all permissions in these ClusterRoles to grant - them. - type: string - cheDebug: - description: Enables the debug mode for Che server. Defaults to - `false`. - type: string - cheFlavor: - description: Specifies a variation of the installation. The options - are `che` for upstream Che installations, or `codeready` for link:https://developers.redhat.com/products/codeready-workspaces/overview[CodeReady - Workspaces] installation. Override the default value only on necessary - occasions. - type: string - cheHost: - description: Public host name of the installed Che server. When - value is omitted, the value it will be automatically set by the - Operator. See the `cheHostTLSSecret` field. - type: string - cheHostTLSSecret: - description: Name of a secret containing certificates to secure - ingress or route for the custom host name of the installed Che - server. See the `cheHost` field. - type: string - cheImage: - description: Overrides the container image used in Che deployment. - This does NOT include the container image tag. Omit it or leave - it empty to use the default container image provided by the Operator. - type: string - cheImagePullPolicy: - description: Overrides the image pull policy used in Che deployment. - Default value is `Always` for `nightly` or `latest` images, and - `IfNotPresent` in other cases. - type: string - cheImageTag: - description: Overrides the tag of the container image used in Che - deployment. Omit it or leave it empty to use the default image - tag provided by the Operator. - type: string - cheLogLevel: - description: 'Log level for the Che server: `INFO` or `DEBUG`. Defaults - to `INFO`.' - type: string - cheServerIngress: - description: The Che server ingress custom settings. - properties: - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - cheServerRoute: - description: The Che server route custom settings. - properties: - domain: - description: 'Operator uses the domain to generate a hostname - for a route. In a conjunction with labels it creates a route, - which is served by a non-default Ingress controller. The generated - host name will follow this pattern: `-.`.' - type: string - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - cheWorkspaceClusterRole: - description: Custom cluster role bound to the user for the Che workspaces. - The default roles are used when omitted or left blank. - type: string - customCheProperties: - additionalProperties: - type: string - description: Map of additional environment variables that will be - applied in the generated `che` ConfigMap to be used by the Che - server, in addition to the values already generated from other - fields of the `CheCluster` custom resource (CR). When `customCheProperties` - contains a property that would be normally generated in `che` - ConfigMap from other CR fields, the value defined in the `customCheProperties` - is used instead. - type: object - dashboardCpuLimit: - description: Overrides the CPU limit used in the dashboard deployment. - In cores. (500m = .5 cores). Default to 500m. - type: string - dashboardCpuRequest: - description: Overrides the CPU request used in the dashboard deployment. - In cores. (500m = .5 cores). Default to 100m. - type: string - dashboardImage: - description: Overrides the container image used in the dashboard - deployment. This includes the image tag. Omit it or leave it empty - to use the default container image provided by the Operator. - type: string - dashboardImagePullPolicy: - description: Overrides the image pull policy used in the dashboard - deployment. Default value is `Always` for `nightly` or `latest` - images, and `IfNotPresent` in other cases. - type: string - dashboardMemoryLimit: - description: Overrides the memory limit used in the dashboard deployment. - Defaults to 256Mi. - type: string - dashboardMemoryRequest: - description: Overrides the memory request used in the dashboard - deployment. Defaults to 16Mi. - type: string - devfileRegistryCpuLimit: - description: Overrides the CPU limit used in the devfile registry - deployment. In cores. (500m = .5 cores). Default to 500m. - type: string - devfileRegistryCpuRequest: - description: Overrides the CPU request used in the devfile registry - deployment. In cores. (500m = .5 cores). Default to 100m. - type: string - devfileRegistryImage: - description: Overrides the container image used in the devfile registry - deployment. This includes the image tag. Omit it or leave it empty - to use the default container image provided by the Operator. - type: string - devfileRegistryIngress: - description: The devfile registry ingress custom settings. - properties: - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - devfileRegistryMemoryLimit: - description: Overrides the memory limit used in the devfile registry - deployment. Defaults to 256Mi. - type: string - devfileRegistryMemoryRequest: - description: Overrides the memory request used in the devfile registry - deployment. Defaults to 16Mi. - type: string - devfileRegistryPullPolicy: - description: Overrides the image pull policy used in the devfile - registry deployment. Default value is `Always` for `nightly` or - `latest` images, and `IfNotPresent` in other cases. - type: string - devfileRegistryRoute: - description: The devfile registry route custom settings. - properties: - domain: - description: 'Operator uses the domain to generate a hostname - for a route. In a conjunction with labels it creates a route, - which is served by a non-default Ingress controller. The generated - host name will follow this pattern: `-.`.' - type: string - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - devfileRegistryUrl: - description: Public URL of the devfile registry, that serves sample, - ready-to-use devfiles. Set this ONLY when a use of an external - devfile registry is needed. See the `externalDevfileRegistry` - field. By default, this will be automatically calculated by the - Operator. - type: string - externalDevfileRegistry: - description: Instructs the Operator on whether to deploy a dedicated - devfile registry server. By default, a dedicated devfile registry - server is started. When `externalDevfileRegistry` is `true`, no - such dedicated server will be started by the Operator and you - will have to manually set the `devfileRegistryUrl` field - type: boolean - externalPluginRegistry: - description: Instructs the Operator on whether to deploy a dedicated - plugin registry server. By default, a dedicated plugin registry - server is started. When `externalPluginRegistry` is `true`, no - such dedicated server will be started by the Operator and you - will have to manually set the `pluginRegistryUrl` field. - type: boolean - gitSelfSignedCert: - description: When enabled, the certificate from `che-git-self-signed-cert` - ConfigMap will be propagated to the Che components and provide - particular configuration for Git. - type: boolean - nonProxyHosts: - description: 'List of hosts that will be reached directly, bypassing - the proxy. Specify wild card domain use the following form `.` - and `|` as delimiter, for example: `localhost|.my.host.com|123.42.12.32` - Only use when configuring a proxy is required. Operator respects - OpenShift cluster wide proxy configuration and no additional configuration - is required, but defining `nonProxyHosts` in a custom resource - leads to merging non proxy hosts lists from the cluster proxy - configuration and ones defined in the custom resources. See the - doc https://docs.openshift.com/container-platform/4.4/networking/enable-cluster-wide-proxy.html. - See also the `proxyURL` fields.' - type: string - pluginRegistryCpuLimit: - description: Overrides the CPU limit used in the plugin registry - deployment. In cores. (500m = .5 cores). Default to 500m. - type: string - pluginRegistryCpuRequest: - description: Overrides the CPU request used in the plugin registry - deployment. In cores. (500m = .5 cores). Default to 100m. - type: string - pluginRegistryImage: - description: Overrides the container image used in the plugin registry - deployment. This includes the image tag. Omit it or leave it empty - to use the default container image provided by the Operator. - type: string - pluginRegistryIngress: - description: Plugin registry ingress custom settings. - properties: - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - pluginRegistryMemoryLimit: - description: Overrides the memory limit used in the plugin registry - deployment. Defaults to 256Mi. - type: string - pluginRegistryMemoryRequest: - description: Overrides the memory request used in the plugin registry - deployment. Defaults to 16Mi. - type: string - pluginRegistryPullPolicy: - description: Overrides the image pull policy used in the plugin - registry deployment. Default value is `Always` for `nightly` or - `latest` images, and `IfNotPresent` in other cases. - type: string - pluginRegistryRoute: - description: Plugin registry route custom settings. - properties: - domain: - description: 'Operator uses the domain to generate a hostname - for a route. In a conjunction with labels it creates a route, - which is served by a non-default Ingress controller. The generated - host name will follow this pattern: `-.`.' - type: string - labels: - description: Comma separated list of labels that can be used - to organize and categorize objects by scoping and selecting. - type: string - type: object - pluginRegistryUrl: - description: Public URL of the plugin registry that serves sample - ready-to-use devfiles. Set this ONLY when a use of an external - devfile registry is needed. See the `externalPluginRegistry` field. - By default, this will be automatically calculated by the Operator. - type: string - proxyPassword: - description: Password of the proxy server. Only use when proxy configuration - is required. See the `proxyURL`, `proxyUser` and `proxySecret` - fields. - type: string - proxyPort: - description: Port of the proxy server. Only use when configuring - a proxy is required. See also the `proxyURL` and `nonProxyHosts` - fields. - type: string - proxySecret: - description: The secret that contains `user` and `password` for - a proxy server. When the secret is defined, the `proxyUser` and - `proxyPassword` are ignored. - type: string - proxyURL: - description: URL (protocol+host name) of the proxy server. This - drives the appropriate changes in the `JAVA_OPTS` and `https(s)_proxy` - variables in the Che server and workspaces containers. Only use - when configuring a proxy is required. Operator respects OpenShift - cluster wide proxy configuration and no additional configuration - is required, but defining `proxyUrl` in a custom resource leads - to overrides the cluster proxy configuration with fields `proxyUrl`, - `proxyPort`, `proxyUser` and `proxyPassword` from the custom resource. - See the doc https://docs.openshift.com/container-platform/4.4/networking/enable-cluster-wide-proxy.html. - See also the `proxyPort` and `nonProxyHosts` fields. - type: string - proxyUser: - description: User name of the proxy server. Only use when configuring - a proxy is required. See also the `proxyURL`, `proxyPassword` - and `proxySecret` fields. - type: string - selfSignedCert: - description: Deprecated. The value of this flag is ignored. The - Che Operator will automatically detect whether the router certificate - is self-signed and propagate it to other components, such as the - Che server. - type: boolean - serverCpuLimit: - description: Overrides the CPU limit used in the Che server deployment - In cores. (500m = .5 cores). Default to 1. - type: string - serverCpuRequest: - description: Overrides the CPU request used in the Che server deployment - In cores. (500m = .5 cores). Default to 100m. - type: string - serverExposureStrategy: - description: Sets the server and workspaces exposure type. Possible - values are `multi-host`, `single-host`, `default-host`. Defaults - to `multi-host`, which creates a separate ingress, or OpenShift - routes, for every required endpoint. `single-host` makes Che exposed - on a single host name with workspaces exposed on subpaths. Read - the docs to learn about the limitations of this approach. Also - consult the `singleHostExposureType` property to further configure - how the Operator and the Che server make that happen on Kubernetes. - `default-host` exposes the Che server on the host of the cluster. - Read the docs to learn about the limitations of this approach. - type: string - serverMemoryLimit: - description: Overrides the memory limit used in the Che server deployment. - Defaults to 1Gi. - type: string - serverMemoryRequest: - description: Overrides the memory request used in the Che server - deployment. Defaults to 512Mi. - type: string - serverTrustStoreConfigMapName: - description: Name of the ConfigMap with public certificates to add - to Java trust store of the Che server. This is often required - when adding the OpenShift OAuth provider, which has HTTPS endpoint - signed with self-signed cert. The Che server must be aware of - its CA cert to be able to request it. This is disabled by default. - type: string - singleHostGatewayConfigMapLabels: - additionalProperties: - type: string - description: The labels that need to be present in the ConfigMaps - representing the gateway configuration. - type: object - singleHostGatewayConfigSidecarImage: - description: The image used for the gateway sidecar that provides - configuration to the gateway. Omit it or leave it empty to use - the default container image provided by the Operator. - type: string - singleHostGatewayImage: - description: The image used for the gateway in the single host mode. - Omit it or leave it empty to use the default container image provided - by the Operator. - type: string - tlsSupport: - description: Deprecated. Instructs the Operator to deploy Che in - TLS mode. This is enabled by default. Disabling TLS sometimes - cause malfunction of some Che components. - type: boolean - useInternalClusterSVCNames: - description: Use internal cluster SVC names to communicate between - components to speed up the traffic and avoid proxy issues. The - default value is `true`. - type: boolean - workspaceNamespaceDefault: - description: Defines Kubernetes default namespace in which user's - workspaces are created for a case when a user does not override - it. It's possible to use ``, `` and `` - placeholders, such as che-workspace-. In that case, - a new namespace will be created for each user or workspace. - type: string - type: object - storage: - description: Configuration settings related to the persistent storage - used by the Che installation. - properties: - postgresPVCStorageClassName: - description: Storage class for the Persistent Volume Claim dedicated - to the PostgreSQL database. When omitted or left blank, a default - storage class is used. - type: string - preCreateSubPaths: - description: Instructs the Che server to start a special Pod to - pre-create a sub-path in the Persistent Volumes. Defaults to `false`, - however it will need to enable it according to the configuration - of your Kubernetes cluster. - type: boolean - pvcClaimSize: - description: Size of the persistent volume claim for workspaces. - Defaults to `1Gi`. - type: string - pvcJobsImage: - description: Overrides the container image used to create sub-paths - in the Persistent Volumes. This includes the image tag. Omit it - or leave it empty to use the default container image provided - by the Operator. See also the `preCreateSubPaths` field. - type: string - pvcStrategy: - description: Persistent volume claim strategy for the Che server. - This Can be:`common` (all workspaces PVCs in one volume), `per-workspace` - (one PVC per workspace for all declared volumes) and `unique` - (one PVC per declared volume). Defaults to `common`. - type: string - workspacePVCStorageClassName: - description: Storage class for the Persistent Volume Claims dedicated - to the Che workspaces. When omitted or left blank, a default storage - class is used. - type: string - type: object - type: object - status: - description: CheClusterStatus defines the observed state of Che installation - properties: - cheClusterRunning: - description: Status of a Che installation. Can be `Available`, `Unavailable`, - or `Available, Rolling Update in Progress`. - type: string - cheURL: - description: Public URL to the Che server. - type: string - cheVersion: - description: Current installed Che version. - type: string - dbProvisioned: - description: Indicates that a PostgreSQL instance has been correctly - provisioned or not. - type: boolean - devfileRegistryURL: - description: Public URL to the devfile registry. - type: string - gitHubOAuthProvisioned: - description: Indicates whether an Identity Provider instance, Keycloak - or RH-SSO, has been configured to integrate with the GitHub OAuth. - type: boolean - helpLink: - description: A URL that points to some URL where to find help related - to the current Operator status. - type: string - keycloakProvisioned: - description: Indicates whether an Identity Provider instance, Keycloak - or RH-SSO, has been provisioned with realm, client and user. - type: boolean - keycloakURL: - description: Public URL to the Identity Provider server, Keycloak or - RH-SSO,. - type: string - message: - description: A human readable message indicating details about why the - Pod is in this condition. - type: string - openShiftOAuthUserCredentialsSecret: - description: OpenShift OAuth secret in `openshift-config` namespace - that contains user credentials for HTPasswd identity provider. - type: string - openShiftoAuthProvisioned: - description: Indicates whether an Identity Provider instance, Keycloak - or RH-SSO, has been configured to integrate with the OpenShift OAuth. - type: boolean - pluginRegistryURL: - description: Public URL to the plugin registry. - type: string - reason: - description: A brief CamelCase message indicating details about why - the Pod is in this state. - type: string - type: object - type: object version: v1 versions: - name: v1 + schema: + openAPIV3Schema: + description: The `CheCluster` custom resource allows defining and managing + a Che server installation + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation + of an object. Servers should convert recognized schemas to the latest + internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource this + object represents. Servers may infer this from the endpoint the client + submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + description: Desired configuration of the Che installation. Based on these + settings, the Operator automatically creates and maintains several + ConfigMaps that will contain the appropriate environment variables the + various components of the Che installation. These generated ConfigMaps + must NOT be updated manually. + properties: + auth: + description: Configuration settings related to the Authentication + used by the Che installation. + properties: + externalIdentityProvider: + description: 'Instructs the Operator on whether or not to deploy + a dedicated Identity Provider (Keycloak or RH SSO instance). + Instructs the Operator on whether to deploy a dedicated Identity + Provider (Keycloak or RH-SSO instance). By default, a dedicated + Identity Provider server is deployed as part of the Che installation. + When `externalIdentityProvider` is `true`, no dedicated identity + provider will be deployed by the Operator and you will need + to provide details about the external identity provider you + are about to use. See also all the other fields starting with: + `identityProvider`.' + type: boolean + identityProviderAdminUserName: + description: Overrides the name of the Identity Provider administrator + user. Defaults to `admin`. + type: string + identityProviderClientId: + description: Name of a Identity provider, Keycloak or RH-SSO, + `client-id` that is used for Che. Override this when an external + Identity Provider is in use. See the `externalIdentityProvider` + field. When omitted or left blank, it is set to the value of + the `flavour` field suffixed with `-public`. + type: string + identityProviderContainerResources: + description: Identity provider container custom settings. + properties: + limits: + description: Limits describes the maximum amount of compute + resources allowed. + properties: + cpu: + description: CPU, in cores. (500m = .5 cores) + type: string + memory: + description: Memory, in bytes. (500Gi = 500GiB = 500 * + 1024 * 1024 * 1024) + type: string + type: object + request: + description: Requests describes the minimum amount of compute + resources required. + properties: + cpu: + description: CPU, in cores. (500m = .5 cores) + type: string + memory: + description: Memory, in bytes. (500Gi = 500GiB = 500 * + 1024 * 1024 * 1024) + type: string + type: object + type: object + identityProviderImage: + description: Overrides the container image used in the Identity + Provider, Keycloak or RH-SSO, deployment. This includes the + image tag. Omit it or leave it empty to use the default container + image provided by the Operator. + type: string + identityProviderImagePullPolicy: + description: Overrides the image pull policy used in the Identity + Provider, Keycloak or RH-SSO, deployment. Default value is `Always` + for `nightly` or `latest` images, and `IfNotPresent` in other + cases. + type: string + identityProviderIngress: + description: Ingress custom settings. + properties: + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + identityProviderPassword: + description: Overrides the password of Keycloak administrator + user. Override this when an external Identity Provider is in + use. See the `externalIdentityProvider` field. When omitted + or left blank, it is set to an auto-generated password. + type: string + identityProviderPostgresPassword: + description: Password for a Identity Provider, Keycloak or RH-SSO, + to connect to the database. Override this when an external Identity + Provider is in use. See the `externalIdentityProvider` field. + When omitted or left blank, it is set to an auto-generated password. + type: string + identityProviderPostgresSecret: + description: 'The secret that contains `password` for the Identity + Provider, Keycloak or RH-SSO, to connect to the database. When + the secret is defined, the `identityProviderPostgresPassword` + is ignored. When the value is omitted or left blank, the one + of following scenarios applies: 1. `identityProviderPostgresPassword` + is defined, then it will be used to connect to the database. + 2. `identityProviderPostgresPassword` is not defined, then a + new secret with the name `che-identity-postgres-secret` will + be created with an auto-generated value for `password`.' + type: string + identityProviderRealm: + description: Name of a Identity provider, Keycloak or RH-SSO, + realm that is used for Che. Override this when an external Identity + Provider is in use. See the `externalIdentityProvider` field. + When omitted or left blank, it is set to the value of the `flavour` + field. + type: string + identityProviderRoute: + description: Route custom settings. + properties: + domain: + description: 'Operator uses the domain to generate a hostname + for a route. In a conjunction with labels it creates a route, + which is served by a non-default Ingress controller. The + generated host name will follow this pattern: `-.`.' + type: string + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + identityProviderSecret: + description: 'The secret that contains `user` and `password` for + Identity Provider. When the secret is defined, the `identityProviderAdminUserName` + and `identityProviderPassword` are ignored. When the value is + omitted or left blank, the one of following scenarios applies: + 1. `identityProviderAdminUserName` and `identityProviderPassword` + are defined, then they will be used. 2. `identityProviderAdminUserName` + or `identityProviderPassword` are not defined, then a new secret + with the name `che-identity-secret` will be created with default + value `admin` for `user` and with an auto-generated value for + `password`.' + type: string + identityProviderURL: + description: Public URL of the Identity Provider server (Keycloak + / RH-SSO server). Set this ONLY when a use of an external Identity + Provider is needed. See the `externalIdentityProvider` field. + By default, this will be automatically calculated and set by + the Operator. + type: string + initialOpenShiftOAuthUser: + description: For operating with the OpenShift OAuth authentication, + create a new user account since the kubeadmin can not be used. + If the value is true, then a new OpenShift OAuth user will be + created for the HTPasswd identity provider. If the value is + false and the user has already been created, then it will be + removed. If value is an empty, then do nothing. The user's credentials + are stored in the `openshift-oauth-user-credentials` secret + in 'openshift-config' namespace by Operator. Note that this + solution is Openshift 4 platform-specific. + type: boolean + oAuthClientName: + description: Name of the OpenShift `OAuthClient` resource used + to setup identity federation on the OpenShift side. Auto-generated + when left blank. See also the `OpenShiftoAuth` field. + type: string + oAuthSecret: + description: Name of the secret set in the OpenShift `OAuthClient` + resource used to setup identity federation on the OpenShift + side. Auto-generated when left blank. See also the `OAuthClientName` + field. + type: string + openShiftoAuth: + description: 'Enables the integration of the identity provider + (Keycloak / RHSSO) with OpenShift OAuth. Empty value on OpenShift + by default. This will allow users to directly login with their + OpenShift user through the OpenShift login, and have their workspaces + created under personal OpenShift namespaces. WARNING: the `kubeadmin` + user is NOT supported, and logging through it will NOT allow + accessing the Che Dashboard.' + type: boolean + updateAdminPassword: + description: Forces the default `admin` Che user to update password + on first login. Defaults to `false`. + type: boolean + type: object + database: + description: Configuration settings related to the database used by + the Che installation. + properties: + chePostgresContainerResources: + description: PostgreSQL container custom settings + properties: + limits: + description: Limits describes the maximum amount of compute + resources allowed. + properties: + cpu: + description: CPU, in cores. (500m = .5 cores) + type: string + memory: + description: Memory, in bytes. (500Gi = 500GiB = 500 * + 1024 * 1024 * 1024) + type: string + type: object + request: + description: Requests describes the minimum amount of compute + resources required. + properties: + cpu: + description: CPU, in cores. (500m = .5 cores) + type: string + memory: + description: Memory, in bytes. (500Gi = 500GiB = 500 * + 1024 * 1024 * 1024) + type: string + type: object + type: object + chePostgresDb: + description: PostgreSQL database name that the Che server uses + to connect to the DB. Defaults to `dbche`. + type: string + chePostgresHostName: + description: PostgreSQL Database host name that the Che server + uses to connect to. Defaults is `postgres`. Override this value + ONLY when using an external database. See field `externalDb`. + In the default case it will be automatically set by the Operator. + type: string + chePostgresPassword: + description: PostgreSQL password that the Che server uses to connect + to the DB. When omitted or left blank, it will be set to an + automatically generated value. + type: string + chePostgresPort: + description: PostgreSQL Database port that the Che server uses + to connect to. Defaults to 5432. Override this value ONLY when + using an external database. See field `externalDb`. In the default + case it will be automatically set by the Operator. + type: string + chePostgresSecret: + description: 'The secret that contains PostgreSQL`user` and `password` + that the Che server uses to connect to the DB. When the secret + is defined, the `chePostgresUser` and `chePostgresPassword` + are ignored. When the value is omitted or left blank, the one + of following scenarios applies: 1. `chePostgresUser` and `chePostgresPassword` + are defined, then they will be used to connect to the DB. 2. + `chePostgresUser` or `chePostgresPassword` are not defined, + then a new secret with the name `che-postgres-secret` will be + created with default value of `pgche` for `user` and with an + auto-generated value for `password`.' + type: string + chePostgresUser: + description: PostgreSQL user that the Che server uses to connect + to the DB. Defaults to `pgche`. + type: string + externalDb: + description: 'Instructs the Operator on whether to deploy a dedicated + database. By default, a dedicated PostgreSQL database is deployed + as part of the Che installation. When `externalDb` is `true`, + no dedicated database will be deployed by the Operator and you + will need to provide connection details to the external DB you + are about to use. See also all the fields starting with: `chePostgres`.' + type: boolean + postgresImage: + description: Overrides the container image used in the PostgreSQL + database deployment. This includes the image tag. Omit it or + leave it empty to use the default container image provided by + the Operator. + type: string + postgresImagePullPolicy: + description: Overrides the image pull policy used in the PostgreSQL + database deployment. Default value is `Always` for `nightly` + or `latest` images, and `IfNotPresent` in other cases. + type: string + type: object + devWorkspace: + description: Dev Workspace operator configuration + properties: + controllerImage: + description: Overrides the container image used in the DevWorkspace + controller deployment. This includes the image tag. Omit it + or leave it empty to use the default container image provided + by the Operator. + type: string + enable: + description: Deploys the DevWorkspace Operator in the cluster. + Does nothing when a matching version of the Operator is already + installed. Fails when a non-matching version of the Operator + is already installed. + type: boolean + type: object + imagePuller: + description: Kubernetes Image Puller configuration + properties: + enable: + description: "Install and configure the Community Supported Kubernetes + Image Puller Operator. When set to `true` and no spec is provided, + it will create a default KubernetesImagePuller object to be + managed by the Operator. When set to `false`, the KubernetesImagePuller + object will be deleted, and the Operator will be uninstalled, + regardless of whether a spec is provided. + Note that while + this the Operator and its behavior is community-supported, its + payload may be commercially-supported for pulling commercially-supported + images." + type: boolean + spec: + description: A KubernetesImagePullerSpec to configure the image + puller in the CheCluster + properties: + cachingCPULimit: + type: string + cachingCPURequest: + type: string + cachingIntervalHours: + type: string + cachingMemoryLimit: + type: string + cachingMemoryRequest: + type: string + configMapName: + type: string + daemonsetName: + type: string + deploymentName: + type: string + images: + type: string + nodeSelector: + type: string + type: object + type: object + k8s: + description: Configuration settings specific to Che installations + made on upstream Kubernetes. + properties: + ingressClass: + description: 'Ingress class that will define the which controller + will manage ingresses. Defaults to `nginx`. NB: This drives + the `kubernetes.io/ingress.class` annotation on Che-related + ingresses.' + type: string + ingressDomain: + description: 'Global ingress domain for a Kubernetes cluster. + This MUST be explicitly specified: there are no defaults.' + type: string + ingressStrategy: + description: 'Strategy for ingress creation. Options are: `multi-host` + (host is explicitly provided in ingress), `single-host` (host + is provided, path-based rules) and `default-host` (no host is + provided, path-based rules). Defaults to `multi-host` Deprecated + in favor of `serverExposureStrategy` in the `server` section, + which defines this regardless of the cluster type. When both + are defined, the `serverExposureStrategy` option takes precedence.' + type: string + securityContextFsGroup: + description: The FSGroup in which the Che Pod and workspace Pods + containers runs in. Default value is `1724`. + type: string + securityContextRunAsUser: + description: ID of the user the Che Pod and workspace Pods containers + run as. Default value is `1724`. + type: string + singleHostExposureType: + description: When the serverExposureStrategy is set to `single-host`, + the way the server, registries and workspaces are exposed is + further configured by this property. The possible values are + `native`, which means that the server and workspaces are exposed + using ingresses on K8s or `gateway` where the server and workspaces + are exposed using a custom gateway based on link:https://doc.traefik.io/traefik/[Traefik]. + All the endpoints whether backed by the ingress or gateway `route` + always point to the subpaths on the same domain. Defaults to + `native`. + type: string + tlsSecretName: + description: Name of a secret that will be used to setup ingress + TLS termination when TLS is enabled. When the field is empty + string, the default cluster certificate will be used. See also + the `tlsSupport` field. + type: string + type: object + metrics: + description: Configuration settings related to the metrics collection + used by the Che installation. + properties: + enable: + description: Enables `metrics` the Che server endpoint. Default + to `true`. + type: boolean + type: object + server: + description: General configuration settings related to the Che server + and the plugin and devfile registries + properties: + airGapContainerRegistryHostname: + description: Optional host name, or URL, to an alternate container + registry to pull images from. This value overrides the container + registry host name defined in all the default container images + involved in a Che deployment. This is particularly useful to + install Che in a restricted environment. + type: string + airGapContainerRegistryOrganization: + description: Optional repository name of an alternate container + registry to pull images from. This value overrides the container + registry organization defined in all the default container images + involved in a Che deployment. This is particularly useful to + install Eclipse Che in a restricted environment. + type: string + allowUserDefinedWorkspaceNamespaces: + description: Defines that a user is allowed to specify a Kubernetes + namespace, or an OpenShift project, which differs from the default. + It's NOT RECOMMENDED to set to `true` without OpenShift OAuth + configured. The OpenShift infrastructure also uses this property. + type: boolean + cheClusterRoles: + description: A comma-separated list of ClusterRoles that will + be assigned to Che ServiceAccount. Be aware that the Che Operator + has to already have all permissions in these ClusterRoles to + grant them. + type: string + cheDebug: + description: Enables the debug mode for Che server. Defaults to + `false`. + type: string + cheFlavor: + description: Specifies a variation of the installation. The options + are `che` for upstream Che installations, or `codeready` for + link:https://developers.redhat.com/products/codeready-workspaces/overview[CodeReady + Workspaces] installation. Override the default value only on + necessary occasions. + type: string + cheHost: + description: Public host name of the installed Che server. When + value is omitted, the value it will be automatically set by + the Operator. See the `cheHostTLSSecret` field. + type: string + cheHostTLSSecret: + description: Name of a secret containing certificates to secure + ingress or route for the custom host name of the installed Che + server. See the `cheHost` field. + type: string + cheImage: + description: Overrides the container image used in Che deployment. + This does NOT include the container image tag. Omit it or leave + it empty to use the default container image provided by the + Operator. + type: string + cheImagePullPolicy: + description: Overrides the image pull policy used in Che deployment. + Default value is `Always` for `nightly` or `latest` images, + and `IfNotPresent` in other cases. + type: string + cheImageTag: + description: Overrides the tag of the container image used in + Che deployment. Omit it or leave it empty to use the default + image tag provided by the Operator. + type: string + cheLogLevel: + description: 'Log level for the Che server: `INFO` or `DEBUG`. + Defaults to `INFO`.' + type: string + cheServerIngress: + description: The Che server ingress custom settings. + properties: + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + cheServerRoute: + description: The Che server route custom settings. + properties: + domain: + description: 'Operator uses the domain to generate a hostname + for a route. In a conjunction with labels it creates a route, + which is served by a non-default Ingress controller. The + generated host name will follow this pattern: `-.`.' + type: string + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + cheWorkspaceClusterRole: + description: Custom cluster role bound to the user for the Che + workspaces. The default roles are used when omitted or left + blank. + type: string + customCheProperties: + additionalProperties: + type: string + description: Map of additional environment variables that will + be applied in the generated `che` ConfigMap to be used by the + Che server, in addition to the values already generated from + other fields of the `CheCluster` custom resource (CR). When + `customCheProperties` contains a property that would be normally + generated in `che` ConfigMap from other CR fields, the value + defined in the `customCheProperties` is used instead. + type: object + dashboardCpuLimit: + description: Overrides the CPU limit used in the dashboard deployment. + In cores. (500m = .5 cores). Default to 500m. + type: string + dashboardCpuRequest: + description: Overrides the CPU request used in the dashboard deployment. + In cores. (500m = .5 cores). Default to 100m. + type: string + dashboardImage: + description: Overrides the container image used in the dashboard + deployment. This includes the image tag. Omit it or leave it + empty to use the default container image provided by the Operator. + type: string + dashboardImagePullPolicy: + description: Overrides the image pull policy used in the dashboard + deployment. Default value is `Always` for `nightly` or `latest` + images, and `IfNotPresent` in other cases. + type: string + dashboardMemoryLimit: + description: Overrides the memory limit used in the dashboard + deployment. Defaults to 256Mi. + type: string + dashboardMemoryRequest: + description: Overrides the memory request used in the dashboard + deployment. Defaults to 16Mi. + type: string + devfileRegistryCpuLimit: + description: Overrides the CPU limit used in the devfile registry + deployment. In cores. (500m = .5 cores). Default to 500m. + type: string + devfileRegistryCpuRequest: + description: Overrides the CPU request used in the devfile registry + deployment. In cores. (500m = .5 cores). Default to 100m. + type: string + devfileRegistryImage: + description: Overrides the container image used in the devfile + registry deployment. This includes the image tag. Omit it or + leave it empty to use the default container image provided by + the Operator. + type: string + devfileRegistryIngress: + description: The devfile registry ingress custom settings. + properties: + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + devfileRegistryMemoryLimit: + description: Overrides the memory limit used in the devfile registry + deployment. Defaults to 256Mi. + type: string + devfileRegistryMemoryRequest: + description: Overrides the memory request used in the devfile + registry deployment. Defaults to 16Mi. + type: string + devfileRegistryPullPolicy: + description: Overrides the image pull policy used in the devfile + registry deployment. Default value is `Always` for `nightly` + or `latest` images, and `IfNotPresent` in other cases. + type: string + devfileRegistryRoute: + description: The devfile registry route custom settings. + properties: + domain: + description: 'Operator uses the domain to generate a hostname + for a route. In a conjunction with labels it creates a route, + which is served by a non-default Ingress controller. The + generated host name will follow this pattern: `-.`.' + type: string + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + devfileRegistryUrl: + description: Public URL of the devfile registry, that serves sample, + ready-to-use devfiles. Set this ONLY when a use of an external + devfile registry is needed. See the `externalDevfileRegistry` + field. By default, this will be automatically calculated by + the Operator. + type: string + externalDevfileRegistry: + description: Instructs the Operator on whether to deploy a dedicated + devfile registry server. By default, a dedicated devfile registry + server is started. When `externalDevfileRegistry` is `true`, + no such dedicated server will be started by the Operator and + you will have to manually set the `devfileRegistryUrl` field + type: boolean + externalPluginRegistry: + description: Instructs the Operator on whether to deploy a dedicated + plugin registry server. By default, a dedicated plugin registry + server is started. When `externalPluginRegistry` is `true`, + no such dedicated server will be started by the Operator and + you will have to manually set the `pluginRegistryUrl` field. + type: boolean + gitSelfSignedCert: + description: When enabled, the certificate from `che-git-self-signed-cert` + ConfigMap will be propagated to the Che components and provide + particular configuration for Git. + type: boolean + nonProxyHosts: + description: 'List of hosts that will be reached directly, bypassing + the proxy. Specify wild card domain use the following form `.` + and `|` as delimiter, for example: `localhost|.my.host.com|123.42.12.32` + Only use when configuring a proxy is required. Operator respects + OpenShift cluster wide proxy configuration and no additional + configuration is required, but defining `nonProxyHosts` in a + custom resource leads to merging non proxy hosts lists from + the cluster proxy configuration and ones defined in the custom + resources. See the doc https://docs.openshift.com/container-platform/4.4/networking/enable-cluster-wide-proxy.html. + See also the `proxyURL` fields.' + type: string + pluginRegistryCpuLimit: + description: Overrides the CPU limit used in the plugin registry + deployment. In cores. (500m = .5 cores). Default to 500m. + type: string + pluginRegistryCpuRequest: + description: Overrides the CPU request used in the plugin registry + deployment. In cores. (500m = .5 cores). Default to 100m. + type: string + pluginRegistryImage: + description: Overrides the container image used in the plugin + registry deployment. This includes the image tag. Omit it or + leave it empty to use the default container image provided by + the Operator. + type: string + pluginRegistryIngress: + description: Plugin registry ingress custom settings. + properties: + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + pluginRegistryMemoryLimit: + description: Overrides the memory limit used in the plugin registry + deployment. Defaults to 256Mi. + type: string + pluginRegistryMemoryRequest: + description: Overrides the memory request used in the plugin registry + deployment. Defaults to 16Mi. + type: string + pluginRegistryPullPolicy: + description: Overrides the image pull policy used in the plugin + registry deployment. Default value is `Always` for `nightly` + or `latest` images, and `IfNotPresent` in other cases. + type: string + pluginRegistryRoute: + description: Plugin registry route custom settings. + properties: + domain: + description: 'Operator uses the domain to generate a hostname + for a route. In a conjunction with labels it creates a route, + which is served by a non-default Ingress controller. The + generated host name will follow this pattern: `-.`.' + type: string + labels: + description: Comma separated list of labels that can be used + to organize and categorize objects by scoping and selecting. + type: string + type: object + pluginRegistryUrl: + description: Public URL of the plugin registry that serves sample + ready-to-use devfiles. Set this ONLY when a use of an external + devfile registry is needed. See the `externalPluginRegistry` + field. By default, this will be automatically calculated by + the Operator. + type: string + proxyPassword: + description: Password of the proxy server. Only use when proxy + configuration is required. See the `proxyURL`, `proxyUser` and + `proxySecret` fields. + type: string + proxyPort: + description: Port of the proxy server. Only use when configuring + a proxy is required. See also the `proxyURL` and `nonProxyHosts` + fields. + type: string + proxySecret: + description: The secret that contains `user` and `password` for + a proxy server. When the secret is defined, the `proxyUser` + and `proxyPassword` are ignored. + type: string + proxyURL: + description: URL (protocol+host name) of the proxy server. This + drives the appropriate changes in the `JAVA_OPTS` and `https(s)_proxy` + variables in the Che server and workspaces containers. Only + use when configuring a proxy is required. Operator respects + OpenShift cluster wide proxy configuration and no additional + configuration is required, but defining `proxyUrl` in a custom + resource leads to overrides the cluster proxy configuration + with fields `proxyUrl`, `proxyPort`, `proxyUser` and `proxyPassword` + from the custom resource. See the doc https://docs.openshift.com/container-platform/4.4/networking/enable-cluster-wide-proxy.html. + See also the `proxyPort` and `nonProxyHosts` fields. + type: string + proxyUser: + description: User name of the proxy server. Only use when configuring + a proxy is required. See also the `proxyURL`, `proxyPassword` + and `proxySecret` fields. + type: string + selfSignedCert: + description: Deprecated. The value of this flag is ignored. The + Che Operator will automatically detect whether the router certificate + is self-signed and propagate it to other components, such as + the Che server. + type: boolean + serverCpuLimit: + description: Overrides the CPU limit used in the Che server deployment + In cores. (500m = .5 cores). Default to 1. + type: string + serverCpuRequest: + description: Overrides the CPU request used in the Che server + deployment In cores. (500m = .5 cores). Default to 100m. + type: string + serverExposureStrategy: + description: Sets the server and workspaces exposure type. Possible + values are `multi-host`, `single-host`, `default-host`. Defaults + to `multi-host`, which creates a separate ingress, or OpenShift + routes, for every required endpoint. `single-host` makes Che + exposed on a single host name with workspaces exposed on subpaths. + Read the docs to learn about the limitations of this approach. + Also consult the `singleHostExposureType` property to further + configure how the Operator and the Che server make that happen + on Kubernetes. `default-host` exposes the Che server on the + host of the cluster. Read the docs to learn about the limitations + of this approach. + type: string + serverMemoryLimit: + description: Overrides the memory limit used in the Che server + deployment. Defaults to 1Gi. + type: string + serverMemoryRequest: + description: Overrides the memory request used in the Che server + deployment. Defaults to 512Mi. + type: string + serverTrustStoreConfigMapName: + description: Name of the ConfigMap with public certificates to + add to Java trust store of the Che server. This is often required + when adding the OpenShift OAuth provider, which has HTTPS endpoint + signed with self-signed cert. The Che server must be aware of + its CA cert to be able to request it. This is disabled by default. + type: string + singleHostGatewayConfigMapLabels: + additionalProperties: + type: string + description: The labels that need to be present in the ConfigMaps + representing the gateway configuration. + type: object + singleHostGatewayConfigSidecarImage: + description: The image used for the gateway sidecar that provides + configuration to the gateway. Omit it or leave it empty to use + the default container image provided by the Operator. + type: string + singleHostGatewayImage: + description: The image used for the gateway in the single host + mode. Omit it or leave it empty to use the default container + image provided by the Operator. + type: string + tlsSupport: + description: Deprecated. Instructs the Operator to deploy Che + in TLS mode. This is enabled by default. Disabling TLS sometimes + cause malfunction of some Che components. + type: boolean + useInternalClusterSVCNames: + description: Use internal cluster SVC names to communicate between + components to speed up the traffic and avoid proxy issues. The + default value is `true`. + type: boolean + workspaceNamespaceDefault: + description: Defines Kubernetes default namespace in which user's + workspaces are created for a case when a user does not override + it. It's possible to use ``, `` and `` + placeholders, such as che-workspace-. In that case, + a new namespace will be created for each user or workspace. + type: string + type: object + storage: + description: Configuration settings related to the persistent storage + used by the Che installation. + properties: + postgresPVCStorageClassName: + description: Storage class for the Persistent Volume Claim dedicated + to the PostgreSQL database. When omitted or left blank, a default + storage class is used. + type: string + preCreateSubPaths: + description: Instructs the Che server to start a special Pod to + pre-create a sub-path in the Persistent Volumes. Defaults to + `false`, however it will need to enable it according to the + configuration of your Kubernetes cluster. + type: boolean + pvcClaimSize: + description: Size of the persistent volume claim for workspaces. + Defaults to `1Gi`. + type: string + pvcJobsImage: + description: Overrides the container image used to create sub-paths + in the Persistent Volumes. This includes the image tag. Omit + it or leave it empty to use the default container image provided + by the Operator. See also the `preCreateSubPaths` field. + type: string + pvcStrategy: + description: Persistent volume claim strategy for the Che server. + This Can be:`common` (all workspaces PVCs in one volume), `per-workspace` + (one PVC per workspace for all declared volumes) and `unique` + (one PVC per declared volume). Defaults to `common`. + type: string + workspacePVCStorageClassName: + description: Storage class for the Persistent Volume Claims dedicated + to the Che workspaces. When omitted or left blank, a default + storage class is used. + type: string + type: object + type: object + status: + description: CheClusterStatus defines the observed state of Che installation + properties: + cheClusterRunning: + description: Status of a Che installation. Can be `Available`, `Unavailable`, + or `Available, Rolling Update in Progress`. + type: string + cheURL: + description: Public URL to the Che server. + type: string + cheVersion: + description: Current installed Che version. + type: string + dbProvisioned: + description: Indicates that a PostgreSQL instance has been correctly + provisioned or not. + type: boolean + devfileRegistryURL: + description: Public URL to the devfile registry. + type: string + gitHubOAuthProvisioned: + description: Indicates whether an Identity Provider instance, Keycloak + or RH-SSO, has been configured to integrate with the GitHub OAuth. + type: boolean + helpLink: + description: A URL that points to some URL where to find help related + to the current Operator status. + type: string + keycloakProvisioned: + description: Indicates whether an Identity Provider instance, Keycloak + or RH-SSO, has been provisioned with realm, client and user. + type: boolean + keycloakURL: + description: Public URL to the Identity Provider server, Keycloak + or RH-SSO,. + type: string + message: + description: A human readable message indicating details about why + the Pod is in this condition. + type: string + openShiftOAuthUserCredentialsSecret: + description: OpenShift OAuth secret in `openshift-config` namespace + that contains user credentials for HTPasswd identity provider. + type: string + openShiftoAuthProvisioned: + description: Indicates whether an Identity Provider instance, Keycloak + or RH-SSO, has been configured to integrate with the OpenShift OAuth. + type: boolean + pluginRegistryURL: + description: Public URL to the plugin registry. + type: string + reason: + description: A brief CamelCase message indicating details about why + the Pod is in this state. + type: string + type: object + type: object served: true storage: true + - name: v2alpha1 + schema: + openAPIV3Schema: + description: CheCluster is the configuration of the CheCluster layer of Devworkspace. + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation + of an object. Servers should convert recognized schemas to the latest + internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource this + object represents. Servers may infer this from the endpoint the client + submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + description: CheClusterSpec holds the configuration of the Che controller. + properties: + gateway: + description: Gateway contains the configuration of the gateway used + for workspace endpoint routing. + properties: + configurerImage: + description: ConfigurerImage is the docker image to use for the + sidecar of the Che gateway that is used to configure it. This + is only used when Enabled is true. If not defined in the CR, + it is taken from the `RELATED_IMAGE_gateway_configurer` environment + variable of the operator deployment/pod. If not defined there, + it defaults to a hardcoded value. + type: string + enabled: + description: "Enabled enables or disables routing of the url rewrite + supporting devworkspace endpoints through a common gateway (the + hostname of which is defined by the Host). + Default value + is \"true\" meaning that the gateway is enabled. + If set to + true (i.e. the gateway is enabled), endpoints marked using the + \"urlRewriteSupported\" attribute are exposed on unique subpaths + of the Host, while the rest of the devworkspace endpoints are + exposed on subdomains of the Host. + If set to false (i.e. + the gateway is disabled), all endpoints are deployed on subdomains + of the Host." + type: boolean + image: + description: Image is the docker image to use for the Che gateway. This + is only used if Enabled is true. If not defined in the CR, it + is taken from the `RELATED_IMAGE_gateway` environment variable + of the operator deployment/pod. If not defined there, it defaults + to a hardcoded value. + type: string + type: object + host: + description: "Host is the full host name used to expose devworkspace + endpoints either on subpaths or on subdomains. See the gateway.enabled + attribute for a more detailed description of where and how are devworkspace + endpoints exposed in various configurations. + This attribute is + mandatory on Kubernetes, optional on OpenShift." + type: string + k8s: + description: K8s contains the configuration specific only to Kubernetes + properties: + ingressAnnotations: + additionalProperties: + type: string + description: "IngressAnnotations are the annotations to be put + on the generated ingresses. This can be used to configure the + ingress class and the ingress-controller-specific behavior for + both the gateway and the ingresses created to expose the Devworkspace + component endpoints. When not specified, this defaults to: + + \ kubernetes.io/ingress.class: \"nginx\" + \ nginx.ingress.kubernetes.io/proxy-read-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/proxy-connect-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/ssl-redirect: \"true\"" + type: object + type: object + tlsSecretName: + description: "Name of a secret that will be used to setup ingress/route + TLS certificate. When the field is empty string, the default cluster + certificate will be used. The same secret is assumed to exist in + the same namespace as the CheCluster CR and is used for both the + gateway and all devworkspace endpoints. In case of the devworkspace + endpoints, the secret is copied to the namespace of the devworkspace. + + The secret has to be of type \"tls\"." + type: string + type: object + status: + description: CheClusterStatus contains the status of the CheCluster object + properties: + gatewayHost: + description: ResolvedHost is the resolved host of the ingress/route. + This is equal to the Host in the spec on Kubernetes but contains + the actual host name of the route if Host is unspecified on OpenShift. + type: string + gatewayPhase: + description: GatewayPhase specifies the phase in which the gateway + deployment currently is. If the gateway is disabled, the phase is + "Inactive". + type: string + message: + description: Message contains further human-readable info for why + the Che cluster is in the phase it currently is. + type: string + phase: + description: Phase is the phase in which the Che cluster as a whole + finds itself in. + type: string + type: object + type: object + served: true + storage: false diff --git a/deploy/crds/org_v1_che_crd.yaml b/deploy/crds/org_v1_che_crd.yaml index 92b4a27f92..434ea3ce0b 100644 --- a/deploy/crds/org_v1_che_crd.yaml +++ b/deploy/crds/org_v1_che_crd.yaml @@ -913,3 +913,122 @@ spec: storage: true subresources: status: {} + - name: v2alpha1 + schema: + openAPIV3Schema: + description: CheCluster is the configuration of the CheCluster layer of Devworkspace. + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation + of an object. Servers should convert recognized schemas to the latest + internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource this + object represents. Servers may infer this from the endpoint the client + submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + description: CheClusterSpec holds the configuration of the Che controller. + properties: + gateway: + description: Gateway contains the configuration of the gateway used + for workspace endpoint routing. + properties: + configurerImage: + description: ConfigurerImage is the docker image to use for the + sidecar of the Che gateway that is used to configure it. This + is only used when Enabled is true. If not defined in the CR, + it is taken from the `RELATED_IMAGE_gateway_configurer` environment + variable of the operator deployment/pod. If not defined there, + it defaults to a hardcoded value. + type: string + enabled: + description: "Enabled enables or disables routing of the url rewrite + supporting devworkspace endpoints through a common gateway (the + hostname of which is defined by the Host). + Default value + is \"true\" meaning that the gateway is enabled. + If set to + true (i.e. the gateway is enabled), endpoints marked using the + \"urlRewriteSupported\" attribute are exposed on unique subpaths + of the Host, while the rest of the devworkspace endpoints are + exposed on subdomains of the Host. + If set to false (i.e. + the gateway is disabled), all endpoints are deployed on subdomains + of the Host." + type: boolean + image: + description: Image is the docker image to use for the Che gateway. This + is only used if Enabled is true. If not defined in the CR, it + is taken from the `RELATED_IMAGE_gateway` environment variable + of the operator deployment/pod. If not defined there, it defaults + to a hardcoded value. + type: string + type: object + host: + description: "Host is the full host name used to expose devworkspace + endpoints either on subpaths or on subdomains. See the gateway.enabled + attribute for a more detailed description of where and how are devworkspace + endpoints exposed in various configurations. + This attribute is + mandatory on Kubernetes, optional on OpenShift." + type: string + k8s: + description: K8s contains the configuration specific only to Kubernetes + properties: + ingressAnnotations: + additionalProperties: + type: string + description: "IngressAnnotations are the annotations to be put + on the generated ingresses. This can be used to configure the + ingress class and the ingress-controller-specific behavior for + both the gateway and the ingresses created to expose the Devworkspace + component endpoints. When not specified, this defaults to: + + \ kubernetes.io/ingress.class: \"nginx\" + \ nginx.ingress.kubernetes.io/proxy-read-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/proxy-connect-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/ssl-redirect: \"true\"" + type: object + type: object + tlsSecretName: + description: "Name of a secret that will be used to setup ingress/route + TLS certificate. When the field is empty string, the default cluster + certificate will be used. The same secret is assumed to exist in + the same namespace as the CheCluster CR and is used for both the + gateway and all devworkspace endpoints. In case of the devworkspace + endpoints, the secret is copied to the namespace of the devworkspace. + + The secret has to be of type \"tls\"." + type: string + type: object + status: + description: CheClusterStatus contains the status of the CheCluster object + properties: + gatewayHost: + description: ResolvedHost is the resolved host of the ingress/route. + This is equal to the Host in the spec on Kubernetes but contains + the actual host name of the route if Host is unspecified on OpenShift. + type: string + gatewayPhase: + description: GatewayPhase specifies the phase in which the gateway + deployment currently is. If the gateway is disabled, the phase is + "Inactive". + type: string + message: + description: Message contains further human-readable info for why + the Che cluster is in the phase it currently is. + type: string + phase: + description: Phase is the phase in which the Che cluster as a whole + finds itself in. + type: string + type: object + type: object + served: true + storage: false + subresources: + status: {} diff --git a/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/che-operator.clusterserviceversion.yaml b/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/che-operator.clusterserviceversion.yaml index bf2bb9fece..0bdf9fa624 100644 --- a/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/che-operator.clusterserviceversion.yaml +++ b/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/che-operator.clusterserviceversion.yaml @@ -76,13 +76,13 @@ metadata: categories: Developer Tools certified: "false" containerImage: quay.io/eclipse/che-operator:nightly - createdAt: "2021-05-06T14:33:11Z" + createdAt: "2021-05-07T12:19:30Z" description: A Kube-native development solution that delivers portable and collaborative developer workspaces. operatorframework.io/suggested-namespace: eclipse-che repository: https://github.com/eclipse-che/che-operator support: Eclipse Foundation - name: eclipse-che-preview-kubernetes.v7.30.0-174.nightly + name: eclipse-che-preview-kubernetes.v7.30.0-176.nightly namespace: placeholder spec: apiservicedefinitions: {} @@ -152,6 +152,10 @@ spec: - urn:alm:descriptor:io.kubernetes.phase:reason - urn:alm:descriptor:text version: v1 + - description: CheCluster is the configuration of the CheCluster layer of Devworkspace. + kind: CheCluster + name: checlusters.org.eclipse.che + version: v2alpha1 description: | A collaborative Kubernetes-native development solution that delivers Kubernetes workspaces and in-browser IDE for rapid cloud application development. This operator installs PostgreSQL, Keycloak, Registries and the Eclipse Che server, as well as configures all these services. @@ -1127,4 +1131,4 @@ spec: maturity: stable provider: name: Eclipse Foundation - version: 7.30.0-174.nightly + version: 7.30.0-176.nightly diff --git a/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/org_v1_che_crd.yaml b/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/org_v1_che_crd.yaml index 92b4a27f92..434ea3ce0b 100644 --- a/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/org_v1_che_crd.yaml +++ b/deploy/olm-catalog/nightly/eclipse-che-preview-kubernetes/manifests/org_v1_che_crd.yaml @@ -913,3 +913,122 @@ spec: storage: true subresources: status: {} + - name: v2alpha1 + schema: + openAPIV3Schema: + description: CheCluster is the configuration of the CheCluster layer of Devworkspace. + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation + of an object. Servers should convert recognized schemas to the latest + internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource this + object represents. Servers may infer this from the endpoint the client + submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + description: CheClusterSpec holds the configuration of the Che controller. + properties: + gateway: + description: Gateway contains the configuration of the gateway used + for workspace endpoint routing. + properties: + configurerImage: + description: ConfigurerImage is the docker image to use for the + sidecar of the Che gateway that is used to configure it. This + is only used when Enabled is true. If not defined in the CR, + it is taken from the `RELATED_IMAGE_gateway_configurer` environment + variable of the operator deployment/pod. If not defined there, + it defaults to a hardcoded value. + type: string + enabled: + description: "Enabled enables or disables routing of the url rewrite + supporting devworkspace endpoints through a common gateway (the + hostname of which is defined by the Host). + Default value + is \"true\" meaning that the gateway is enabled. + If set to + true (i.e. the gateway is enabled), endpoints marked using the + \"urlRewriteSupported\" attribute are exposed on unique subpaths + of the Host, while the rest of the devworkspace endpoints are + exposed on subdomains of the Host. + If set to false (i.e. + the gateway is disabled), all endpoints are deployed on subdomains + of the Host." + type: boolean + image: + description: Image is the docker image to use for the Che gateway. This + is only used if Enabled is true. If not defined in the CR, it + is taken from the `RELATED_IMAGE_gateway` environment variable + of the operator deployment/pod. If not defined there, it defaults + to a hardcoded value. + type: string + type: object + host: + description: "Host is the full host name used to expose devworkspace + endpoints either on subpaths or on subdomains. See the gateway.enabled + attribute for a more detailed description of where and how are devworkspace + endpoints exposed in various configurations. + This attribute is + mandatory on Kubernetes, optional on OpenShift." + type: string + k8s: + description: K8s contains the configuration specific only to Kubernetes + properties: + ingressAnnotations: + additionalProperties: + type: string + description: "IngressAnnotations are the annotations to be put + on the generated ingresses. This can be used to configure the + ingress class and the ingress-controller-specific behavior for + both the gateway and the ingresses created to expose the Devworkspace + component endpoints. When not specified, this defaults to: + + \ kubernetes.io/ingress.class: \"nginx\" + \ nginx.ingress.kubernetes.io/proxy-read-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/proxy-connect-timeout: \"3600\", + \ nginx.ingress.kubernetes.io/ssl-redirect: \"true\"" + type: object + type: object + tlsSecretName: + description: "Name of a secret that will be used to setup ingress/route + TLS certificate. When the field is empty string, the default cluster + certificate will be used. The same secret is assumed to exist in + the same namespace as the CheCluster CR and is used for both the + gateway and all devworkspace endpoints. In case of the devworkspace + endpoints, the secret is copied to the namespace of the devworkspace. + + The secret has to be of type \"tls\"." + type: string + type: object + status: + description: CheClusterStatus contains the status of the CheCluster object + properties: + gatewayHost: + description: ResolvedHost is the resolved host of the ingress/route. + This is equal to the Host in the spec on Kubernetes but contains + the actual host name of the route if Host is unspecified on OpenShift. + type: string + gatewayPhase: + description: GatewayPhase specifies the phase in which the gateway + deployment currently is. If the gateway is disabled, the phase is + "Inactive". + type: string + message: + description: Message contains further human-readable info for why + the Che cluster is in the phase it currently is. + type: string + phase: + description: Phase is the phase in which the Che cluster as a whole + finds itself in. + type: string + type: object + type: object + served: true + storage: false + subresources: + status: {} diff --git a/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/che-operator.clusterserviceversion.yaml b/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/che-operator.clusterserviceversion.yaml index 1118d45ae0..ff0731ef28 100644 --- a/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/che-operator.clusterserviceversion.yaml +++ b/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/che-operator.clusterserviceversion.yaml @@ -67,13 +67,13 @@ metadata: categories: Developer Tools, OpenShift Optional certified: "false" containerImage: quay.io/eclipse/che-operator:nightly - createdAt: "2021-05-06T14:33:21Z" + createdAt: "2021-05-07T12:19:41Z" description: A Kube-native development solution that delivers portable and collaborative developer workspaces in OpenShift. operatorframework.io/suggested-namespace: eclipse-che repository: https://github.com/eclipse-che/che-operator support: Eclipse Foundation - name: eclipse-che-preview-openshift.v7.30.0-174.nightly + name: eclipse-che-preview-openshift.v7.30.0-176.nightly namespace: placeholder spec: apiservicedefinitions: {} @@ -143,6 +143,10 @@ spec: - urn:alm:descriptor:io.kubernetes.phase:reason - urn:alm:descriptor:text version: v1 + - description: CheCluster is the configuration of the CheCluster layer of Devworkspace. + kind: CheCluster + name: checlusters.org.eclipse.che + version: v2alpha1 description: | A collaborative Kubernetes-native development solution that delivers OpenShift workspaces and in-browser IDE for rapid cloud application development. This operator installs PostgreSQL, Keycloak, and the Eclipse Che server, as well as configures all three services. @@ -1200,4 +1204,4 @@ spec: maturity: stable provider: name: Eclipse Foundation - version: 7.30.0-174.nightly + version: 7.30.0-176.nightly diff --git a/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/org_v1_che_crd.yaml b/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/org_v1_che_crd.yaml index cc5fc3d0c6..977e4cc5da 100644 --- a/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/org_v1_che_crd.yaml +++ b/deploy/olm-catalog/nightly/eclipse-che-preview-openshift/manifests/org_v1_che_crd.yaml @@ -928,3 +928,120 @@ spec: storage: true subresources: status: {} + - name: v2alpha1 + schema: + openAPIV3Schema: + description: CheCluster is the configuration of the CheCluster layer of + Devworkspace. + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation + of an object. Servers should convert recognized schemas to the latest + internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource + this object represents. Servers may infer this from the endpoint the + client submits requests to. Cannot be updated. In CamelCase. More + info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + description: CheClusterSpec holds the configuration of the Che controller. + properties: + gateway: + description: Gateway contains the configuration of the gateway used + for workspace endpoint routing. + properties: + configurerImage: + description: ConfigurerImage is the docker image to use for + the sidecar of the Che gateway that is used to configure it. + This is only used when Enabled is true. If not defined in + the CR, it is taken from the `RELATED_IMAGE_gateway_configurer` + environment variable of the operator deployment/pod. If not + defined there, it defaults to a hardcoded value. + type: string + enabled: + description: "Enabled enables or disables routing of the url\ + \ rewrite supporting devworkspace endpoints through a common\ + \ gateway (the hostname of which is defined by the Host).\ + \ Default value is \"true\" meaning that the gateway is enabled.\ + \ If set to true (i.e. the gateway is enabled), endpoints\ + \ marked using the \"urlRewriteSupported\" attribute are exposed\ + \ on unique subpaths of the Host, while the rest of the devworkspace\ + \ endpoints are exposed on subdomains of the Host. If set\ + \ to false (i.e. the gateway is disabled), all endpoints are\ + \ deployed on subdomains of the Host." + type: boolean + image: + description: Image is the docker image to use for the Che gateway. This + is only used if Enabled is true. If not defined in the CR, + it is taken from the `RELATED_IMAGE_gateway` environment variable + of the operator deployment/pod. If not defined there, it defaults + to a hardcoded value. + type: string + type: object + host: + description: "Host is the full host name used to expose devworkspace\ + \ endpoints either on subpaths or on subdomains. See the gateway.enabled\ + \ attribute for a more detailed description of where and how are\ + \ devworkspace endpoints exposed in various configurations. This\ + \ attribute is mandatory on Kubernetes, optional on OpenShift." + type: string + k8s: + description: K8s contains the configuration specific only to Kubernetes + properties: + ingressAnnotations: + additionalProperties: + type: string + description: "IngressAnnotations are the annotations to be put\ + \ on the generated ingresses. This can be used to configure\ + \ the ingress class and the ingress-controller-specific behavior\ + \ for both the gateway and the ingresses created to expose\ + \ the Devworkspace component endpoints. When not specified,\ + \ this defaults to:\n kubernetes.io/ingress.class: \ + \ \"nginx\" nginx.ingress.kubernetes.io/proxy-read-timeout:\ + \ \"3600\", nginx.ingress.kubernetes.io/proxy-connect-timeout:\ + \ \"3600\", nginx.ingress.kubernetes.io/ssl-redirect:\ + \ \"true\"" + type: object + type: object + tlsSecretName: + description: "Name of a secret that will be used to setup ingress/route\ + \ TLS certificate. When the field is empty string, the default\ + \ cluster certificate will be used. The same secret is assumed\ + \ to exist in the same namespace as the CheCluster CR and is used\ + \ for both the gateway and all devworkspace endpoints. In case\ + \ of the devworkspace endpoints, the secret is copied to the namespace\ + \ of the devworkspace.\nThe secret has to be of type \"tls\"." + type: string + type: object + status: + description: CheClusterStatus contains the status of the CheCluster + object + properties: + gatewayHost: + description: ResolvedHost is the resolved host of the ingress/route. + This is equal to the Host in the spec on Kubernetes but contains + the actual host name of the route if Host is unspecified on OpenShift. + type: string + gatewayPhase: + description: GatewayPhase specifies the phase in which the gateway + deployment currently is. If the gateway is disabled, the phase + is "Inactive". + type: string + message: + description: Message contains further human-readable info for why + the Che cluster is in the phase it currently is. + type: string + phase: + description: Phase is the phase in which the Che cluster as a whole + finds itself in. + type: string + type: object + type: object + served: true + storage: false + subresources: + status: {} diff --git a/pkg/apis/addtoscheme_org_v1.go b/pkg/apis/addtoscheme_org_v1.go index 1f78b6f799..1949ddcd1d 100644 --- a/pkg/apis/addtoscheme_org_v1.go +++ b/pkg/apis/addtoscheme_org_v1.go @@ -2,9 +2,11 @@ package apis import ( v1 "github.com/eclipse-che/che-operator/pkg/apis/org/v1" + "github.com/eclipse-che/che-operator/pkg/apis/org/v2alpha1" ) func init() { // Register the types with the Scheme so the components can map objects to GroupVersionKinds and back AddToSchemes = append(AddToSchemes, v1.SchemeBuilder.AddToScheme) + AddToSchemes = append(AddToSchemes, v2alpha1.AddToScheme) } diff --git a/pkg/apis/org/v1/che_types.go b/pkg/apis/org/v1/che_types.go index 6d6ac3f8cc..807fb6ed7b 100644 --- a/pkg/apis/org/v1/che_types.go +++ b/pkg/apis/org/v1/che_types.go @@ -666,6 +666,7 @@ type CheClusterStatus struct { // +k8s:openapi-gen=true // +kubebuilder:subresource:status // +operator-sdk:gen-csv:customresourcedefinitions.displayName="Eclipse Che Cluster" +// +kubebuilder:storageversion type CheCluster struct { metav1.TypeMeta `json:",inline"` metav1.ObjectMeta `json:"metadata,omitempty"` diff --git a/pkg/apis/org/v2alpha1/checluster.go b/pkg/apis/org/v2alpha1/checluster.go new file mode 100644 index 0000000000..21b3612441 --- /dev/null +++ b/pkg/apis/org/v2alpha1/checluster.go @@ -0,0 +1,150 @@ +// +// Copyright (c) 2012-2021 Red Hat, Inc. +// This program and the accompanying materials are made +// available under the terms of the Eclipse Public License 2.0 +// which is available at https://www.eclipse.org/legal/epl-2.0/ +// +// SPDX-License-Identifier: EPL-2.0 +// +// Contributors: +// Red Hat, Inc. - initial API and implementation +// + +package v2alpha1 + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// CheClusterSpec holds the configuration of the Che controller. +// +k8s:openapi-gen=true +type CheClusterSpec struct { + // Host is the full host name used to expose devworkspace endpoints either on subpaths or on subdomains. + // See the gateway.enabled attribute for a more detailed description of where and how are devworkspace endpoints + // exposed in various configurations. + // + // This attribute is mandatory on Kubernetes, optional on OpenShift. + Host string `json:"host,omitempty"` + + // Gateway contains the configuration of the gateway used for workspace endpoint routing. + Gateway CheGatewaySpec `json:"gateway,omitempty"` + + // Name of a secret that will be used to setup ingress/route TLS certificate. + // When the field is empty string, the default cluster certificate will be used. + // The same secret is assumed to exist in the same namespace as the CheCluster CR and is used for both + // the gateway and all devworkspace endpoints. + // In case of the devworkspace endpoints, the secret is copied to the namespace of the devworkspace. + // + // The secret has to be of type "tls". + // + // +optional + TlsSecretName string `json:"tlsSecretName,omitempty"` + + // K8s contains the configuration specific only to Kubernetes + K8s CheClusterSpecK8s `json:"k8s,omitempty"` +} + +type CheGatewaySpec struct { + // Enabled enables or disables routing of the url rewrite supporting devworkspace endpoints + // through a common gateway (the hostname of which is defined by the Host). + // + // Default value is "true" meaning that the gateway is enabled. + // + // If set to true (i.e. the gateway is enabled), endpoints marked using the "urlRewriteSupported" attribute + // are exposed on unique subpaths of the Host, while the rest of the devworkspace endpoints are exposed + // on subdomains of the Host. + // + // If set to false (i.e. the gateway is disabled), all endpoints are deployed on subdomains of + // the Host. + Enabled *bool `json:"enabled,omitempty"` + + // Image is the docker image to use for the Che gateway. This is only used if Enabled is true. + // If not defined in the CR, it is taken from + // the `RELATED_IMAGE_gateway` environment variable of the operator deployment/pod. If not defined there, + // it defaults to a hardcoded value. + Image string `json:"image,omitempty"` + + // ConfigurerImage is the docker image to use for the sidecar of the Che gateway that is + // used to configure it. This is only used when Enabled is true. If not defined in the CR, + // it is taken from the `RELATED_IMAGE_gateway_configurer` environment variable of the operator + // deployment/pod. If not defined there, it defaults to a hardcoded value. + ConfigurerImage string `json:"configurerImage,omitempty"` +} + +// CheClusterSpecK8s contains the configuration options specific to Kubernetes only. +type CheClusterSpecK8s struct { + // IngressAnnotations are the annotations to be put on the generated ingresses. This can be used to + // configure the ingress class and the ingress-controller-specific behavior for both the gateway + // and the ingresses created to expose the Devworkspace component endpoints. + // When not specified, this defaults to: + // + // kubernetes.io/ingress.class: "nginx" + // nginx.ingress.kubernetes.io/proxy-read-timeout: "3600", + // nginx.ingress.kubernetes.io/proxy-connect-timeout: "3600", + // nginx.ingress.kubernetes.io/ssl-redirect: "true" + // + // +optional + IngressAnnotations map[string]string `json:"ingressAnnotations,omitempty"` +} + +// GatewayPhase describes the different phases of the Che gateway lifecycle +type GatewayPhase string + +const ( + GatewayPhaseInitializing = "Initializing" + GatewayPhaseEstablished = "Established" + GatewayPhaseInactive = "Inactive" +) + +// ClusterPhase describes the different phases of the Che cluster lifecycle +type ClusterPhase string + +const ( + ManagerPhaseActive = "Active" + ManagerPhaseInactive = "Inactive" + ManagerPhasePendingDeletion = "PendingDeletion" +) + +// CheClusterStatus contains the status of the CheCluster object +// +k8s:openapi-gen=true +type CheClusterStatus struct { + // GatewayPhase specifies the phase in which the gateway deployment currently is. + // If the gateway is disabled, the phase is "Inactive". + GatewayPhase GatewayPhase `json:"gatewayPhase,omitempty"` + + // ResolvedHost is the resolved host of the ingress/route. This is equal to the Host in the spec + // on Kubernetes but contains the actual host name of the route if Host is unspecified on OpenShift. + ResolvedHost string `json:"gatewayHost,omitempty"` + + // Phase is the phase in which the Che cluster as a whole finds itself in. + Phase ClusterPhase `json:"phase,omitempty"` + + // Message contains further human-readable info for why the Che cluster is in the phase it currently is. + Message string `json:"message,omitempty"` +} + +// CheCluster is the configuration of the CheCluster layer of Devworkspace. +// +k8s:openapi-gen=true +// +kubebuilder:subresource:status +// +kubebuilder:resource:path=checlusters,scope=Namespaced +// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object +type CheCluster struct { + metav1.TypeMeta `json:",inline"` + metav1.ObjectMeta `json:"metadata,omitempty"` + + Spec CheClusterSpec `json:"spec,omitempty"` + Status CheClusterStatus `json:"status,omitempty"` +} + +// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object + +// CheClusterList is the list type for CheCluster +type CheClusterList struct { + metav1.TypeMeta `json:",inline"` + metav1.ListMeta `json:"metadata,omitempty"` + Items []CheCluster `json:"items"` +} + +func init() { + SchemeBuilder.Register(&CheCluster{}, &CheClusterList{}) +} diff --git a/pkg/apis/org/v2alpha1/doc.go b/pkg/apis/org/v2alpha1/doc.go new file mode 100644 index 0000000000..055e0ef3d0 --- /dev/null +++ b/pkg/apis/org/v2alpha1/doc.go @@ -0,0 +1,15 @@ +// +// Copyright (c) 2012-2021 Red Hat, Inc. +// This program and the accompanying materials are made +// available under the terms of the Eclipse Public License 2.0 +// which is available at https://www.eclipse.org/legal/epl-2.0/ +// +// SPDX-License-Identifier: EPL-2.0 +// +// Contributors: +// Red Hat, Inc. - initial API and implementation +// +// Package v2alpha1 contains API Schema definitions for the org v2alpha1 API group +// +k8s:deepcopy-gen=package,register +// +groupName=org.eclipse.che +package v2alpha1 diff --git a/pkg/apis/org/v2alpha1/register.go b/pkg/apis/org/v2alpha1/register.go new file mode 100644 index 0000000000..6cc657c8bc --- /dev/null +++ b/pkg/apis/org/v2alpha1/register.go @@ -0,0 +1,33 @@ +// +// Copyright (c) 2012-2021 Red Hat, Inc. +// This program and the accompanying materials are made +// available under the terms of the Eclipse Public License 2.0 +// which is available at https://www.eclipse.org/legal/epl-2.0/ +// +// SPDX-License-Identifier: EPL-2.0 +// +// Contributors: +// Red Hat, Inc. - initial API and implementation +// +// NOTE: Boilerplate only. Ignore this file. + +// Package v2alpha1 contains API Schema definitions for the org v2alpha1 API group +// +k8s:deepcopy-gen=package,register +// +groupName=org.eclipse.che +package v2alpha1 + +import ( + "k8s.io/apimachinery/pkg/runtime/schema" + "sigs.k8s.io/controller-runtime/pkg/scheme" +) + +var ( + // SchemeGroupVersion is group version used to register these objects + SchemeGroupVersion = schema.GroupVersion{Group: "org.eclipse.che", Version: "v2alpha1"} + + // SchemeBuilder is used to add go types to the GroupVersionKind scheme + SchemeBuilder = &scheme.Builder{GroupVersion: SchemeGroupVersion} + + // AddToScheme adds the types in this group-version to the given scheme. + AddToScheme = SchemeBuilder.AddToScheme +) diff --git a/pkg/apis/org/v2alpha1/zz_generated.deepcopy.go b/pkg/apis/org/v2alpha1/zz_generated.deepcopy.go new file mode 100644 index 0000000000..28a31da299 --- /dev/null +++ b/pkg/apis/org/v2alpha1/zz_generated.deepcopy.go @@ -0,0 +1,148 @@ +// +build !ignore_autogenerated + +// Code generated by operator-sdk. DO NOT EDIT. + +package v2alpha1 + +import ( + runtime "k8s.io/apimachinery/pkg/runtime" +) + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheCluster) DeepCopyInto(out *CheCluster) { + *out = *in + out.TypeMeta = in.TypeMeta + in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) + in.Spec.DeepCopyInto(&out.Spec) + out.Status = in.Status + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheCluster. +func (in *CheCluster) DeepCopy() *CheCluster { + if in == nil { + return nil + } + out := new(CheCluster) + in.DeepCopyInto(out) + return out +} + +// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object. +func (in *CheCluster) DeepCopyObject() runtime.Object { + if c := in.DeepCopy(); c != nil { + return c + } + return nil +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheClusterList) DeepCopyInto(out *CheClusterList) { + *out = *in + out.TypeMeta = in.TypeMeta + in.ListMeta.DeepCopyInto(&out.ListMeta) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]CheCluster, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheClusterList. +func (in *CheClusterList) DeepCopy() *CheClusterList { + if in == nil { + return nil + } + out := new(CheClusterList) + in.DeepCopyInto(out) + return out +} + +// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object. +func (in *CheClusterList) DeepCopyObject() runtime.Object { + if c := in.DeepCopy(); c != nil { + return c + } + return nil +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheClusterSpec) DeepCopyInto(out *CheClusterSpec) { + *out = *in + in.Gateway.DeepCopyInto(&out.Gateway) + in.K8s.DeepCopyInto(&out.K8s) + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheClusterSpec. +func (in *CheClusterSpec) DeepCopy() *CheClusterSpec { + if in == nil { + return nil + } + out := new(CheClusterSpec) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheClusterSpecK8s) DeepCopyInto(out *CheClusterSpecK8s) { + *out = *in + if in.IngressAnnotations != nil { + in, out := &in.IngressAnnotations, &out.IngressAnnotations + *out = make(map[string]string, len(*in)) + for key, val := range *in { + (*out)[key] = val + } + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheClusterSpecK8s. +func (in *CheClusterSpecK8s) DeepCopy() *CheClusterSpecK8s { + if in == nil { + return nil + } + out := new(CheClusterSpecK8s) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheClusterStatus) DeepCopyInto(out *CheClusterStatus) { + *out = *in + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheClusterStatus. +func (in *CheClusterStatus) DeepCopy() *CheClusterStatus { + if in == nil { + return nil + } + out := new(CheClusterStatus) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *CheGatewaySpec) DeepCopyInto(out *CheGatewaySpec) { + *out = *in + if in.Enabled != nil { + in, out := &in.Enabled, &out.Enabled + *out = new(bool) + **out = **in + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CheGatewaySpec. +func (in *CheGatewaySpec) DeepCopy() *CheGatewaySpec { + if in == nil { + return nil + } + out := new(CheGatewaySpec) + in.DeepCopyInto(out) + return out +} diff --git a/pkg/webhooks/checluster/conversion.go b/pkg/webhooks/checluster/conversion.go new file mode 100644 index 0000000000..10dd288f3f --- /dev/null +++ b/pkg/webhooks/checluster/conversion.go @@ -0,0 +1,183 @@ +package checluster + +import ( + v1 "github.com/eclipse-che/che-operator/pkg/apis/org/v1" + "github.com/eclipse-che/che-operator/pkg/apis/org/v2alpha1" + "github.com/eclipse-che/che-operator/pkg/util" + "gopkg.in/yaml.v2" +) + +const ( + v1StorageAnnotation = "che.eclipse.org/cheClusterV1Spec" + v2alpha1StorageAnnotation = "che.eclipse.org/cheClusterV2alpha1Spec" + routeDomainSuffixPropertyKey = "CHE_INFRA_OPENSHIFT_ROUTE_HOST_DOMAIN__SUFFIX" +) + +func V1ToV2alpha1(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) error { + v2Data := v1.Annotations[v2alpha1StorageAnnotation] + v2Spec := v2alpha1.CheClusterSpec{} + if v2Data != "" { + err := yaml.Unmarshal([]byte(v2Data), &v2Spec) + if err != nil { + return err + } + } + + v2.ObjectMeta = v1.ObjectMeta + v2.Spec = v2Spec + + v1Spec, err := yaml.Marshal(v1.Spec) + if err != nil { + return err + } + if v2.Annotations == nil { + v2.Annotations = map[string]string{} + } + v2.Annotations[v1StorageAnnotation] = string(v1Spec) + + v1ToV2alpha1_Host(v1, v2) + v1ToV2alpha1_GatewayEnabled(v1, v2) + v1ToV2alpha1_GatewayImage(v1, v2) + v1ToV2alpha1_GatewayConfigurerImage(v1, v2) + v1ToV2alpha1_TlsSecretName(v1, v2) + v1ToV2alpha1_K8sIngressAnnotations(v1, v2) + + return nil +} + +func V2alpha1ToV1(v2 *v2alpha1.CheCluster, v1Obj *v1.CheCluster) error { + v1Data := v2.Annotations[v1StorageAnnotation] + v1Spec := v1.CheClusterSpec{} + if v1Data != "" { + err := yaml.Unmarshal([]byte(v1Data), &v1Spec) + if err != nil { + return err + } + } + + v1Obj.ObjectMeta = v2.ObjectMeta + v1Obj.Spec = v1Spec + v1Obj.Status = v1.CheClusterStatus{} + + v2Spec, err := yaml.Marshal(v2.Spec) + if err != nil { + return err + } + if v1Obj.Annotations == nil { + v1Obj.Annotations = map[string]string{} + } + v1Obj.Annotations[v2alpha1StorageAnnotation] = string(v2Spec) + + v2alpha1ToV1_Host(v1Obj, v2) + v2alpha1ToV1_GatewayEnabled(v1Obj, v2) + v2alpha1ToV1_GatewayImage(v1Obj, v2) + v2alpha1ToV1_GatewayConfigurerImage(v1Obj, v2) + v2alpha1ToV1_TlsSecretName(v1Obj, v2) + v2alpha1ToV1_K8sIngressAnnotations(v1Obj, v2) + + return nil +} + +func v1ToV2alpha1_Host(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + if util.IsOpenShift { + v2.Spec.Host = v1.Spec.Server.CustomCheProperties[routeDomainSuffixPropertyKey] + } else { + v2.Spec.Host = v1.Spec.K8s.IngressDomain + } +} + +func v1ToV2alpha1_GatewayEnabled(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + val := util.GetServerExposureStrategy(v1) == "single-host" + v2.Spec.Gateway.Enabled = &val +} + +func v1ToV2alpha1_GatewayImage(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + v2.Spec.Gateway.Image = v1.Spec.Server.SingleHostGatewayImage +} + +func v1ToV2alpha1_GatewayConfigurerImage(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + v2.Spec.Gateway.ConfigurerImage = v1.Spec.Server.SingleHostGatewayConfigSidecarImage +} + +func v1ToV2alpha1_TlsSecretName(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + // v1.Spec.Server.CheHostTLSSecret is used specifically for Che Host - i.e. the host under which che server is deployed. + // In DW we would only used that for subpath endpoints but wouldn't know what TLS to use for subdomain endpoints. + // Che server always uses the default cluster certificate for these on OpenShift, and the K8s.TlsSecretName on K8s. + // Because we're dealing with endpoints, let's try to use the secret on Kubernetes and nothing (e.g. the default cluster cert on OpenShift) + // which is in line with the logic of the Che server. Let's ignore CheHostTLSSecret for now - this is used only for che server which + // we are not exposing anyway. + if !util.IsOpenShift { + v2.Spec.TlsSecretName = v1.Spec.K8s.TlsSecretName + } +} + +func v1ToV2alpha1_K8sIngressAnnotations(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + annotations := map[string]string{ + "kubernetes.io/ingress.class": v1.Spec.K8s.IngressClass, + "nginx.ingress.kubernetes.io/proxy-read-timeout": "3600", + "nginx.ingress.kubernetes.io/proxy-connect-timeout": "3600", + "nginx.ingress.kubernetes.io/ssl-redirect": "true", + } + // This is what is applied in the deploy/ingress.go but I don't think it is applicable in our situation + // if ingressStrategy != "multi-host" && (component == DevfileRegistryName || component == PluginRegistryName) { + // annotations["nginx.ingress.kubernetes.io/rewrite-target"] = "/$1" + // } + + v2.Spec.K8s.IngressAnnotations = annotations +} + +func v2alpha1ToV1_Host(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + if util.IsOpenShift { + if v1.Spec.Server.CustomCheProperties == nil { + v1.Spec.Server.CustomCheProperties = map[string]string{} + } + v1.Spec.Server.CustomCheProperties[routeDomainSuffixPropertyKey] = v2.Spec.Host + } else { + v1.Spec.K8s.IngressDomain = v2.Spec.Host + } +} + +func v2alpha1ToV1_GatewayEnabled(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + v1Strategy := util.GetServerExposureStrategy(v1) + var v2Strategy string + if *v2.Spec.Gateway.Enabled { + v2Strategy = "single-host" + } else { + v2Strategy = "multi-host" + } + + if v1Strategy != v2Strategy && v1Strategy != "default-host" { + // we need to reconstruct what the configuration might have looked like in the original + if v1.Spec.Server.ServerExposureStrategy == "" { + if util.IsOpenShift { + v1.Spec.Server.ServerExposureStrategy = v2Strategy + } else { + v1.Spec.K8s.IngressStrategy = v2Strategy + } + } else { + v1.Spec.Server.ServerExposureStrategy = v2Strategy + } + } +} + +func v2alpha1ToV1_GatewayImage(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + v1.Spec.Server.SingleHostGatewayImage = v2.Spec.Gateway.Image +} + +func v2alpha1ToV1_GatewayConfigurerImage(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + v1.Spec.Server.SingleHostGatewayConfigSidecarImage = v2.Spec.Gateway.Image +} + +func v2alpha1ToV1_TlsSecretName(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + if !util.IsOpenShift { + v1.Spec.K8s.TlsSecretName = v2.Spec.TlsSecretName + } +} + +func v2alpha1ToV1_K8sIngressAnnotations(v1 *v1.CheCluster, v2 *v2alpha1.CheCluster) { + ingressClass := v2.Spec.K8s.IngressAnnotations["kubernetes.io/ingress.class"] + if ingressClass == "" { + ingressClass = "nginx" + } + v1.Spec.K8s.IngressClass = ingressClass +} diff --git a/pkg/webhooks/checluster/conversion_test.go b/pkg/webhooks/checluster/conversion_test.go new file mode 100644 index 0000000000..2d9f3968cb --- /dev/null +++ b/pkg/webhooks/checluster/conversion_test.go @@ -0,0 +1,350 @@ +package checluster + +import ( + "reflect" + "testing" + + "github.com/che-incubator/kubernetes-image-puller-operator/pkg/apis/che/v1alpha1" + v1 "github.com/eclipse-che/che-operator/pkg/apis/org/v1" + "github.com/eclipse-che/che-operator/pkg/apis/org/v2alpha1" + "github.com/eclipse-che/che-operator/pkg/util" + "github.com/google/go-cmp/cmp" + "gopkg.in/yaml.v2" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +func TestV1ToV2alpha1(t *testing.T) { + v1Obj := v1.CheCluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: "che-cluster", + Annotations: map[string]string{ + "anno1": "annoValue1", + "anno2": "annoValue2", + }, + }, + Spec: v1.CheClusterSpec{ + Auth: v1.CheClusterSpecAuth{ + IdentityProviderURL: "kachny", + }, + Database: v1.CheClusterSpecDB{ + ExternalDb: true, + PostgresImage: "postgres:the-best-version", + }, + DevWorkspace: v1.CheClusterSpecDevWorkspace{}, + ImagePuller: v1.CheClusterSpecImagePuller{ + Spec: v1alpha1.KubernetesImagePullerSpec{ + ConfigMapName: "pulled-kachna", + }, + }, + K8s: v1.CheClusterSpecK8SOnly{ + IngressDomain: "ingressDomain", + IngressClass: "traefik", + TlsSecretName: "k8sSecret", + IngressStrategy: "single-host", + }, + Metrics: v1.CheClusterSpecMetrics{ + Enable: true, + }, + Server: v1.CheClusterSpecServer{ + CheHost: "cheHost", + CheImage: "teh-che-severe", + SingleHostGatewayImage: "single-host-image-of-the-year", + CustomCheProperties: map[string]string{ + "CHE_INFRA_OPENSHIFT_ROUTE_HOST_DOMAIN__SUFFIX": "routeDomain", + }, + // a nil map gets unmarshalled into an empty map, so just use an empty map here to avoid a diff below + SingleHostGatewayConfigMapLabels: map[string]string{}, + }, + Storage: v1.CheClusterSpecStorage{ + PvcStrategy: "common", + }, + }, + } + + t.Run("origInAnnos", func(t *testing.T) { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + anno1 := v2.Annotations["anno1"] + anno2 := v2.Annotations["anno2"] + storedV1 := v2.Annotations[v1StorageAnnotation] + + if anno1 != "annoValue1" { + t.Errorf("anno1 not copied") + } + + if anno2 != "annoValue2" { + t.Errorf("anno2 not copied") + } + + if storedV1 == "" { + t.Errorf("v2 should contain v1 data in annnotation") + } + + restoredV1Spec := v1.CheClusterSpec{} + yaml.Unmarshal([]byte(storedV1), &restoredV1Spec) + + if !reflect.DeepEqual(&v1Obj.Spec, &restoredV1Spec) { + t.Errorf("The spec should be restored verbatim from the annotations, but there's a diff %s", cmp.Diff(&v1Obj.Spec, &restoredV1Spec)) + } + }) + + t.Run("Host-k8s", func(t *testing.T) { + onFakeKubernetes(func() { + + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.Host != "ingressDomain" { + t.Errorf("Unexpected v2.Spec.Host: %s", v2.Spec.Host) + } + }) + }) + + t.Run("Host-openshift", func(t *testing.T) { + onFakeOpenShift(func() { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.Host != "routeDomain" { + t.Errorf("Unexpected v2.Spec.Host: %s", v2.Spec.Host) + } + }) + }) + + t.Run("GatewayEnabled", func(t *testing.T) { + onFakeOpenShift(func() { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.Gateway.Enabled == nil { + t.Logf("The gateway.enabled attribute should be set explicitly after the conversion.") + t.FailNow() + } + + if *v2.Spec.Gateway.Enabled { + t.Errorf("The default for OpenShift without devworkspace enabled (which is our testing object) is multihost, but we found v2 in singlehost.") + } + }) + }) + + t.Run("GatewayImage", func(t *testing.T) { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.Gateway.Image != "single-host-image-of-the-year" { + t.Errorf("Unexpected gateway image") + } + }) + + t.Run("TlsSecretName_k8s", func(t *testing.T) { + onFakeKubernetes(func() { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.TlsSecretName != "k8sSecret" { + t.Errorf("Unexpected TlsSecretName") + } + }) + }) + + t.Run("TlsSecretName_OpenShift", func(t *testing.T) { + onFakeOpenShift(func() { + v2 := &v2alpha1.CheCluster{} + err := V1ToV2alpha1(&v1Obj, v2) + if err != nil { + t.Error(err) + } + + if v2.Spec.TlsSecretName != "" { + t.Errorf("Unexpected TlsSecretName") + } + }) + }) +} + +func TestV2alpha1ToV1(t *testing.T) { + enabled := true + v2Obj := v2alpha1.CheCluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: "che-cluster", + Annotations: map[string]string{ + "anno1": "annoValue1", + "anno2": "annoValue2", + }, + }, + Spec: v2alpha1.CheClusterSpec{ + Host: "v2Host", + Gateway: v2alpha1.CheGatewaySpec{ + Enabled: &enabled, + Image: "gateway-image", + ConfigurerImage: "configurer-image", + }, + TlsSecretName: "superSecret", + K8s: v2alpha1.CheClusterSpecK8s{ + IngressAnnotations: map[string]string{ + "kubernetes.io/ingress.class": "some-other-ingress", + "a": "b", + }, + }, + }, + } + + t.Run("origInAnnos", func(t *testing.T) { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + anno1 := v1.Annotations["anno1"] + anno2 := v1.Annotations["anno2"] + storedV2 := v1.Annotations[v2alpha1StorageAnnotation] + + if anno1 != "annoValue1" { + t.Errorf("anno1 not copied") + } + + if anno2 != "annoValue2" { + t.Errorf("anno2 not copied") + } + + if storedV2 == "" { + t.Errorf("v1 should contain v2 data in annnotation") + } + + restoredV2Spec := v2alpha1.CheClusterSpec{} + yaml.Unmarshal([]byte(storedV2), &restoredV2Spec) + + if !reflect.DeepEqual(&v2Obj.Spec, &restoredV2Spec) { + t.Errorf("The spec should be restored verbatim from the annotations, but there's a diff %s", cmp.Diff(&v2Obj.Spec, &restoredV2Spec)) + } + }) + + t.Run("Host-k8s", func(t *testing.T) { + onFakeKubernetes(func() { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.K8s.IngressDomain != "v2Host" { + t.Errorf("Unexpected v1.Spec.K8s.IngressDomain: %s", v1.Spec.K8s.IngressDomain) + } + }) + }) + + t.Run("Host-openshift", func(t *testing.T) { + onFakeOpenShift(func() { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.Server.CustomCheProperties[routeDomainSuffixPropertyKey] != "v2Host" { + t.Errorf("Unexpected v1.Spec.Server.CustomCheProperties[%s]: %s", routeDomainSuffixPropertyKey, v1.Spec.Server.CustomCheProperties[routeDomainSuffixPropertyKey]) + } + }) + }) + + t.Run("GatewayEnabled", func(t *testing.T) { + onFakeOpenShift(func() { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.Server.ServerExposureStrategy != "single-host" { + t.Logf("When gateway.enabled is true in v2, v1 is single-host.") + t.FailNow() + } + }) + }) + + t.Run("GatewayImage", func(t *testing.T) { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.Server.SingleHostGatewayImage != "gateway-image" { + t.Errorf("Unexpected gateway image") + } + }) + + t.Run("TlsSecretName_k8s", func(t *testing.T) { + onFakeKubernetes(func() { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.K8s.TlsSecretName != "superSecret" { + t.Errorf("Unexpected TlsSecretName: %s", v1.Spec.K8s.TlsSecretName) + } + }) + }) + + t.Run("TlsSecretName_OpenShift", func(t *testing.T) { + onFakeOpenShift(func() { + v1 := &v1.CheCluster{} + err := V2alpha1ToV1(&v2Obj, v1) + if err != nil { + t.Error(err) + } + + if v1.Spec.K8s.TlsSecretName != "" { + t.Errorf("Unexpected TlsSecretName") + } + }) + }) +} + +func onFakeOpenShift(f func()) { + origOpenshift := util.IsOpenShift + origOpenshift4 := util.IsOpenShift4 + + util.IsOpenShift = true + util.IsOpenShift4 = true + + f() + + util.IsOpenShift = origOpenshift + util.IsOpenShift4 = origOpenshift4 +} + +func onFakeKubernetes(f func()) { + origOpenshift := util.IsOpenShift + origOpenshift4 := util.IsOpenShift4 + + util.IsOpenShift = false + util.IsOpenShift4 = false + + f() + + util.IsOpenShift = origOpenshift + util.IsOpenShift4 = origOpenshift4 +}