Search in sources :

Example 6 with KubernetesInfrastructureException

use of org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException in project devspaces-images by redhat-developer.

the class AsyncStoragePodInterceptor method deleteAsyncStoragePod.

private CompletableFuture<Void> deleteAsyncStoragePod(PodResource<Pod> podResource) throws InfrastructureException {
    Watch toCloseOnException = null;
    try {
        final CompletableFuture<Void> deleteFuture = new CompletableFuture<>();
        final Watch watch = podResource.watch(new DeleteWatcher<>(deleteFuture));
        toCloseOnException = watch;
        Boolean deleteSucceeded = podResource.withPropagationPolicy(BACKGROUND).delete();
        if (deleteSucceeded == null || !deleteSucceeded) {
            deleteFuture.complete(null);
        }
        return deleteFuture.whenComplete((v, e) -> {
            if (e != null) {
                LOG.warn("Failed to remove pod {} cause {}", ASYNC_STORAGE, e.getMessage());
            }
            watch.close();
        });
    } catch (KubernetesClientException e) {
        if (toCloseOnException != null) {
            toCloseOnException.close();
        }
        throw new KubernetesInfrastructureException(e);
    } catch (Exception e) {
        if (toCloseOnException != null) {
            toCloseOnException.close();
        }
        throw e;
    }
}
Also used : CompletableFuture(java.util.concurrent.CompletableFuture) Watch(io.fabric8.kubernetes.client.Watch) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) TimeoutException(java.util.concurrent.TimeoutException) WatcherException(io.fabric8.kubernetes.client.WatcherException) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException) ExecutionException(java.util.concurrent.ExecutionException) InfrastructureException(org.eclipse.che.api.workspace.server.spi.InfrastructureException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException)

Example 7 with KubernetesInfrastructureException

use of org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException in project devspaces-images by redhat-developer.

the class KubernetesDeployments method watchEvents.

/**
 * Registers a specified handler for handling events about changes in pods containers. Registering
 * several handlers doesn't create multiple websocket connections, so it is efficient to call this
 * method several times instead of using composite handler to combine other handlers.
 *
 * @param handler pod container events handler
 * @throws InfrastructureException if any error occurs while watcher starting
 */
