If no configuration file is passed to platydock generate a minimal Dockerfile.

This commit is contained in:
Fabio Manganiello 2023-08-20 02:35:25 +02:00
parent 199ac5f0f7
commit 28ba042810
Signed by untrusted user: blacklight
GPG key ID: D90FBA7F76362774
8 changed files with 94 additions and 49 deletions

View file

@ -1,8 +1,12 @@
FROM alpine
ADD . /install
WORKDIR /var/lib/platypush
RUN DOCKER_CTX=1 /install/platypush/install/scripts/alpine/install.sh
ARG DOCKER_CTX=1
ENV DOCKER_CTX=1
RUN /install/platypush/install/scripts/alpine/install.sh
RUN cd /install && pip install -U --no-input --no-cache-dir .
RUN rm -rf /install
@ -11,4 +15,7 @@ EXPOSE 8008
VOLUME /etc/platypush
VOLUME /var/lib/platypush
CMD /run.sh
CMD platypush \
--start-redis \
--config /etc/platypush/config.yaml \
--workdir /var/lib/platypush

View file

@ -1,10 +1,16 @@
FROM debian
ADD . /install
WORKDIR /var/lib/platypush
ARG DEBIAN_FRONTEND=noninteractive
ENV DEBIAN_FRONTEND=noninteractive
ARG DOCKER_CTX=1
ENV DOCKER_CTX=1
RUN apt update
RUN DOCKER_CTX=1 /install/platypush/install/scripts/debian/install.sh
RUN cd /install && pip install -U --no-input --no-cache-dir .
RUN /install/platypush/install/scripts/debian/install.sh
RUN cd /install && pip install -U --no-input --no-cache-dir . --break-system-packages
RUN rm -rf /install
RUN apt autoclean -y
RUN apt autoremove -y
@ -15,4 +21,7 @@ EXPOSE 8008
VOLUME /etc/platypush
VOLUME /var/lib/platypush
CMD /run.sh
CMD platypush \
--start-redis \
--config /etc/platypush/config.yaml \
--workdir /var/lib/platypush

View file

@ -1,9 +1,15 @@
FROM ubuntu
ADD . /install
WORKDIR /var/lib/platypush
ARG DEBIAN_FRONTEND=noninteractive
ENV DEBIAN_FRONTEND=noninteractive
ARG DOCKER_CTX=1
ENV DOCKER_CTX=1
RUN apt update
RUN DOCKER_CTX=1 /install/platypush/install/scripts/debian/install.sh
RUN /install/platypush/install/scripts/debian/install.sh
RUN cd /install && pip install -U --no-input --no-cache-dir .
RUN rm -rf /install
RUN apt autoclean -y
@ -15,4 +21,7 @@ EXPOSE 8008
VOLUME /etc/platypush
VOLUME /var/lib/platypush
CMD /run.sh
CMD platypush \
--start-redis \
--config /etc/platypush/config.yaml \
--workdir /var/lib/platypush

View file

@ -1 +1 @@
DEBIAN_FRONTEND=noninteractive apt install -y
apt install -y

View file

@ -1,8 +0,0 @@
#!/bin/sh
# This script is used as a default entry point for Docker containers
DOCKER_CTX=1 platypush \
--start-redis \
--config /etc/platypush/config.yaml \
--workdir /var/lib/platypush

View file

@ -14,15 +14,9 @@ CMD="$(cat "${SCRIPT_PATH}/PKGCMD")"
REQUIREMENTS="$(cat "${SCRIPT_PATH}/../../requirements/${OS}.txt" | tr '\n' ' ')"
SUDO=
# If we are running in a Docker context then we want to copy the docker-run.sh
# script where we can easily find it.
if [ -n "$DOCKER_CTX" ]; then
cp -v /install/platypush/install/scripts/docker-run.sh /run.sh
fi
# If we aren't running in a Docker context, or the user is not root, we should
# use sudo to install system packages.
if [[ "$(id -u)" != "0" ]] || [ -z "$DOCKER_CTX" ]; then
if [ $(id -u) -ne 0 ] || [ -z "$DOCKER_CTX" ]; then
if ! type sudo >/dev/null; then
echo "sudo executable not found, I can't install system packages" >&2
exit 1

View file

