Source code for controller.commands.swarm.remove

import time
from typing import Dict, List, Union

import typer
from python_on_whales import Service
from python_on_whales.exceptions import DockerException

from controller import RED, REGISTRY, log, print_and_exit
from controller.app import Application, Configuration
from controller.deploy.docker import Docker


[docs] def wait_network_removal(docker: Docker, network: str) -> None: MAX = 30 for i in range(0, MAX): try: for n in docker.client.network.list(): if n.driver == "overlay" and n.name == network: break else: break log.info("Stack is still removing, waiting... [{}/{}]", i + 1, MAX) time.sleep(2) # Can happens when the network is near to be removed and # returned by list but no longer available for inspect # It is assumed to be removed except DockerException: # pragma: no cover break
[docs] @Application.app.command(help="Stop and remove services") def remove( services: List[str] = typer.Argument( None, help="Services to be removed", shell_complete=Application.autocomplete_service, ), ) -> None: Application.print_command(Application.serialize_parameter("", services)) remove_extras: List[str] = [] for extra in ( REGISTRY, "adminer", "swaggerui", ): if services and extra in services: # services is a tuple, even if defined as List[str] ... services = list(services) services.pop(services.index(extra)) remove_extras.append(extra) Application.get_controller().controller_init(services) docker = Docker() if remove_extras: for extra_service in remove_extras: if not docker.client.container.exists(extra_service): log.error("Service {} is not running", extra_service) continue docker.client.container.remove(extra_service, force=True) log.info("Service {} removed", extra_service) # Nothing more to do if not services: return all_services = Application.data.services == Application.data.active_services if all_services: docker.swarm.remove() # This is needed because docker stack remove does not support a --wait flag # To make the remove command sync and chainable with a start command engine = Application.env.get("DEPLOY_ENGINE", "swarm") network_name = f"{Configuration.project}_{engine}_default" wait_network_removal(docker, network_name) log.info("Stack removed") else: if not docker.swarm.stack_is_running(): print_and_exit( "Stack {} is not running, deploy it with {command}", Configuration.project, command=RED("rapydo start"), ) scales: Dict[Union[str, Service], int] = {} for service in Application.data.services: service_name = Docker.get_service(service) scales[service_name] = 0 docker.client.service.scale(scales, detach=False) log.info("Services removed")