public void watchEvents(PodEventHandler handler) throws InfrastructureException {
    if (containerWatch == null) {
        final Watcher<Event> watcher = new Watcher<>() {

            @Override
            public void eventReceived(Action action, Event event) {
                ObjectReference involvedObject = event.getInvolvedObject();
                if (POD_OBJECT_KIND.equals(involvedObject.getKind()) || REPLICASET_OBJECT_KIND.equals(involvedObject.getKind()) || DEPLOYMENT_OBJECT_KIND.equals(involvedObject.getKind())) {
                    String podName = involvedObject.getName();
                    String lastTimestamp = event.getLastTimestamp();
                    if (lastTimestamp == null) {
                        String firstTimestamp = event.getFirstTimestamp();
                        if (firstTimestamp != null) {
                            // Done in the same way like it made in
                            // https://github.com/kubernetes/kubernetes/pull/86557
                            lastTimestamp = firstTimestamp;
                        } else {
                            LOG.debug("lastTimestamp and firstTimestamp are undefined. Event: {}.  Fallback to the current time.", event);
                            lastTimestamp = PodEvents.convertDateToEventTimestamp(new Date());
                        }
                    }
                    PodEvent podEvent = new PodEvent(podName, getContainerName(involvedObject.getFieldPath()), event.getReason(), event.getMessage(), event.getMetadata().getCreationTimestamp(), lastTimestamp);
                    try {
                        if (happenedAfterWatcherInitialization(podEvent)) {
                            containerEventsHandlers.forEach(h -> h.handle(podEvent));
                        }
                    } catch (ParseException e) {
                        LOG.error("Failed to parse last timestamp of the event. Cause: {}. Event: {}", e.getMessage(), podEvent, e);
                    }
                }
            }

            @Override
            public void onClose(WatcherException ignored) {
            }

            /**
             * Returns the container name if the event is related to container. When the event is
             * related to container `fieldPath` field contain information in the following format:
             * `spec.container{web}`, where `web` is container name
             */
            private String getContainerName(String fieldPath) {
                String containerName = null;
                if (fieldPath != null) {
                    Matcher containerFieldMatcher = CONTAINER_FIELD_PATH_PATTERN.matcher(fieldPath);
                    if (containerFieldMatcher.matches()) {
                        containerName = containerFieldMatcher.group(CONTAINER_NAME_GROUP);
                    }
                }
                return containerName;
            }

            /**
             * Returns true if 'lastTimestamp' of the event is *after* the time of the watcher
             * initialization
             */
            private boolean happenedAfterWatcherInitialization(PodEvent event) throws ParseException {
                String eventLastTimestamp = event.getLastTimestamp();
                Date eventLastTimestampDate = PodEvents.convertEventTimestampToDate(eventLastTimestamp);
                return eventLastTimestampDate.after(watcherInitializationDate);
            }
        };
        try {
            watcherInitializationDate = new Date();
            containerWatch = clientFactory.create(workspaceId).v1().events().inNamespace(namespace).watch(watcher);
        } catch (KubernetesClientException ex) {
            throw new KubernetesInfrastructureException(ex);
        }
    }
    containerEventsHandlers.add(handler);
}
Also used : Matcher(java.util.regex.Matcher) Watcher(io.fabric8.kubernetes.client.Watcher) LogWatcher(org.eclipse.che.workspace.infrastructure.kubernetes.namespace.log.LogWatcher) PodEvent(org.eclipse.che.workspace.infrastructure.kubernetes.namespace.event.PodEvent) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) Date(java.util.Date) WatcherException(io.fabric8.kubernetes.client.WatcherException) LocalObjectReference(io.fabric8.kubernetes.api.model.LocalObjectReference) ObjectReference(io.fabric8.kubernetes.api.model.ObjectReference) Event(io.fabric8.kubernetes.api.model.Event) PodEvent(org.eclipse.che.workspace.infrastructure.kubernetes.namespace.event.PodEvent) ParseException(java.text.ParseException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException)

Example 8 with KubernetesInfrastructureException

use of org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException in project devspaces-images by redhat-developer.

the class KubernetesDeployments method delete.

/**
 * Deletes all existing pods and the Deployments that control them.
 *
 * <p>Note that this method will mark Kubernetes pods as interrupted and then will wait until all
 * pods will be killed.
 *
 * @throws InfrastructureException when {@link Thread} is interrupted while command executing
 * @throws InfrastructureException when pods removal timeout is reached
 * @throws InfrastructureException when any other exception occurs
 */
public void delete() throws InfrastructureException {
    try {
        final List<CompletableFuture<Void>> deleteFutures = new ArrayList<>();
        // We first delete all deployments, then clean up any bare Pods.
        List<Deployment> deployments = clientFactory.create(workspaceId).apps().deployments().inNamespace(namespace).withLabel(CHE_WORKSPACE_ID_LABEL, workspaceId).list().getItems();
        for (Deployment deployment : deployments) {
            deleteFutures.add(doDeleteDeployment(deployment.getMetadata().getName()));
        }
        // We have to be careful to not include pods that are controlled by a deployment
        List<Pod> pods = clientFactory.create(workspaceId).pods().inNamespace(namespace).withLabel(CHE_WORKSPACE_ID_LABEL, workspaceId).withoutLabel(CHE_DEPLOYMENT_NAME_LABEL).list().getItems();
        for (Pod pod : pods) {
            List<OwnerReference> ownerReferences = pod.getMetadata().getOwnerReferences();
            if (ownerReferences == null || ownerReferences.isEmpty()) {
                deleteFutures.add(doDeletePod(pod.getMetadata().getName()));
            }
        }
        final CompletableFuture<Void> removed = allOf(deleteFutures.toArray(new CompletableFuture[deleteFutures.size()]));
        try {
            removed.get(POD_REMOVAL_TIMEOUT_MIN, TimeUnit.MINUTES);
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
            throw new InfrastructureException("Interrupted while waiting for pod removal. " + e.getMessage());
        } catch (ExecutionException e) {
            throw new InfrastructureException("Error occurred while waiting for pod removing. " + e.getMessage());
        } catch (TimeoutException ex) {
            throw new InfrastructureException("Pods removal timeout reached " + ex.getMessage());
        }
    } catch (KubernetesClientException e) {
        throw new KubernetesInfrastructureException(e);
    }
}
Also used : Pod(io.fabric8.kubernetes.api.model.Pod) ArrayList(java.util.ArrayList) Deployment(io.fabric8.kubernetes.api.model.apps.Deployment) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) CompletableFuture(java.util.concurrent.CompletableFuture) OwnerReference(io.fabric8.kubernetes.api.model.OwnerReference) ExecutionException(java.util.concurrent.ExecutionException) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) InfrastructureException(org.eclipse.che.api.workspace.server.spi.InfrastructureException) TimeoutException(java.util.concurrent.TimeoutException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException)