@ -4,7 +4,6 @@ Dockerfile for Platypush starting from a configuration file.
"""
import argparse
from enum import Enum
import inspect
import os
import pathlib
@ -12,23 +11,12 @@ import sys
from typing import Iterable
from platypush.config import Config
from platypush.utils.manifest import Dependencies, InstallContext, PackageManagers
class BaseImage(Enum):
"""
Supported base images for Dockerfiles.
"""
ALPINE = 'alpine'
DEBIAN = 'debian'
UBUNTU = 'ubuntu'
def __str__(self) -> str:
"""
Explicit __str__ override for argparse purposes.
"""
return self.value
from platypush.utils.manifest import (
BaseImage,
Dependencies,
InstallContext,
PackageManagers,
)
# pylint: disable=too-few-public-methods
@ -67,6 +55,7 @@ class DockerfileGenerator:
self.cfgfile,
pkg_manager=pkg_manager,
install_context=InstallContext.DOCKER,
base_image=self.image,
)
is_after_expose_cmd = False
@ -135,7 +124,11 @@ def main():
'-h', '--help', dest='show_usage', action='store_true', help='Show usage'
)
parser.add_argument(
'cfgfile', type=str, nargs='?', help='The path to the configuration file.'
'cfgfile',
type=str,
nargs='?',
help='The path to the configuration file. If not specified a minimal '
'Dockerfile with no extra dependencies will be generated.',
)
parser.add_argument(
'--image',
@ -154,11 +147,15 @@ def main():
return 0
if not opts.cfgfile:
opts.cfgfile = os.path.join(
str(pathlib.Path(inspect.getfile(Config)).parent),
'config.auto.yaml',
)
print(
f'Please specify a configuration file.\nRun {sys.argv[0]} --help to get the available options.',
f'No configuration file specified. Using {opts.cfgfile}.',
file=sys.stderr,
)
return 1
dockerfile = DockerfileGenerator(opts.cfgfile, image=opts.image).generate()
print(dockerfile)

View file

@ -31,6 +31,22 @@ _available_package_manager = None
logger = logging.getLogger(__name__)
class BaseImage(Enum):
"""
Supported base images for Dockerfiles.
"""
ALPINE = 'alpine'
DEBIAN = 'debian'
UBUNTU = 'ubuntu'
def __str__(self) -> str:
"""
Explicit __str__ override for argparse purposes.
"""
return self.value
@dataclass
class PackageManager:
"""
@ -55,7 +71,7 @@ class PackageManagers(Enum):
APT = PackageManager(
executable='apt',
command=('DEBIAN_FRONTEND=noninteractive', 'apt', 'install', '-y'),
command=('apt', 'install', '-y'),
)
PACMAN = PackageManager(
@ -142,6 +158,9 @@ class Dependencies:
pkg_manager: Optional[PackageManagers] = None
""" Override the default package manager detected on the system. """
install_context: InstallContext = InstallContext.NONE
""" The installation context - Docker, virtual environment or bare metal. """
base_image: Optional[BaseImage] = None
""" Base image used in case of Docker installations. """
@property
def _is_venv(self) -> bool:
@ -154,17 +173,34 @@ class Dependencies:
self.install_context == InstallContext.VENV or sys.prefix != sys.base_prefix
)
@property
def _is_docker(self) -> bool:
"""
:return: True if the dependencies scanning logic is running either in a
Docker environment.
"""
return (
self.install_context == InstallContext.DOCKER
or 'DOCKER_CTX' in os.environ
or os.path.isfile('/.dockerenv')
)
@classmethod
def from_config(
cls,
conf_file: Optional[str] = None,
pkg_manager: Optional[PackageManagers] = None,
install_context: InstallContext = InstallContext.NONE,
base_image: Optional[BaseImage] = None,
) -> "Dependencies":
"""
Parse the required dependencies from a configuration file.
"""
deps = cls(pkg_manager=pkg_manager, install_context=install_context)
deps = cls(
pkg_manager=pkg_manager,
install_context=install_context,
base_image=base_image,
)
for manifest in Manifests.by_config(conf_file, pkg_manager=pkg_manager):
deps.before += manifest.install.before
@ -179,7 +215,7 @@ class Dependencies:
Generates the package manager commands required to install the given
dependencies on the system.
"""
wants_sudo = self.install_context != InstallContext.DOCKER and os.getuid() != 0
wants_sudo = not (self._is_docker or os.getuid() == 0)
pkg_manager = self.pkg_manager or PackageManagers.scan()
if self.packages and pkg_manager:
yield ' '.join(
@ -196,8 +232,9 @@ class Dependencies:
the system.
"""
wants_break_system_packages = not (
# Docker installations shouldn't require --break-system-packages in pip
self.install_context == InstallContext.DOCKER
# Docker installations shouldn't require --break-system-packages in
# pip, except for Debian
(self._is_docker and self.base_image != BaseImage.DEBIAN)
# --break-system-packages has been introduced in Python 3.10
or sys.version_info < (3, 11)
# If we're in a virtual environment then we don't need