diff --git a/apis/controller/v1alpha1/devworkspacerouting_types.go b/apis/controller/v1alpha1/devworkspacerouting_types.go index b88057e84..80e108f0a 100644 --- a/apis/controller/v1alpha1/devworkspacerouting_types.go +++ b/apis/controller/v1alpha1/devworkspacerouting_types.go @@ -23,6 +23,8 @@ import ( type DevWorkspaceRoutingSpec struct { // Id for the DevWorkspace being routed DevWorkspaceId string `json:"devworkspaceId"` + // Started is true if the owning DevWorkspace has .spec.started=true + Started bool `json:"started"` // Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing RoutingClass DevWorkspaceRoutingClass `json:"routingClass,omitempty"` // Machines to endpoints map diff --git a/controllers/controller/devworkspacerouting/devworkspacerouting_controller.go b/controllers/controller/devworkspacerouting/devworkspacerouting_controller.go index adec686a0..e97b911ea 100644 --- a/controllers/controller/devworkspacerouting/devworkspacerouting_controller.go +++ b/controllers/controller/devworkspacerouting/devworkspacerouting_controller.go @@ -81,6 +81,10 @@ func (r *DevWorkspaceRoutingReconciler) Reconcile(ctx context.Context, req ctrl. // Error reading the object - requeue the request. return reconcile.Result{}, err } + if !instance.Spec.Started { + return reconcile.Result{}, nil + } + reqLogger = reqLogger.WithValues(constants.DevWorkspaceIDLoggerKey, instance.Spec.DevWorkspaceId) reqLogger.Info("Reconciling DevWorkspaceRouting") diff --git a/controllers/workspace/devworkspace_controller.go b/controllers/workspace/devworkspace_controller.go index 312bce996..944018b14 100644 --- a/controllers/workspace/devworkspace_controller.go +++ b/controllers/workspace/devworkspace_controller.go @@ -21,6 +21,7 @@ import ( devfilevalidation "github.com/devfile/api/v2/pkg/validation" + "github.com/devfile/devworkspace-operator/apis/controller/v1alpha1" controllerv1alpha1 "github.com/devfile/devworkspace-operator/apis/controller/v1alpha1" "github.com/devfile/devworkspace-operator/controllers/workspace/metrics" "github.com/devfile/devworkspace-operator/pkg/common" @@ -416,6 +417,25 @@ func (r *DevWorkspaceReconciler) doStop(workspace *dw.DevWorkspace, logger logr. return false, err } + // Update DevWorkspaceRouting to have .spec.started=false + routing := &v1alpha1.DevWorkspaceRouting{} + routingRef := types.NamespacedName{ + Name: common.DevWorkspaceRoutingName(workspace.Status.DevWorkspaceId), + Namespace: workspace.Namespace, + } + err = r.Get(context.TODO(), routingRef, routing) + if err != nil { + if !k8sErrors.IsNotFound(err) { + return false, err + } + } else if routing.Spec.Started { + routing.Spec.Started = false + err := r.Update(context.TODO(), routing) + if err != nil && !k8sErrors.IsConflict(err) { + return false, err + } + } + replicas := workspaceDeployment.Spec.Replicas if replicas == nil || *replicas > 0 { logger.Info("Stopping workspace") diff --git a/deploy/bundle/manifests/controller.devfile.io_devworkspaceroutings.yaml b/deploy/bundle/manifests/controller.devfile.io_devworkspaceroutings.yaml index 67746d3c1..c2de5d679 100644 --- a/deploy/bundle/manifests/controller.devfile.io_devworkspaceroutings.yaml +++ b/deploy/bundle/manifests/controller.devfile.io_devworkspaceroutings.yaml @@ -105,10 +105,14 @@ spec: routingClass: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of DevWorkspaceRouting diff --git a/deploy/deployment/kubernetes/combined.yaml b/deploy/deployment/kubernetes/combined.yaml index 9e24a5849..5af7fc720 100644 --- a/deploy/deployment/kubernetes/combined.yaml +++ b/deploy/deployment/kubernetes/combined.yaml @@ -140,10 +140,14 @@ spec: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of DevWorkspaceRouting diff --git a/deploy/deployment/kubernetes/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml b/deploy/deployment/kubernetes/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml index 3d6b98afd..49339ea6a 100644 --- a/deploy/deployment/kubernetes/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml +++ b/deploy/deployment/kubernetes/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml @@ -140,10 +140,14 @@ spec: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of DevWorkspaceRouting diff --git a/deploy/deployment/openshift/combined.yaml b/deploy/deployment/openshift/combined.yaml index 99f9f463d..e649efaeb 100644 --- a/deploy/deployment/openshift/combined.yaml +++ b/deploy/deployment/openshift/combined.yaml @@ -140,10 +140,14 @@ spec: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of DevWorkspaceRouting diff --git a/deploy/deployment/openshift/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml b/deploy/deployment/openshift/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml index 3d6b98afd..49339ea6a 100644 --- a/deploy/deployment/openshift/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml +++ b/deploy/deployment/openshift/objects/devworkspaceroutings.controller.devfile.io.CustomResourceDefinition.yaml @@ -140,10 +140,14 @@ spec: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of DevWorkspaceRouting diff --git a/deploy/templates/crd/bases/controller.devfile.io_devworkspaceroutings.yaml b/deploy/templates/crd/bases/controller.devfile.io_devworkspaceroutings.yaml index 800863f22..7bff96e20 100644 --- a/deploy/templates/crd/bases/controller.devfile.io_devworkspaceroutings.yaml +++ b/deploy/templates/crd/bases/controller.devfile.io_devworkspaceroutings.yaml @@ -139,10 +139,14 @@ spec: description: 'Class of the routing: this drives which DevWorkspaceRouting controller will manage this routing' type: string + started: + description: Started is true if the owning DevWorkspace has .spec.started=true + type: boolean required: - devworkspaceId - endpoints - podSelector + - started type: object status: description: DevWorkspaceRoutingStatus defines the observed state of diff --git a/pkg/common/naming.go b/pkg/common/naming.go index 662bda160..3cf63c106 100644 --- a/pkg/common/naming.go +++ b/pkg/common/naming.go @@ -20,6 +20,10 @@ import ( var NonAlphaNumRegexp = regexp.MustCompile(`[^a-z0-9]+`) +func DevWorkspaceRoutingName(workspaceId string) string { + return fmt.Sprintf("routing-%s", workspaceId) +} + func EndpointName(endpointName string) string { name := strings.ToLower(endpointName) name = NonAlphaNumRegexp.ReplaceAllString(name, "-") diff --git a/pkg/provision/workspace/routing.go b/pkg/provision/workspace/routing.go index fbca72409..286eb93ad 100644 --- a/pkg/provision/workspace/routing.go +++ b/pkg/provision/workspace/routing.go @@ -21,6 +21,7 @@ import ( "github.com/devfile/devworkspace-operator/apis/controller/v1alpha1" maputils "github.com/devfile/devworkspace-operator/internal/map" + "github.com/devfile/devworkspace-operator/pkg/common" "github.com/devfile/devworkspace-operator/pkg/config" "github.com/devfile/devworkspace-operator/pkg/constants" @@ -169,7 +170,7 @@ func getSpecRouting( routing := &v1alpha1.DevWorkspaceRouting{ ObjectMeta: metav1.ObjectMeta{ - Name: fmt.Sprintf("routing-%s", workspace.Status.DevWorkspaceId), + Name: common.DevWorkspaceRoutingName(workspace.Status.DevWorkspaceId), Namespace: workspace.Namespace, Labels: map[string]string{ constants.DevWorkspaceIDLabel: workspace.Status.DevWorkspaceId, @@ -178,6 +179,7 @@ func getSpecRouting( }, Spec: v1alpha1.DevWorkspaceRoutingSpec{ DevWorkspaceId: workspace.Status.DevWorkspaceId, + Started: workspace.Spec.Started, RoutingClass: v1alpha1.DevWorkspaceRoutingClass(routingClass), Endpoints: endpoints, PodSelector: map[string]string{