Example 9 with KubernetesInfrastructureException

use of org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException in project devspaces-images by redhat-developer.

the class KubernetesIngresses method wait.

public Ingress wait(String name, long timeout, TimeUnit timeoutUnit, Predicate<Ingress> predicate) throws InfrastructureException {
    CompletableFuture<Ingress> future = new CompletableFuture<>();
    Watch watch = null;
    try {
        Resource<Ingress> ingressResource = clientFactory.create(workspaceId).network().v1().ingresses().inNamespace(namespace).withName(name);
        watch = ingressResource.watch(new Watcher<>() {

            @Override
            public void eventReceived(Action action, Ingress ingress) {
                if (predicate.test(ingress)) {
                    future.complete(ingress);
                }
            }

            @Override
            public void onClose(WatcherException cause) {
                future.completeExceptionally(new InfrastructureException("Waiting for ingress '" + name + "' was interrupted"));
            }
        });
        Ingress actualIngress = ingressResource.get();
        if (actualIngress == null) {
            throw new InfrastructureException("Specified ingress " + name + " doesn't exist");
        }
        if (predicate.test(actualIngress)) {
            return actualIngress;
        }
        try {
            return future.get(timeout, timeoutUnit);
        } catch (ExecutionException e) {
            throw new InfrastructureException(e.getCause().getMessage(), e);
        } catch (TimeoutException e) {
            throw new InfrastructureException("Waiting for ingress '" + name + "' reached timeout");
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
            throw new InfrastructureException("Waiting for ingress '" + name + "' was interrupted");
        }
    } catch (KubernetesClientException e) {
        throw new KubernetesInfrastructureException(e);
    } finally {
        if (watch != null) {
            watch.close();
        }
    }
}
Also used : Ingress(io.fabric8.kubernetes.api.model.networking.v1.Ingress) Watcher(io.fabric8.kubernetes.client.Watcher) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) WatcherException(io.fabric8.kubernetes.client.WatcherException) CompletableFuture(java.util.concurrent.CompletableFuture) Watch(io.fabric8.kubernetes.client.Watch) ExecutionException(java.util.concurrent.ExecutionException) InfrastructureException(org.eclipse.che.api.workspace.server.spi.InfrastructureException) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) TimeoutException(java.util.concurrent.TimeoutException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException)

Example 10 with KubernetesInfrastructureException

use of org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException in project devspaces-images by redhat-developer.

the class KubernetesNamespace method waitDefaultServiceAccount.

/**
 * Waits few seconds until 'default' service account become available otherwise an infrastructure
 * exception will be thrown.
 */
