#!/bin/bash # Exit on any error set -e # Check if running as root if [ "$EUID" -ne 0 ]; then echo "Please run as root" exit 1 fi # Default values DOCKER_IMAGE="alpine:3.16.0" CONTAINER_NAME="dockerimage" TEMPLATE_NAME="alpine-3.16-docker_$(date +%Y%m%d)_amd64.tar.xz" # Parse command line arguments while getopts "i:n:t:" opt; do case $opt in i) DOCKER_IMAGE="$OPTARG" ;; n) CONTAINER_NAME="$OPTARG" ;; t) TEMPLATE_NAME="$OPTARG" ;; ?) echo "Usage: $0 [-i docker_image] [-n container_name] [-t template_name]" >&2; exit 1 ;; esac done echo "Installing required packages..." apt update && apt -y install skopeo umoci jq echo "Creating LXC container from Docker image..." lxc-create "$CONTAINER_NAME" -t oci -- --url "docker://${DOCKER_IMAGE}" echo "Updating network configuration..." sed -i "s/lxcbr0/vmbr0/" "/var/lib/lxc/${CONTAINER_NAME}/config" echo "Removing extra TTYs..." sed -i '/.*tty[56]$/d' "/var/lib/lxc/${CONTAINER_NAME}/rootfs/etc/inittab" echo "Configuring network interfaces..." cat << EOF > "/var/lib/lxc/${CONTAINER_NAME}/rootfs/etc/network/interfaces" auto eth0 iface eth0 inet dhcp hostname \$(hostname) EOF echo "Adding required packages..." WORLD="/var/lib/lxc/${CONTAINER_NAME}/rootfs/etc/apk/world" for pkg in alpine-base alpine-baselayout alpine-keys apk-tools busybox doas libc-utils logrotate; do grep -q "^${pkg}$" "$WORLD" || echo "$pkg" >> "$WORLD" done LC_ALL=C sort "$WORLD" -o "$WORLD" echo "Starting container and configuring services..." lxc-start -f "/var/lib/lxc/${CONTAINER_NAME}/config" --name="$CONTAINER_NAME" --logfile ~/lxc.log --logpriority DEBUG # Wait for container to start sleep 5 # Configure networking and install packages cat << 'EOF' | lxc-attach --name="$CONTAINER_NAME" ifdown -a ifup -a && apk add --root=/ --initdb $(cat /etc/apk/world) rc-update --quiet add bootmisc boot rc-update --quiet add hostname boot rc-update --quiet add savecache shutdown rc-update --quiet add killprocs shutdown rc-update --quiet add syslog boot rc-update --quiet add networking boot default rc-update --quiet add crond default reboot EOF # Wait for container to reboot sleep 10 echo "Preparing template files..." ROOTFS="/var/lib/lxc/${CONTAINER_NAME}/rootfs" # Stop container lxc-stop --name="$CONTAINER_NAME" # Update template files cat << EOF > "${ROOTFS}/etc/hosts" 127.0.1.1 LXC_NAME 127.0.0.1 localhost localhost.localdomain ::1 localhost localhost.localdomain EOF echo "LXC_NAME" > "${ROOTFS}/etc/hostname" # Clean up files echo -n > "${ROOTFS}/root/.ash_history" rm -f "${ROOTFS}/var/log/messages"* echo -n > "${ROOTFS}/var/log/messages" # Clean /run directory cd "${ROOTFS}/run/" rm -rf ./* echo "Creating template..." TEMPLATEDIR="/var/lib/vz/template/cache" tar -cJf "${TEMPLATEDIR}/${TEMPLATE_NAME}" -p --sparse -C "$ROOTFS" $(ls -A "$ROOTFS") echo "Cleaning up..." lxc-destroy "$CONTAINER_NAME" echo "Template creation complete: ${TEMPLATE_NAME}" echo "You can now create containers from this template using the Proxmox GUI or pct create command"