From 422c54f3d1ce8edbe70c735853c308efeacfa6d8 Mon Sep 17 00:00:00 2001 From: IT Administration Date: Tue, 21 Apr 2026 13:20:01 +0200 Subject: [PATCH] Initial: bootstrap-client.sh (Sync aus privatem Repo) --- README.md | 13 +++++++++ bootstrap-client.sh | 68 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 81 insertions(+) create mode 100644 README.md create mode 100755 bootstrap-client.sh diff --git a/README.md b/README.md new file mode 100644 index 0000000..e451249 --- /dev/null +++ b/README.md @@ -0,0 +1,13 @@ +# bootstrap-public + +Einmaliges Initial-Provisioning-Skript für Werkschule-Milkau-Clients. +Public, weil nur der SSH-Public-Key und Shell-Logik enthalten sind. + +## Einzeiler (MeshCentral-Gruppenaktion, als root): + +``` +curl -fsSL https://git.evwsm.de/admin/bootstrap-public/raw/branch/main/bootstrap-client.sh | bash +``` + +Das Skript ist idempotent, kann bedenkenlos mehrfach auf demselben +Client laufen. diff --git a/bootstrap-client.sh b/bootstrap-client.sh new file mode 100755 index 0000000..ce52c34 --- /dev/null +++ b/bootstrap-client.sh @@ -0,0 +1,68 @@ +#!/usr/bin/env bash +# Initial-Provisioning eines Clients fuer Ansible-Verwaltung. +# Ausfuehrung als root, einmal pro Client (z.B. via MeshCentral-Shell). +# Idempotent — wiederholte Laeufe aendern nichts. +set -euo pipefail + +ANSIBLE_USER="ansible" +PUBKEY="ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOzJuCu5KZAEjsoiWE8nl9U9BKZ0OwK46Kpt4Y4huPoz ansible@docker-ansible" + +if [[ $EUID -ne 0 ]]; then + echo "ERR: muss als root laufen" >&2 + exit 1 +fi + +# 1. User anlegen +if ! id -u "${ANSIBLE_USER}" >/dev/null 2>&1; then + useradd -m -s /bin/bash -c "Ansible Automation" "${ANSIBLE_USER}" + echo "User '${ANSIBLE_USER}' angelegt." +else + echo "User '${ANSIBLE_USER}' existiert bereits." +fi + +# 2. sudoer-Drop-in (nur fuer diesen User, NOPASSWD) +SUDOERS_FILE="/etc/sudoers.d/90-ansible" +printf '%s ALL=(ALL) NOPASSWD:ALL\n' "${ANSIBLE_USER}" > "${SUDOERS_FILE}" +chmod 440 "${SUDOERS_FILE}" +visudo -cf "${SUDOERS_FILE}" >/dev/null +echo "sudoers-Eintrag gesetzt: ${SUDOERS_FILE}" + +# 3. SSH authorized_keys +SSH_DIR="/home/${ANSIBLE_USER}/.ssh" +AUTH_KEYS="${SSH_DIR}/authorized_keys" + +install -d -m 0700 -o "${ANSIBLE_USER}" -g "${ANSIBLE_USER}" "${SSH_DIR}" +touch "${AUTH_KEYS}" +chmod 600 "${AUTH_KEYS}" +chown "${ANSIBLE_USER}:${ANSIBLE_USER}" "${AUTH_KEYS}" + +if ! grep -qxF "${PUBKEY}" "${AUTH_KEYS}"; then + echo "${PUBKEY}" >> "${AUTH_KEYS}" + echo "Public-Key installiert." +else + echo "Public-Key bereits vorhanden." +fi + +# 4. Pakete: openssh-server (Zorin-Desktop bringt ihn nicht mit) + python3 +export DEBIAN_FRONTEND=noninteractive +NEEDED_PKGS=() +command -v python3 >/dev/null 2>&1 || NEEDED_PKGS+=("python3") +dpkg -s openssh-server >/dev/null 2>&1 || NEEDED_PKGS+=("openssh-server") +if (( ${#NEEDED_PKGS[@]} )); then + apt-get update -qq + apt-get install -y "${NEEDED_PKGS[@]}" + echo "Installiert: ${NEEDED_PKGS[*]}" +else + echo "openssh-server + python3 bereits vorhanden." +fi + +# 5. sshd sicher aktiv +systemctl enable --now ssh >/dev/null 2>&1 || systemctl enable --now sshd >/dev/null 2>&1 || true +systemctl is-active --quiet ssh && echo "sshd laeuft." || echo "WARN: sshd nicht aktiv." >&2 + +# 6. UFW-Regel, falls Firewall aktiv +if command -v ufw >/dev/null 2>&1 && ufw status | grep -q "Status: active"; then + ufw allow 22/tcp >/dev/null && echo "UFW: Port 22 freigegeben." +fi + +echo "--- Bootstrap abgeschlossen auf $(hostname) ---"