132 lines
4.6 KiB
Python
132 lines
4.6 KiB
Python
import logging
|
|
import subprocess
|
|
import os
|
|
import re
|
|
|
|
REGISTRY_URL = "dr.gosrv.ru"
|
|
REGISTRY_LOGIN = "dr_admin"
|
|
REGISTRY_PASSWORD = "Qweasdzxc123C@"
|
|
DOCKER_COMPOSE_FILE_PATH = "/usr/local/share/postinstall/portainer/"
|
|
|
|
|
|
class DockerConfig:
|
|
def check_installed(self, command: str) -> bool:
|
|
try:
|
|
return (
|
|
subprocess.run(
|
|
["which", command], capture_output=True, text=True
|
|
).returncode
|
|
== 0
|
|
)
|
|
except subprocess.SubprocessError as e:
|
|
logging.error(f"Error checking if {command} is installed: {e}")
|
|
return False
|
|
|
|
def install_docker(self):
|
|
try:
|
|
if not self.check_installed("docker"):
|
|
logging.info("Установка Docker...")
|
|
subprocess.run(["apt-get", "update"], check=True)
|
|
subprocess.run(["apt-get", "install", "-y", "docker.io"], check=True)
|
|
logging.info("Docker успешно установился")
|
|
|
|
if not self.check_installed("docker-compose"):
|
|
logging.info("Установка Docker Compose...")
|
|
subprocess.run(
|
|
["apt-get", "install", "-y", "docker-compose"], check=True
|
|
)
|
|
logging.info("Docker Compose успешно установился")
|
|
except subprocess.CalledProcessError as e:
|
|
logging.error(f"Ошибка при установке Docker: {e}")
|
|
raise
|
|
|
|
def check_docker_login(self, registry_url):
|
|
try:
|
|
result = subprocess.run(
|
|
["docker", "login", registry_url, "--password-stdin"],
|
|
input=b"\n",
|
|
capture_output=True,
|
|
text=True,
|
|
check=True,
|
|
)
|
|
return "login succeeded" in result.stdout.lower()
|
|
except subprocess.CalledProcessError as e:
|
|
logging.error(f"Error checking Docker login: {e}")
|
|
return False
|
|
|
|
def login_to_registry(self):
|
|
try:
|
|
if not self.check_docker_login(REGISTRY_URL):
|
|
logging.info("Вход в Docker registry...")
|
|
subprocess.run(
|
|
["docker", "login", REGISTRY_URL],
|
|
input=f"{REGISTRY_LOGIN}\n{REGISTRY_PASSWORD}\n".encode(),
|
|
check=True,
|
|
)
|
|
logging.info("Успешный вход в Docker registry")
|
|
except subprocess.CalledProcessError as e:
|
|
logging.error(f"Ошибка при входе в Docker registry: {e}")
|
|
raise
|
|
|
|
def install_portainer(self, port, login, password, ip):
|
|
try:
|
|
if not self.check_docker_login(REGISTRY_URL):
|
|
self.login_to_registry()
|
|
|
|
os.makedirs(os.path.dirname(DOCKER_COMPOSE_FILE_PATH), exist_ok=True)
|
|
docker_compose_content = f"""
|
|
version: '3'
|
|
|
|
services:
|
|
portainer:
|
|
image: dr.gosrv.ru/portainer
|
|
container_name: portainer
|
|
restart: unless-stopped
|
|
security_opt:
|
|
- no-new-privileges:true
|
|
volumes:
|
|
- /etc/localtime:/etc/localtime:ro
|
|
- /var/run/docker.sock:/var/run/docker.sock:ro
|
|
- portainer_data:/data
|
|
- ./portainer_password:{DOCKER_COMPOSE_FILE_PATH}/portainer_password
|
|
ports:
|
|
- "{ip}:{port}:9000"
|
|
environment:
|
|
- ADMIN_USER={login}
|
|
- ADMIN_PASSWORD_FILE={DOCKER_COMPOSE_FILE_PATH}/portainer_password
|
|
|
|
volumes:
|
|
portainer_data:
|
|
"""
|
|
|
|
with open(DOCKER_COMPOSE_FILE_PATH + "docker-compose.yml", "w") as f:
|
|
f.write(docker_compose_content)
|
|
|
|
subprocess.run(
|
|
["htpasswd", "-nb", login, password],
|
|
stdout=open(DOCKER_COMPOSE_FILE_PATH + "portainer_password", "w"),
|
|
check=True,
|
|
)
|
|
|
|
subprocess.run(
|
|
[
|
|
"docker-compose",
|
|
"-f",
|
|
DOCKER_COMPOSE_FILE_PATH + "docker-compose.yml",
|
|
"up",
|
|
"-d",
|
|
],
|
|
check=True,
|
|
)
|
|
logging.info("Portainer успешно установлен")
|
|
except subprocess.CalledProcessError as e:
|
|
logging.error(f"Ошибка при установке Portainer: {e}")
|
|
raise
|
|
except IOError as e:
|
|
logging.error(f"Ошибка при создании файла: {e}")
|
|
raise
|
|
|
|
def validate_input(self, value, pattern, error_message):
|
|
if not re.match(pattern, value):
|
|
return False
|
|
return True
|