Skip to content

Custom SSH Images

Overview

This page provides a template and instructions for building custom Docker images for Serverless Pods SKUs where SSH access is required.
By following this guide, you can create tailored environments for different applications that seamlessly integrate with infrastructure requiring SSH-based access.

The approach uses a common entrypoint script and standardized setup to handle user creation and SSH configuration. Your application dependencies and tools can then be layered on top of this base.


Step 1: Create the entrypoint.sh Script

This script is the cornerstone of the SSH setup.
It runs each time a container starts from your image and is responsible for configuring and launching the SSH server.

Create a file named entrypoint.sh in the same directory as your Dockerfile and add the following content.

🚨 Important: This script should not be modified.

#!/bin/bash
set -e
# The path where Kubernetes will mount the public key from the Secret
USER_PUBLIC_KEY_PATH="/home/ubuntu/authorized_keys"
# Check if a public key has been provided and configure SSH
if [ -f "$USER_PUBLIC_KEY_PATH" ]; then
    echo "Public key found. Configuring SSH for user 'ubuntu'."
    mkdir -p /home/ubuntu/.ssh
    cp "$USER_PUBLIC_KEY_PATH" /home/ubuntu/.ssh/authorized_keys
    chown -R ubuntu:ubuntu /home/ubuntu/.ssh
    chmod 700 /home/ubuntu/.ssh
    chmod 600 /home/ubuntu/.ssh/authorized_keys
else
    echo "WARNING: No public key found at $USER_PUBLIC_KEY_PATH. SSH login will not work."
fi
# Start the SSH daemon in the foreground
echo "Starting SSH daemon..."
exec /usr/sbin/sshd -D

Step 2: Create Your Custom Dockerfile

Use the following template to create your Dockerfile. It includes mandatory SSH setup sections and a customizable section for adding your own dependencies.

Copy the template below into a new file named Dockerfile and modify only the Customization Section.

# syntax=docker/dockerfile:1.4

# ==============================================================================
# SECTION 1: BASE IMAGE
#
# Choose the base operating system for your image.
# For example: ubuntu:22.04, ubuntu:24.04, etc.
# Using a specific version is recommended for reproducibility.
# The --platform flag is optional but useful for multi-architecture builds.
# ==============================================================================
FROM --platform=${TARGETPLATFORM:-linux/amd64} ubuntu:22.04


# ==============================================================================
# SECTION 2: STANDARD SSH & USER SETUP (MANDATORY)
#
# DO NOT MODIFY THIS SECTION.
# These layers install the SSH server and create a standard 'ubuntu' user
# with sudo privileges. This ensures a consistent access environment across
# all custom images.
# ==============================================================================

# Set non-interactive frontend to avoid prompts during package installation
ENV DEBIAN_FRONTEND=noninteractive

# Install openssh-server, sudo, and other base utilities
RUN apt-get update && apt-get install -y \
    openssh-server \
    sudo \
    ca-certificates \
    curl \
    gnupg \
    lsb-release \
    wget \
    vim \
    && rm -rf /var/lib/apt/lists/*

# Create a non-root user 'ubuntu' with a home directory and bash shell
# Then, grant the 'ubuntu' user passwordless sudo access
RUN useradd -m -s /bin/bash ubuntu && \
    echo "ubuntu ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers

# Create the required directory for the SSH daemon to run
RUN mkdir /var/run/sshd


# ==============================================================================
# SECTION 3: YOUR CUSTOMIZATIONS (ADD YOUR CODE HERE)
#
# This is where you add the specific tools, libraries, and dependencies
# for your custom image.
#
# Below is a detailed example for creating a PyTorch development environment.
# You can delete or replace this example with your own commands.
# ==============================================================================

# --- Example Start: Install whatever you need for your image---

# Install build-essential for compiling software
RUN apt-get update && apt-get install -y \
    build-essential \
    software-properties-common \


# Install pip for Python 3.11 and upgrade it
RUN curl -sS https://bootstrap.pypa.io/get-pip.py | python3.11 && \
    python -m pip install --upgrade pip setuptools wheel

# Install PyTorch for CUDA 12.8.
RUN --mount=type=cache,target=/root/.cache/pip \
    python -m pip install --no-cache-dir \
    torch==2.7.0+cu128 torchvision==0.22.0+cu128 torchaudio==2.7.0+cu128 \
    --index-url https://download.pytorch.org/whl/cu128

# Install common Python data science libraries
RUN --mount=type=cache,target=/root/.cache/pip \
    python -m pip install --no-cache-dir \
    numpy \
    matplotlib \
    jupyter \
    ipython \
    pandas

# Set environment variables for NVIDIA GPU Operator compatibility (optional)
ENV CUDA_HOME=/usr/local/cuda
ENV LD_LIBRARY_PATH=/usr/local/cuda/lib64:${LD_LIBRARY_PATH}
ENV PATH=/usr/local/cuda/bin:${PATH}

# ---------- Example End ------------


# ==============================================================================
# SECTION 4: ENTRYPOINT CONFIGURATION (MANDATORY)
#
# DO NOT MODIFY THIS SECTION.
# This copies the entrypoint script into the image, makes it executable,
# exposes the SSH port, and sets the container to run the script on start.
# ==============================================================================

# Copy the entrypoint script into the container
COPY entrypoint.sh /entrypoint.sh

# Make the entrypoint script executable
RUN chmod +x /entrypoint.sh

# Expose the standard SSH port
EXPOSE 22

# Set the entrypoint to our script
ENTRYPOINT ["/entrypoint.sh"]

Step 3: Build Your Docker Image

Once your Dockerfile and entrypoint.sh are in the same directory, you can build the image using Docker Buildx.

Open a terminal in the directory containing the files, and run one of the following commands.

Option A: Build for a Single Architecture

# Replace 'your-image-name:tag' with your desired image name
docker buildx build --platform linux/amd64 -t your-image-name:tag . --load

Option B: Build for Multiple Architectures

# Replace 'your-registry/your-image-name:tag' with your full image path
docker buildx build --platform linux/amd64,linux/arm64 -t your-registry/your-image-name:tag . --push

After the build completes, you will have a custom Docker image ready for use in your Serverless Pods with SSH access.