cmdeploy: consolidate container detection into is_in_container() helper

This commit is contained in:
j4n
2026-04-14 16:14:59 +02:00
parent cef739e3b3
commit 2bdfecff72
3 changed files with 18 additions and 15 deletions

View File

@@ -3,6 +3,8 @@ import io
import os import os
from contextlib import contextmanager from contextlib import contextmanager
from pyinfra import host
from pyinfra.facts.server import Command
from pyinfra.operations import files, server, systemd from pyinfra.operations import files, server, systemd
@@ -11,6 +13,17 @@ def has_systemd():
return os.path.isdir("/run/systemd/system") return os.path.isdir("/run/systemd/system")
def is_in_container() -> bool:
"""Return True if running inside a container (Docker, LXC, etc.)."""
return (
host.get_fact(
Command,
"systemd-detect-virt --container --quiet 2>/dev/null && echo yes || true",
)
== "yes"
)
@contextmanager @contextmanager
def blocked_service_startup(): def blocked_service_startup():
"""Prevent services from auto-starting during package installation. """Prevent services from auto-starting during package installation.

View File

@@ -2,7 +2,6 @@
Chat Mail pyinfra deploy. Chat Mail pyinfra deploy.
""" """
import os
import shutil import shutil
import subprocess import subprocess
import sys import sys
@@ -28,6 +27,7 @@ from .basedeploy import (
configure_remote_units, configure_remote_units,
get_resource, get_resource,
has_systemd, has_systemd,
is_in_container,
) )
from .dovecot.deployer import DovecotDeployer from .dovecot.deployer import DovecotDeployer
from .external.deployer import ExternalTlsDeployer from .external.deployer import ExternalTlsDeployer
@@ -584,7 +584,7 @@ def deploy_chatmail(config_path: Path, disable_mail: bool, website_only: bool) -
Out().red(f"Deploy failed: mtail_address {config.mtail_address} is not available (VPN up?).\n") Out().red(f"Deploy failed: mtail_address {config.mtail_address} is not available (VPN up?).\n")
exit(1) exit(1)
if not os.environ.get("CHATMAIL_NOPORTCHECK"): if not is_in_container():
port_services = [ port_services = [
(["master", "smtpd"], 25), (["master", "smtpd"], 25),
("unbound", 53), ("unbound", 53),

View File

@@ -4,7 +4,7 @@ import urllib.request
from chatmaild.config import Config from chatmaild.config import Config
from pyinfra import host from pyinfra import host
from pyinfra.facts.deb import DebPackages from pyinfra.facts.deb import DebPackages
from pyinfra.facts.server import Arch, Command, Sysctl from pyinfra.facts.server import Arch, Sysctl
from pyinfra.operations import apt, files, server, systemd from pyinfra.operations import apt, files, server, systemd
from cmdeploy.basedeploy import ( from cmdeploy.basedeploy import (
@@ -13,6 +13,7 @@ from cmdeploy.basedeploy import (
blocked_service_startup, blocked_service_startup,
configure_remote_units, configure_remote_units,
get_resource, get_resource,
is_in_container,
) )
DOVECOT_ARCHIVE_VERSION = "2.3.21+dfsg1-3" DOVECOT_ARCHIVE_VERSION = "2.3.21+dfsg1-3"
@@ -136,17 +137,6 @@ def _download_dovecot_package(package: str, arch: str) -> tuple[str | None, bool
return deb_filename, True return deb_filename, True
def _can_set_inotify_limits() -> bool:
is_container = (
host.get_fact(
Command,
"systemd-detect-virt --container --quiet 2>/dev/null && echo yes || true",
)
== "yes"
)
return not is_container
def _configure_dovecot(config: Config, debug: bool = False) -> tuple[bool, bool]: def _configure_dovecot(config: Config, debug: bool = False) -> tuple[bool, bool]:
"""Configures Dovecot IMAP server.""" """Configures Dovecot IMAP server."""
need_restart = False need_restart = False
@@ -182,7 +172,7 @@ def _configure_dovecot(config: Config, debug: bool = False) -> tuple[bool, bool]
# as per https://doc.dovecot.org/2.3/configuration_manual/os/ # as per https://doc.dovecot.org/2.3/configuration_manual/os/
# it is recommended to set the following inotify limits # it is recommended to set the following inotify limits
can_modify = _can_set_inotify_limits() can_modify = not is_in_container()
for name in ("max_user_instances", "max_user_watches"): for name in ("max_user_instances", "max_user_watches"):
key = f"fs.inotify.{name}" key = f"fs.inotify.{name}"
value = host.get_fact(Sysctl)[key] value = host.get_fact(Sysctl)[key]