From e649fe80f36ce747cb18c802d73315daa2743798 Mon Sep 17 00:00:00 2001 From: thebestvibedev Date: Wed, 15 Jul 2026 10:41:31 +0700 Subject: [PATCH] Script to create Jump VM that loaded tk2s.org SSH private key --- create_tk2s.org_jump_vm.sh | 228 +++++++++++++++++++++++++++++++++++++ 1 file changed, 228 insertions(+) create mode 100644 create_tk2s.org_jump_vm.sh diff --git a/create_tk2s.org_jump_vm.sh b/create_tk2s.org_jump_vm.sh new file mode 100644 index 0000000..66edb36 --- /dev/null +++ b/create_tk2s.org_jump_vm.sh @@ -0,0 +1,228 @@ +#!/bin/bash +set -e + +VM_NAME="vm-ubuntu2204" +VCPUS=16 +RAM=16384 +DISK_SIZE=50G +IMG_URL="https://cloud-images.ubuntu.com/jammy/current/jammy-server-cloudimg-amd64.img" +POOL_DIR="/var/lib/libvirt/images" +BASE_IMG="$POOL_DIR/jammy-base.img" +VM_DISK="$POOL_DIR/${VM_NAME}.qcow2" +SEED_ISO="$POOL_DIR/${VM_NAME}-seed.iso" +PASSWORD="ubuntu" + +GREEN='\033[0;32m'; YELLOW='\033[1;33m'; RED='\033[0;31m'; NC='\033[0m' +log() { echo -e "${GREEN}[$(date '+%H:%M:%S')] [INFO]${NC} $1"; } +warn() { echo -e "${YELLOW}[$(date '+%H:%M:%S')] [WARN]${NC} $1"; } +err() { echo -e "${RED}[$(date '+%H:%M:%S')] [ERROR]${NC} $1"; } +step() { echo -e "\n${GREEN}=========================================="; echo -e " $1"; echo -e "==========================================${NC}"; } + +trap 'err "Script failed at line $LINENO. Aborting."' ERR + +echo -e "${GREEN}" +echo "##############################################" +echo "# DEPLOY UBUNTU 22.04 VM ON KVM #" +echo "# VM: $VM_NAME | ${VCPUS} vCPU | $((RAM/1024))GB RAM | $DISK_SIZE #" +echo "##############################################" +echo -e "${NC}" + +# --------------------------------------------- +step "STEP 0/6: ENVIRONMENT CHECKS" +# --------------------------------------------- +[ "$EUID" -eq 0 ] || { err "Must be run as root/sudo."; exit 1; } +log "Running as root: OK" + +if grep -qE 'vmx|svm' /proc/cpuinfo; then + log "CPU supports hardware virtualization: OK" +else + err "CPU does not support VT-x/AMD-V, or it is disabled in BIOS." + exit 1 +fi + +HOST_CPU=$(nproc); HOST_RAM=$(free -m | awk '/^Mem:/{print $2}') +log "Host: ${HOST_CPU} CPUs, ${HOST_RAM} MB RAM" +[ "$HOST_CPU" -lt "$VCPUS" ] && warn "Host has only ${HOST_CPU} CPUs but VM requests ${VCPUS} (overcommit)." +[ "$HOST_RAM" -lt "$RAM" ] && warn "Host has only ${HOST_RAM} MB RAM but VM requests ${RAM} MB." +log "Free disk space: $(df -h /var/lib | awk 'NR==2{print $4}')" + +# --------------------------------------------- +step "STEP 1/6: INSTALLING LIBVIRT / KVM" +# --------------------------------------------- +log "Updating apt index..." +apt-get update -qq +log "Installing packages: qemu-kvm, libvirt, virtinst, cloud-image-utils..." +DEBIAN_FRONTEND=noninteractive apt-get install -y -qq \ + qemu-kvm libvirt-daemon-system libvirt-clients \ + virtinst bridge-utils cloud-image-utils wget whois \ + libosinfo-bin osinfo-db-tools +log "Package installation complete." + +log "Starting libvirtd..." +systemctl enable --now libvirtd +systemctl is-active --quiet libvirtd && log "libvirtd is running: OK" || { err "libvirtd failed to start."; exit 1; } +log "Versions: $(virsh --version) | $(kvm --version | head -1)" + +log "Configuring 'default' NAT network..." +virsh net-start default 2>/dev/null && log "Started default network." || warn "Default network already running." +virsh net-autostart default >/dev/null 2>&1 || true +log "Network status:" +virsh net-list --all + +# --------------------------------------------- +step "STEP 2/6: RESOLVING OS-VARIANT" +# --------------------------------------------- +os_exists() { osinfo-query os short-id="$1" 2>/dev/null | grep -qw "$1"; } + +OS_VARIANT="" +log "Checking local osinfo database for ubuntu22.04..." +if os_exists ubuntu22.04; then + OS_VARIANT="ubuntu22.04" + log "Found ubuntu22.04 in osinfo database." +else + warn "ubuntu22.04 not found (Ubuntu 20.04 ships an older osinfo-db)." + log "Attempting to import an updated osinfo database..." + OSINFO_TAR="/tmp/osinfo-db.tar.xz" + if wget -q -O "$OSINFO_TAR" "https://releases.pagure.org/libosinfo/osinfo-db-20240701.tar.xz"; then + if osinfo-db-import --local "$OSINFO_TAR" >/dev/null 2>&1; then + log "osinfo database imported successfully." + else + warn "osinfo-db-import failed." + fi + rm -f "$OSINFO_TAR" + else + warn "Could not download osinfo-db (no network or URL changed)." + fi + + log "Re-checking database after import..." + for v in ubuntu22.04 ubuntu20.04 ubuntu18.04 generic; do + if [ "$v" = "generic" ] || os_exists "$v"; then + OS_VARIANT="$v"; break + fi + done +fi + +OS_VARIANT="${OS_VARIANT:-generic}" +log "Using --os-variant $OS_VARIANT" +[ "$OS_VARIANT" != "ubuntu22.04" ] && warn "Falling back to '$OS_VARIANT'. This only affects device/perf defaults; virtio + cloud image still works." + +# --------------------------------------------- +step "STEP 3/6: PREPARING CLOUD IMAGE" +# --------------------------------------------- +if [ -f "$BASE_IMG" ]; then + log "Base image already exists ($(du -h "$BASE_IMG" | cut -f1)), skipping download." +else + log "Downloading Ubuntu 22.04 cloud image (~600MB)..." + log "URL: $IMG_URL" + wget -q --show-progress -O "$BASE_IMG" "$IMG_URL" + log "Download complete: $(du -h "$BASE_IMG" | cut -f1)" +fi +log "Base image info:" +qemu-img info "$BASE_IMG" | sed 's/^/ /' + +# --------------------------------------------- +step "STEP 4/6: CREATING DISK AND CLOUD-INIT" +# --------------------------------------------- +log "Creating ${DISK_SIZE} overlay disk for the VM..." +rm -f "$VM_DISK" +qemu-img create -f qcow2 -F qcow2 -b "$BASE_IMG" "$VM_DISK" "$DISK_SIZE" >/dev/null +log "Disk created: $VM_DISK" + +log "Generating password hash for root..." +HASH=$(mkpasswd -m sha-512 "$PASSWORD") +WORKDIR=$(mktemp -d) +log "Temp directory: $WORKDIR" + +log "Writing user-data (enable root login, password auth)..." +cat > "$WORKDIR/user-data" < "$WORKDIR/meta-data" </dev/null 2>&1; then + warn "VM '$VM_NAME' already exists (possibly from a failed run). Removing it..." + virsh destroy "$VM_NAME" 2>/dev/null || true + virsh undefine "$VM_NAME" 2>/dev/null || true + log "Old VM removed." +fi + +log "Running virt-install with --os-variant $OS_VARIANT ..." +virt-install \ + --name "$VM_NAME" \ + --memory "$RAM" \ + --vcpus "$VCPUS" \ + --cpu host-passthrough \ + --disk path="$VM_DISK",device=disk,bus=virtio \ + --disk path="$SEED_ISO",device=cdrom \ + --os-variant "$OS_VARIANT" \ + --network network=default,model=virtio \ + --graphics none \ + --console pty,target_type=serial \ + --import \ + --noautoconsole +log "VM defined and started." + +virsh autostart "$VM_NAME" >/dev/null +log "Autostart enabled for the VM." + +# --------------------------------------------- +step "STEP 6/6: WAITING FOR BOOT AND IP" +# --------------------------------------------- +log "Waiting for cloud-init to finish and the VM to get an IP (up to 120s)..." +IP="" +for i in $(seq 1 24); do + IP=$(virsh domifaddr "$VM_NAME" 2>/dev/null | awk '/ipv4/{split($4,a,"/"); print a[1]}') + if [ -n "$IP" ]; then + log "Got IP after $((i*5))s: $IP" + break + fi + echo -e "${YELLOW} ... waiting ($((i*5))s/120s)${NC}" + sleep 5 +done +[ -z "$IP" ] && warn "No IP yet. Check later with: virsh domifaddr $VM_NAME" + +# --------------------------------------------- +step "DONE" +# --------------------------------------------- +virsh dominfo "$VM_NAME" | sed 's/^/ /' +echo +log "VM Name : $VM_NAME" +log "vCPU/RAM : ${VCPUS} / $((RAM/1024))GB" +log "Disk : $VM_DISK ($DISK_SIZE)" +log "OS variant : $OS_VARIANT" +log "IP : ${IP:-}" +log "Login : root / $PASSWORD" +echo +log "Console : virsh console $VM_NAME (exit: Ctrl+])" +[ -n "$IP" ] && log "SSH : ssh root@$IP" +warn "Cloud-init may need another 30-60s to finish SSH configuration." \ No newline at end of file