protected void waitDefaultServiceAccount(String namespaceName, KubernetesClient client) throws InfrastructureException {
    final Predicate<ServiceAccount> predicate = Objects::nonNull;
    final CompletableFuture<ServiceAccount> future = new CompletableFuture<>();
    Watch watch = null;
    try {
        final Resource<ServiceAccount> saResource = client.serviceAccounts().inNamespace(namespaceName).withName(DEFAULT_SERVICE_ACCOUNT_NAME);
        watch = saResource.watch(new Watcher<>() {

            @Override
            public void eventReceived(Action action, ServiceAccount serviceAccount) {
                if (predicate.test(serviceAccount)) {
                    future.complete(serviceAccount);
                }
            }

            @Override
            public void onClose(WatcherException cause) {
                future.completeExceptionally(new InfrastructureException("Waiting for service account '" + DEFAULT_SERVICE_ACCOUNT_NAME + "' was interrupted"));
            }
        });
        if (predicate.test(saResource.get())) {
            return;
        }
        try {
            future.get(SERVICE_ACCOUNT_READINESS_TIMEOUT_SEC, TimeUnit.SECONDS);
        } catch (ExecutionException ex) {
            throw new InfrastructureException(ex.getCause().getMessage(), ex);
        } catch (TimeoutException ex) {
            throw new InfrastructureException("Waiting for service account '" + DEFAULT_SERVICE_ACCOUNT_NAME + "' reached timeout");
        } catch (InterruptedException ex) {
            Thread.currentThread().interrupt();
            throw new InfrastructureException("Waiting for service account '" + DEFAULT_SERVICE_ACCOUNT_NAME + "' was interrupted");
        }
    } catch (KubernetesClientException ex) {
        throw new KubernetesInfrastructureException(ex);
    } finally {
        if (watch != null) {
            watch.close();
        }
    }
}
Also used : ServiceAccount(io.fabric8.kubernetes.api.model.ServiceAccount) Watcher(io.fabric8.kubernetes.client.Watcher) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) WatcherException(io.fabric8.kubernetes.client.WatcherException) CompletableFuture(java.util.concurrent.CompletableFuture) Watch(io.fabric8.kubernetes.client.Watch) ExecutionException(java.util.concurrent.ExecutionException) KubernetesInfrastructureException(org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException) InternalInfrastructureException(org.eclipse.che.api.workspace.server.spi.InternalInfrastructureException) InfrastructureException(org.eclipse.che.api.workspace.server.spi.InfrastructureException) TimeoutException(java.util.concurrent.TimeoutException) KubernetesClientException(io.fabric8.kubernetes.client.KubernetesClientException)

Aggregations

KubernetesClientException (io.fabric8.kubernetes.client.KubernetesClientException)36 KubernetesInfrastructureException (org.eclipse.che.workspace.infrastructure.kubernetes.KubernetesInfrastructureException)36 InfrastructureException (org.eclipse.che.api.workspace.server.spi.InfrastructureException)26 Watch (io.fabric8.kubernetes.client.Watch)22 CompletableFuture (java.util.concurrent.CompletableFuture)20 ExecutionException (java.util.concurrent.ExecutionException)18 TimeoutException (java.util.concurrent.TimeoutException)18 WatcherException (io.fabric8.kubernetes.client.WatcherException)16 ExecWatch (io.fabric8.kubernetes.client.dsl.ExecWatch)12 Pod (io.fabric8.kubernetes.api.model.Pod)10 Watcher (io.fabric8.kubernetes.client.Watcher)6 ParseException (java.text.ParseException)6 InternalInfrastructureException (org.eclipse.che.api.workspace.server.spi.InternalInfrastructureException)6 Deployment (io.fabric8.kubernetes.api.model.apps.Deployment)4 UnsupportedEncodingException (java.io.UnsupportedEncodingException)4 ArgumentMatchers.anyString (org.mockito.ArgumentMatchers.anyString)4 Test (org.testng.annotations.Test)4 Event (io.fabric8.kubernetes.api.model.Event)2 LocalObjectReference (io.fabric8.kubernetes.api.model.LocalObjectReference)2 Namespace (io.fabric8.kubernetes.api.model.Namespace)2