diff --git a/sample-docker-templates/django/Dockerfile b/sample-docker-templates/django/Dockerfile index b84c90ebe6..cdd532c72e 100644 --- a/sample-docker-templates/django/Dockerfile +++ b/sample-docker-templates/django/Dockerfile @@ -1,13 +1,12 @@ -# Dockerfile - # Base Image -FROM python:3.8 +# Using official python 3.13-slim for smaller footprint and latest stable version +FROM python:3.13-slim -# set default environment variables -ENV PYTHONUNBUFFERED 1 -ENV LANG C.UTF-8 +# Set environment variables for Python behavior +ENV PYTHONUNBUFFERED=1 +ENV LANG=C.UTF-8 -# to take runtime arguments and set env variables +# Accept build arguments for Django superuser creation ARG DJANGO_SUPERUSER_USERNAME ENV DJANGO_SUPERUSER_USERNAME=${DJANGO_SUPERUSER_USERNAME} @@ -17,32 +16,40 @@ ENV DJANGO_SUPERUSER_PASSWORD=${DJANGO_SUPERUSER_PASSWORD} ARG DJANGO_SUPERUSER_EMAIL ENV DJANGO_SUPERUSER_EMAIL=${DJANGO_SUPERUSER_EMAIL} -# create and set working directory +# Create app directory and assign ownership later to non-root user RUN mkdir /app + WORKDIR /app -RUN chown -R www-data:www-data /app +# Install system dependencies and nginx with minimal packages, no recommends +RUN apt-get update && apt-get install -y --no-install-recommends nginx vim && \ + rm -rf /var/lib/apt/lists/* -# Add current directory code to working directory +# Copy app source code COPY . /app/ -# install environment dependencies -RUN pip install -r requirements.txt +# Install Python dependencies +RUN pip install --no-cache-dir -r requirements.txt -# install nginx -RUN apt-get update && apt-get install nginx vim -y --no-install-recommends +# Create a non-root user 'nonroot' and group, change ownership of /app and nginx logs +RUN groupadd -r nonroot && useradd -r -g nonroot nonroot && \ + chown -R nonroot:nonroot /app /var/log/nginx -#Refer https://github.com/devtron-labs/devtron/blob/main/sample-docker-templates/django/nginx.default for sample nginx.default file +# Copy nginx config file COPY nginx.default /etc/nginx/sites-available/default -RUN ln -sf /dev/stdout /var/log/nginx/access.log \ - && ln -sf /dev/stderr /var/log/nginx/error.log +# Symlink nginx logs to stdout/stderr for container logging +RUN ln -sf /dev/stdout /var/log/nginx/access.log && \ + ln -sf /dev/stderr /var/log/nginx/error.log - -# start server +# Expose port 8000 for Django/gunicorn and nginx EXPOSE 8000 +# Use non-root user for better security +USER nonroot + +# Set stop signal for graceful shutdown STOPSIGNAL SIGTERM -# Refer https://github.com/devtron-labs/devtron/blob/main/sample-docker-templates/django/start-server.sh for sample start-server.sh file -CMD ["/app/start-server.sh"] \ No newline at end of file +# Start server script (migrations, superuser creation, gunicorn & nginx) +CMD ["/app/start-server.sh"] diff --git a/sample-docker-templates/django/start-server.sh b/sample-docker-templates/django/start-server.sh index fa9671fede..5e59ce4446 100755 --- a/sample-docker-templates/django/start-server.sh +++ b/sample-docker-templates/django/start-server.sh @@ -1,22 +1,15 @@ -#!/usr/bin/env bash -# -# Copyright (c) 2024. Devtron Inc. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# +#!/bin/sh -# start-server.sh -python manage.py migrate -python manage.py createsuperuser --no-input +# Apply DB migrations +python manage.py migrate -(gunicorn DjangoApp.wsgi --user www-data --bind 0.0.0.0:8000 --workers 3) && nginx -g "daemon off;" +# Create superuser if details provided (non-interactive) +if [ -n "$DJANGO_SUPERUSER_USERNAME" ] && [ -n "$DJANGO_SUPERUSER_PASSWORD" ] && [ -n "$DJANGO_SUPERUSER_EMAIL" ]; then + python manage.py createsuperuser --no-input || true +fi + +# Start gunicorn as non-root user binding on all interfaces port 8000, 3 workers +gunicorn DjangoApp.wsgi --user nonroot --bind 0.0.0.0:8000 --workers 3 & + +# Start nginx in foreground +nginx -g "daemon off;" diff --git a/sample-docker-templates/flask/Dockerfile b/sample-docker-templates/flask/Dockerfile index ad20d787cc..bcdcbc6d6b 100644 --- a/sample-docker-templates/flask/Dockerfile +++ b/sample-docker-templates/flask/Dockerfile @@ -1,39 +1,50 @@ -#Base Image -FROM python:3.8 - -#Getting System Ready to install dependencies -RUN apt-get clean \ - && apt-get -y update - -#Installing nginx -RUN apt-get -y install nginx \ - && apt-get -y install python3-dev \ - && apt-get -y install build-essential - -#Creating symbolic link for access and error log from nginx -RUN ln -sf /dev/stdout /var/log/nginx/access.log \ - && ln -sf /dev/stderr /var/log/nginx/error.log - -#Creating a dir in Container -RUN mkdir /app - -#Moving into the directory created +# Base Image - Using python:3.13-slim for reduced image size +FROM python:3.13-slim + +# Set environment variables +ENV PYTHONUNBUFFERED=1 +ENV LANG=C.UTF-8 + +# Install system dependencies (nginx, build tools) without recommended packages to keep image small +RUN apt-get update && \ + apt-get install -y --no-install-recommends \ + nginx \ + python3-dev \ + build-essential \ + # Clean up to reduce image size + && rm -rf /var/lib/apt/lists/* + +# Symlink nginx logs to stdout/stderr for containerized log access +RUN ln -sf /dev/stdout /var/log/nginx/access.log && \ + ln -sf /dev/stderr /var/log/nginx/error.log + +# Create application directory +RUN mkdir -p /app + +# Set working directory WORKDIR /app -#Changing ownership of files in /app -RUN chown -R www-data:www-data /app +# Add application code +COPY . /app/ -#Adding the complete project in dir created -ADD . /app/ +# Install Python dependencies +RUN pip install --no-cache-dir -r requirements.txt -#Installing dependencies -RUN pip3 install -r requirements.txt - -# Refer https://raw.githubusercontent.com/devtron-labs/devtron/main/sample-docker-templates/flask/nginx.default for sample nginx.default file +# Copy nginx config COPY nginx.default /etc/nginx/sites-available/default -#Refer https://raw.githubusercontent.com/devtron-labs/devtron/main/sample-docker-templates/flask/start.sh for sample start.sh file -#Making start.sh executable +# Make start.sh executable RUN chmod +x ./start.sh +# Create a non-root user and change ownership of /app to that user +RUN groupadd -r nonroot && useradd -r -g nonroot nonroot && \ + chown -R nonroot:nonroot /app /var/log/nginx + +# Expose port 80 (used by nginx) +EXPOSE 80 + +# Switch to non-root user for better container security +USER nonroot + +# Run app with start.sh CMD ["./start.sh"] diff --git a/sample-docker-templates/flask/start.sh b/sample-docker-templates/flask/start.sh index ef72c97d44..777905edea 100644 --- a/sample-docker-templates/flask/start.sh +++ b/sample-docker-templates/flask/start.sh @@ -1,22 +1,8 @@ -#!/usr/bin/env bash -# -# Copyright (c) 2024. Devtron Inc. -# -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# - -service nginx start -# Refer https://raw.githubusercontent.com/devtron-labs/devtron/main/sample-docker-templates/flask/uwsgi.ini for sample uwsgi.ini file -uwsgi --ini uwsgi.ini +#!/bin/bash +set -e +# Start nginx in the background +nginx +# Start uwsgi with provided ini config +exec uwsgi --ini uwsgi.ini diff --git a/sample-docker-templates/flask/uwsgi.ini b/sample-docker-templates/flask/uwsgi.ini index 9d73c94025..df30ced52f 100644 --- a/sample-docker-templates/flask/uwsgi.ini +++ b/sample-docker-templates/flask/uwsgi.ini @@ -1,14 +1,15 @@ [uwsgi] module = app:app -uid = www-data -gid = www-data + master = true processes = 5 socket = /tmp/uwsgi.socket -chmod-sock = 664 +chmod-socket = 664 vacuum = true die-on-term = true - +# Run as non-root user +uid = nonroot +gid = nonroot diff --git a/sample-docker-templates/go/Dockerfile b/sample-docker-templates/go/Dockerfile index d868e7c930..5cb93d47bd 100644 --- a/sample-docker-templates/go/Dockerfile +++ b/sample-docker-templates/go/Dockerfile @@ -1,36 +1,41 @@ -################################# Build Container ############################### +################################# Build Container ################################# -FROM golang:1.16 as builder +# Use the latest stable Go image for building +FROM golang:1.22.3 AS builder -# Setup the working directory +# Set working directory inside the container WORKDIR /app -# COPY go module -COPY go.mod go.sum /app/ - -# Download go modules and cache for next time build +# Copy Go module files and download dependencies +COPY go.mod go.sum ./ RUN go mod download -# Add source code -ADD . /app/ +# Copy the entire source code into the container +COPY . . -# Build the source +# Build the Go binary with CGO disabled for static linking RUN CGO_ENABLED=0 GOOS=linux go build -a -installsuffix cgo -o main app.go +################################# Production Container ############################ -################################# Prod Container ################################# +# Use a minimal and secure Alpine base image +FROM alpine:3.20 -# Use a minimal alpine image -FROM alpine:3.7 +# Install CA certificates (for HTTPS calls) +RUN apk --no-cache add ca-certificates -# Add ca-certificates in case you need them -RUN apk update && apk add ca-certificates && rm -rf /var/cache/apk/* +# Create a non-root user and switch to it +RUN adduser -D -g '' nonroot +USER nonroot # Set working directory -WORKDIR /root +WORKDIR /home/nonroot -# Copy the binary from builder +# Copy the compiled binary from the builder stage COPY --from=builder /app/main . -# Run the binary -CMD ["./main"] \ No newline at end of file +# Expose port if your app serves over a specific port (optional) +# EXPOSE 8080 + +# Start the application +CMD ["./main"] diff --git a/sample-docker-templates/java/Gradle_Dockerfile b/sample-docker-templates/java/Gradle_Dockerfile index 30945dc67d..96df2f0f79 100644 --- a/sample-docker-templates/java/Gradle_Dockerfile +++ b/sample-docker-templates/java/Gradle_Dockerfile @@ -1,30 +1,37 @@ ################################# Build Container ############################### -# Base Image of Build Container -FROM gradle:4.7.0-jdk8-alpine AS build +# Use latest Gradle with JDK 21 and Alpine for minimal size and speed +FROM gradle:8.13.0-jdk21-alpine AS build -# Changing the ownership of file and copying files in container +# Set working directory and ensure proper permissions COPY --chown=gradle:gradle . /home/gradle/src - -# Moving into workdir WORKDIR /home/gradle/src -# Compiling & building the code -RUN gradle build --no-daemon +# Build the application without using the Gradle daemon +RUN gradle build --no-daemon ################################# Prod Container ################################# -# Base Image for Prod Container -FROM openjdk:8-jre-slim +# Use a minimal JDK base image for production +FROM eclipse-temurin:21-jdk-jammy -# Exposing Port of this container -EXPOSE 8080 +# Create a non-root user to run the app securely +RUN addgroup -g 2002 nonroot && adduser -u 2002 -G nonroot -S nonroot + +# Set the working directory +WORKDIR /app -# Creating a dir -RUN mkdir /app +# Copy the JAR file from the build stage +COPY --from=build /home/gradle/src/build/libs/*.jar /app/demo.jar -# Copying only the jar files created before -COPY --from=build /home/gradle/src/build/libs/*.jar /app/my-app.jar +# Set ownership of the jar file +RUN chown nonroot:nonroot /app/demo.jar + +# Switch to non-root user +USER nonroot + +# Expose the application port +EXPOSE 8080 -# Uncomment if you want to run default commands during the initialization of this container -# CMD exec java -jar /app/my-app.jar \ No newline at end of file +# Run the jar file +CMD ["java", "-jar", "/app/demo.jar"] diff --git a/sample-docker-templates/java/Maven_Dockerfile b/sample-docker-templates/java/Maven_Dockerfile index 52d7181417..ce8e6398bf 100644 --- a/sample-docker-templates/java/Maven_Dockerfile +++ b/sample-docker-templates/java/Maven_Dockerfile @@ -1,33 +1,45 @@ ################################# Build Container ############################### -# Base Image for Build Container -FROM maven:3.5.3-jdk-8-alpine as base +# Use latest Maven with Amazon Corretto 21 on Debian for consistent build environment +FROM maven:3.9.9-amazoncorretto-21-debian as base -# Moving into working directory +# Set working directory inside container WORKDIR /build -# Copying pom.xml file initially for caching +# Copy pom.xml separately to leverage Docker cache for dependencies COPY pom.xml . -# Downloading Dependencies +# Download dependencies for offline use RUN mvn dependency:go-offline -# Copying files to /build/src/ inside container +# Copy the source code to container COPY src/ /build/src/ -# Building package -RUN mvn package +# Build the project and package the application +RUN mvn clean package ################################# Prod Container ################################# -# Base Image for Prod Container -FROM openjdk:8-jre-alpine +# Use a slim OpenJDK 21 image based on Debian for production +FROM eclipse-temurin:21-jdk-jammy -# Exposing Port of this new container -EXPOSE 4567 +# Create a non-root user 'nonroot' for security best practices +RUN addgroup -g 2002 nonroot && adduser -u 2002 -G nonroot -S nonroot -# Copying the executable jar file build on previous container -COPY --from=base /build/target/*.jar /app/my-app.jar +# Set working directory +WORKDIR /app -# Uncomment if you want to run default commands during the initialization of this container -# CMD exec java -jar /app/my-app.jar \ No newline at end of file +# Copy the built jar from build stage +COPY --from=base /build/target/*.jar /app/demo.jar + +# Change ownership to non-root user +RUN chown nonroot:nonroot /app/demo.jar + +# Switch to non-root user +USER nonroot + +# Expose the port the app listens on +EXPOSE 8080 + +# Default command to run the jar file +CMD ["java", "-jar", "/app/demo.jar"] diff --git a/sample-docker-templates/kotlin/Dockerfile b/sample-docker-templates/kotlin/Dockerfile index 198db63704..ca63ec6ce2 100644 --- a/sample-docker-templates/kotlin/Dockerfile +++ b/sample-docker-templates/kotlin/Dockerfile @@ -1,41 +1,44 @@ -# Using Base image -FROM alpine:latest +# Use specific Alpine version (3.21) for stability and reproducibility +FROM alpine:3.21 -# Build args +# Metadata args for build info (optional) ARG VCS_REF ARG BUILD_DATE -# Setting resource quota +# Setting resource quota args (optional, for your usage) ARG MIN_MEM=2G ARG MAX_MEM=2G -RUN apk add --update bash && \ - apk fetch openjdk8 && \ - apk add --no-cache openjdk8; +# Install required packages: bash, openjdk8, unzip, build-base, wget +RUN apk add --no-cache bash openjdk8 unzip build-base wget -RUN apk add --no-cache build-base wget && \ - cd /usr/lib && \ - # Installing Kotlin compiler in zip file - wget 'https://github.com/JetBrains/kotlin/releases/download/v1.3.72/kotlin-compiler-1.3.72.zip' && \ - # Unzipping the downloaded zip file - unzip kotlin-compiler-*.zip && \ - rm kotlin-compiler-*.zip && \ - rm -f kotlinc/bin/*.bat; +# Download and install Kotlin compiler +RUN cd /usr/lib && \ + wget https://github.com/JetBrains/kotlin/releases/download/v1.3.72/kotlin-compiler-1.3.72.zip && \ + unzip kotlin-compiler-1.3.72.zip && \ + rm kotlin-compiler-1.3.72.zip && \ + rm -f kotlinc/bin/*.bat -# Setting up environmental variable path -ENV PATH $PATH:/usr/lib/kotlinc/bin +# Add Kotlin compiler to PATH +ENV PATH="/usr/lib/kotlinc/bin:${PATH}" -# Making a directory named 'app' in the container -RUN mkdir app +# Create app directory and set permissions +RUN mkdir /app -# Copying 'app.kt' from 'app' folder on host to recently created 'app' folder in container -COPY app/app.kt /app +# Copy source code into container +COPY app/app.kt /app/ # Set working directory WORKDIR /app -# Compiling source +# Create a non-root user 'nonroot' and assign ownership of /app to it +RUN adduser -D nonroot && chown -R nonroot:nonroot /app + +# Switch to non-root user +USER nonroot + +# Compile Kotlin source to jar RUN kotlinc app.kt -include-runtime -d app.jar -# Execution -CMD ["java","-jar","./app.jar"] \ No newline at end of file +# Run the compiled jar +CMD ["java", "-jar", "./app.jar"] diff --git a/sample-docker-templates/node/Dockerfile b/sample-docker-templates/node/Dockerfile index 123a903771..746403165d 100644 --- a/sample-docker-templates/node/Dockerfile +++ b/sample-docker-templates/node/Dockerfile @@ -1,36 +1,43 @@ -# Base Image -From node:12.18.1 +# Use a minimal Node.js base image +FROM node:22-alpine -# Seeting up env as production +# Set environment for production ENV NODE_ENV=production -#Getting System Ready to install dependencies -RUN apt-get clean \ - && apt-get -y update - -# Installing nginx -RUN apt-get -y install nginx \ - && apt-get -y install python3-dev \ - && apt-get -y install build-essential +# Install necessary packages: nginx only +RUN apk update && apk add --no-cache nginx -# Creating symbolic link for access and error log from nginx -RUN ln -sf /dev/stdout /var/log/nginx/access.log \ - && ln -sf /dev/stderr /var/log/nginx/error.log +# Set working directory +WORKDIR /app +# Copy application code +COPY . . -# Making /app dir as working dir -WORKDIR /app +# Main global config +COPY nginx.conf /etc/nginx/nginx.conf + +# Default server/site config +COPY nginx-default.conf /etc/nginx/http.d/default.conf + +# Install production dependencies +RUN npm install --production --prefer-offline --no-audit && \ + npm i -g pm2 -# Adding complete files and dirs in app dir in container -ADD . /app/ +# Create non-root user and set permissions +RUN addgroup -g 2002 nonroot && \ + adduser -u 2002 -G nonroot -S nonroot && \ + mkdir -p /var/lib/nginx/tmp/client_body && \ + chown -R nonroot:nonroot /app /var/log/nginx /var/lib/nginx -# Refer https://raw.githubusercontent.com/devtron-labs/devtron/main/sample-docker-templates/node/nginx.default for sample nginx.default -COPY nginx.default /etc/nginx/sites-available/default +# Expose port 8080 +EXPOSE 8080 -# Installing dependencies -RUN npm install --production -RUN npm i -g pm2 +# Switch to non-root user +USER nonroot -# Starting Server -CMD ["sh", "-c", "service nginx start ; pm2-runtime src/index.js -i 0"] +# Link logs to stdout/stderr +RUN ln -sf /dev/stdout /var/log/nginx/access.log && \ + ln -sf /dev/stderr /var/log/nginx/error.log +# Start your app listening on port 8080 +CMD ["sh", "-c", "nginx && pm2-runtime src/index.js -i 0 --port=8080"] \ No newline at end of file diff --git a/sample-docker-templates/node/nginx-default.conf b/sample-docker-templates/node/nginx-default.conf new file mode 100644 index 0000000000..fd1cac68a1 --- /dev/null +++ b/sample-docker-templates/node/nginx-default.conf @@ -0,0 +1,34 @@ +# This contains a server block defining how a specific domain/route should be handled. +# nginx-default.conf + +# To allow a non-root container process to bind to privileged ports (e.g., 80 or 443), +# you need to add the NET_BIND_SERVICE capability to the security context: +# +# securityContext: +# allowPrivilegeEscalation: false +# capabilities: +# add: +# - NET_BIND_SERVICE +# drop: +# - ALL +# +# Since adding capabilities may reduce security or require extra setup in Kubernetes, +# it's simpler and safer to use an unprivileged port like 8080 for your app. + + +server { + listen 8080; + listen [::]:8080; + root /app; + server_name localhost; + + + location / { + proxy_set_header Host $host; + proxy_set_header X-Real-IP $remote_addr; + proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; + proxy_set_header X-Forwarded-Proto $scheme; + proxy_pass http://127.0.0.1:3000; + } + +} \ No newline at end of file diff --git a/sample-docker-templates/node/nginx.conf b/sample-docker-templates/node/nginx.conf new file mode 100644 index 0000000000..40a22b8fa2 --- /dev/null +++ b/sample-docker-templates/node/nginx.conf @@ -0,0 +1,23 @@ +# This is the global Nginx configuration file (typically contains user, worker_processes, http block, etc.) +# /etc/nginx/nginx.conf + +# user nginx; +worker_processes auto; +error_log /var/log/nginx/error.log notice; +pid /tmp/nginx.pid; +events { + worker_connections 1024; +} + +http { + include /etc/nginx/mime.types; + default_type application/octet-stream; + + access_log /var/log/nginx/access.log; + error_log /var/log/nginx/error.log; + + sendfile on; + keepalive_timeout 65; + + include /etc/nginx/http.d/*.conf; +} diff --git a/sample-docker-templates/node/nginx.default b/sample-docker-templates/node/nginx.default deleted file mode 100644 index 831c838473..0000000000 --- a/sample-docker-templates/node/nginx.default +++ /dev/null @@ -1,17 +0,0 @@ -# nginx.default - -server { - listen 80; - listen [::]:80; - server_name example.org; - root /app; - - location / { - proxy_set_header Host $host; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; - proxy_set_header X-Forwarded-Proto $scheme; - proxy_pass http://127.0.0.1:3000; - } - -} diff --git a/sample-docker-templates/php/Apache_Dockerfile b/sample-docker-templates/php/Apache_Dockerfile index 66d9b684b8..b5dfe4133a 100644 --- a/sample-docker-templates/php/Apache_Dockerfile +++ b/sample-docker-templates/php/Apache_Dockerfile @@ -1,16 +1,17 @@ -# Base Image -FROM php:7-apache +# Using latest stable PHP with Apache (8.2) +FROM php:8.2-apache -# Enabling modules from /etc/apache2/mods-available to /etc/apache2/mods-enabled +# Enable apache mod_rewrite RUN a2enmod rewrite -# Restarting apache2 server -RUN /etc/init.d/apache2 restart +# Give ownership of /var/www/html to non-root user +RUN useradd -m nonroot && chown -R nonroot:www-data /var/www/html -# Giving ownship of html dir to www-data user -RUN chown -R www-data:www-data /var/www/html +# Copy application source code +COPY --chown=nonroot:www-data . /var/www/html/ +# Switch to non-root user for security +USER nonroot -# Copy application source -COPY . /var/www/html/ - +# Apache runs as www-data internally, so no need to restart here +# CMD is inherited from base image and will run apache2 in foreground by default diff --git a/sample-docker-templates/php/Nginx_Dockerfile b/sample-docker-templates/php/Nginx_Dockerfile index 1a925599af..5e4cb4edc7 100644 --- a/sample-docker-templates/php/Nginx_Dockerfile +++ b/sample-docker-templates/php/Nginx_Dockerfile @@ -1,31 +1,15 @@ -# base image -FROM ubuntu:16.04 +# Use Ubuntu 24.04 LTS as base image for latest stable environment +FROM ubuntu:24.04 -# update & install system -RUN apt-get update -RUN apt-get -y upgrade +RUN apt-get update && apt-get upgrade -y && \ + apt-get install -y php8.2 php8.2-cli php8.2-fpm nginx && \ + apt-get clean && rm -rf /var/lib/apt/lists/* -# installing packages -RUN DEBIAN_FRONTEND=noninteractive apt-get install -y --fix-missing php7.0 \ - php7.0-cli \ - php-fpm - -RUN DEBIAN_FRONTEND="noninteractive" apt-get install -y nginx-full - -# copying nginx conf to its path +# Copy configs, code, etc. COPY nginx-site.conf /etc/nginx/sites-available/default - -# setting working dir WORKDIR /var/www/html/ - -# creating nested dir where fpm service would be found -RUN mkdir -p /run/php - -# copying static files to location COPY . /var/www/html -# service exposed EXPOSE 80 -# executing command -CMD ["/bin/bash", "-c", "service php7.0-fpm start && nginx -g \"daemon off;\""] \ No newline at end of file +CMD ["/bin/bash", "-c", "service php8.2-fpm start && nginx -g 'daemon off;'"] diff --git a/sample-docker-templates/php/php7.4/Dockerfile b/sample-docker-templates/php/php7.4/Dockerfile index ddff47d9fe..8a2fd72567 100644 --- a/sample-docker-templates/php/php7.4/Dockerfile +++ b/sample-docker-templates/php/php7.4/Dockerfile @@ -1,16 +1,18 @@ -FROM ubuntu:20.04 +FROM ubuntu:24.04 -RUN apt-get update -RUN apt-get -y upgrade +ENV DEBIAN_FRONTEND=noninteractive -RUN DEBIAN_FRONTEND=noninteractive apt-get install -y --fix-missing php7.4 \ - php7.4-cli \ - php-fpm \ - php7.4-mysql \ - php7.4-curl \ - net-tools +RUN apt-get update && apt-get -y upgrade && \ + apt-get install -y --no-install-recommends \ + php8.2 \ + php8.2-cli \ + php8.2-fpm \ + php8.2-mysql \ + php8.2-curl \ + net-tools \ + nginx && \ + apt-get clean && rm -rf /var/lib/apt/lists/* -RUN DEBIAN_FRONTEND="noninteractive" apt-get install -y nginx-full ADD nginx-site.conf /etc/nginx/sites-available/default WORKDIR /var/www/html/ @@ -21,4 +23,4 @@ COPY . /var/www/html EXPOSE 80 -CMD ["/bin/bash", "-c", "service php7.4-fpm start && nginx -g \"daemon off;\""] \ No newline at end of file +CMD ["/bin/bash", "-c", "service php8.2-fpm start && nginx -g 'daemon off;'"] diff --git a/sample-docker-templates/react/Dockerfile b/sample-docker-templates/react/Dockerfile index c89eb45a94..746403165d 100644 --- a/sample-docker-templates/react/Dockerfile +++ b/sample-docker-templates/react/Dockerfile @@ -1,32 +1,43 @@ -###### BUILD ENVIRONMENT ###### +# Use a minimal Node.js base image +FROM node:22-alpine -# Base Image -FROM node:12.18.1 as build +# Set environment for production +ENV NODE_ENV=production -# Moving into working directory +# Install necessary packages: nginx only +RUN apk update && apk add --no-cache nginx + +# Set working directory WORKDIR /app -# Adding all files and dirs to /app inside container -ADD . /app/ +# Copy application code +COPY . . -# Installing dependencies -RUN npm install +# Main global config +COPY nginx.conf /etc/nginx/nginx.conf -# Creating Production build for react-app -RUN npm run build +# Default server/site config +COPY nginx-default.conf /etc/nginx/http.d/default.conf -# In this dockerfile using the concept of docker multistage build +# Install production dependencies +RUN npm install --production --prefer-offline --no-audit && \ + npm i -g pm2 -###### PRODUCTION ENVIRONMENT ###### +# Create non-root user and set permissions +RUN addgroup -g 2002 nonroot && \ + adduser -u 2002 -G nonroot -S nonroot && \ + mkdir -p /var/lib/nginx/tmp/client_body && \ + chown -R nonroot:nonroot /app /var/log/nginx /var/lib/nginx -# Base Image for prod env -FROM nginx:stable-alpine +# Expose port 8080 +EXPOSE 8080 -# Adding the build files from previous container to nginx/html -COPY --from=build /app/build /usr/share/nginx/html +# Switch to non-root user +USER nonroot -# Exposing port 80 to listen http requests -EXPOSE 80 +# Link logs to stdout/stderr +RUN ln -sf /dev/stdout /var/log/nginx/access.log && \ + ln -sf /dev/stderr /var/log/nginx/error.log -# Command to run -CMD ["nginx", "-g", "daemon off;"] +# Start your app listening on port 8080 +CMD ["sh", "-c", "nginx && pm2-runtime src/index.js -i 0 --port=8080"] \ No newline at end of file diff --git a/sample-docker-templates/rust/Dockerfile b/sample-docker-templates/rust/Dockerfile index 97e7454de0..720322d5bf 100644 --- a/sample-docker-templates/rust/Dockerfile +++ b/sample-docker-templates/rust/Dockerfile @@ -1,25 +1,34 @@ -# Using Base image -FROM alpine:latest +# Use a specific Alpine version for stability instead of 'latest' +FROM alpine:3.21 -#Build args +# Build args for metadata (optional, can be used for labels) ARG VCS_REF ARG BUILD_DATE -# Setting resource quota +# Set resource quota as environment variables (optional usage) ARG MIN_MEM=2G ARG MAX_MEM=2G -# Installing rust and making a folder named 'src' into it -RUN apk add --no-cache rust && mkdir /src +# Install rust compiler and related tools, and create working dir +RUN apk add --no-cache rust && mkdir /src -# Copying 'main.rs' from 'src' folder on host to recently created 'src' folder in container +# Copy source code into container COPY src/main.rs /src # Set working directory WORKDIR /src -#Compiling source +# Compile Rust source to binary 'main' RUN rustc main.rs -#Execution -CMD ["./main"] \ No newline at end of file +# Create non-root user for security +RUN addgroup -S nonroot && adduser -S nonroot -G nonroot + +# Change ownership of the compiled binary +RUN chown nonroot:nonroot /src/main + +# Switch to non-root user +USER nonroot + +# Run the compiled binary +CMD ["./main"]