Files
wago-modbustcp-simulator-py/Dockerfile
T
2026-10-03 18:54:37 +02:00

52 lines
1.9 KiB
Docker

# WAGO 750-362 Modbus TCP simulator — service container
#
# Build: docker build -t wago-sim .
# Run: docker run -d --name wago-sim -p 502:502 \
# -v ./config:/app/config:ro -v ./scenarios:/app/scenarios:ro \
# -e WAGO_SIM_NODE=config/pump_node.yaml \
# -e WAGO_SIM_PORT=502 wago-sim
#
# Or with compose: docker compose up -d
FROM python:3.12-slim AS base
# Don't buffer stdout/stderr — service logs must stream immediately
# WAGO_SIM_VERBOSE=1 enables plain-text Modbus request tracing.
ENV PYTHONUNBUFFERED=1 \
PYTHONDONTWRITEBYTECODE=1 \
WAGO_SIM_NODE=config/pump_node.yaml \
WAGO_SIM_HOST=0.0.0.0 \
WAGO_SIM_PORT=502
WORKDIR /app
# Install the package first (layer caching: dependencies rarely change)
COPY pyproject.toml README.md ./
COPY src ./src
RUN pip install --no-cache-dir .
# Node configurations and scenarios are mounted at runtime;
# the example files are baked in for out-of-the-box startup.
COPY config ./config
COPY scenarios ./scenarios
COPY plugins ./plugins
# Non-root user: the Modbus port (502) is configured via WAGO_SIM_PORT,
# so no privileged ports are needed inside the container.
RUN useradd --system --no-create-home wago-sim \
&& chown -R wago-sim:wago-sim /app
USER wago-sim
# Built-in health check: attempt a TCP connect to the Modbus port.
# A full MBAP request/response would be better, but keep the image slim
# (no curl/wget) — the TCP probe is sufficient for compose/Swarm/K8s
# restart decisions.
HEALTHCHECK --interval=30s --timeout=5s --start-period=5s --retries=3 \
CMD python -c "import socket, os; s=socket.create_connection(('127.0.0.1', int(os.environ['WAGO_SIM_PORT'])), timeout=3); s.close()"
# EXPOSE is documentation only; compose maps the actual port.
# Use 5020 on the host if 502 requires privileges on your machine.
EXPOSE 502
# The console script runs the server until SIGTERM (docker stop).
CMD ["wago-sim", "serve"]