Üdvözlöm, Denis vagyok, és az egyik tevékenységi köröm az infrastruktúra megoldások fejlesztése az X5-nél. Ma szeretném megosztani Önökkel, hogyan lehet nyilvános eszközök alapján automatikus rendszert felállítani a szerverek előkészítésére. Véleményem szerint ez egy érdekes, egyszerű és rugalmas megoldás.

Az előkészítés alatt azt értjük: az új, dobozból kivett szerverből teljesen beállított szerver készítése Linux OS-sel vagy ESXi hipervízióval (kiszórás szerverek A Windows a cikkben nem kerül megvitatásra).
Kifejezések:
- szerverek – olyan szerverek, amelyeket be kell állítani.
- install-szerver – a fő szerver, amely biztosítja az egész előkészítési folyamatot hálózaton keresztül.
Miért szükséges az automatizálás?
Tegyük fel, hogy van egy feladat: nagy mennyiségű szerver előkészítése nulláról, csúcsidőszakban – napi 30. Különböző gyártók és modellek szerverei, amelyekre különböző OS-ek telepíthetők, esetleg van, vagy nincs hipervízió.
Milyen műveletek tartoznak a beállítási folyamatba (automatizálás nélkül):
- csatlakoztassa a billentyűzetet, egeret, monitort a szerverhez;
- állítsa be a BIOS-t, RAID-et, IPMI-t;
- frissítse a komponensek firmware-jét;
- készítse el a fájlrendszer képét (vagy telepítse a hipervíziót, és másolja a virtuális gépeket);
Megjegyzés. Alternatív megoldásként az OS telepítése lehetséges egy válaszfájl segítségével. De erről nem fogunk beszélni a cikkben. Bár alább láthatja, hogy ezt a funkciót könnyen hozzá lehet adni.
- állítsa be az OS paramétereit (hostname, IP, stb.).
Ebben a megközelítésben ugyanazokat a beállításokat végezzük el minden szerveren sorozatosan. Az ilyen munka hatékonysága nagyon alacsony.
Az automatizálás lényege – kiiktatni az ember részvételét a szerver előkészítési folyamatából. A lehető legnagyobb mértékben.
Az automatizálás révén csökken az üzemidő a műveletek között, és lehetővé válik több szerver egyidejű előkészítése. Emellett jelentősen csökken a hibák előfordulásának valószínűsége az emberi tényező miatt.

Hogyan történik az automatikus szerver beállítás?
Felejtsük el részletesen az összes lépést.
Van egy linux-szervere, amelyet PXE install-szerverként használ. Rajta telepítve és beállítva vannak a következő szolgáltatások: DHCP, TFTP.
Tehát, indítsuk el a szervert (amelyet be kell állítani) PXE-n. Emlékezzünk, hogyan működik ez:
- A szerveren a hálózati indítás van kiválasztva.
- A szerver betölti a PXE-ROM-ot a hálózati kártyáról, és DHCP-n keresztül kapcsolatba lép az install-szerverrel, hogy megkapja a hálózati címet.
- Az install-szerver DHCP-je címet ad ki, valamint utasítást a PXE-n keresztüli további indításhoz.
- A szerver PXE-n keresztül betölti a hálózati betöltőt az install-szerverről, a további indítás a PXE konfigurációs fájl szerint zajlik.
- Az indítás a kapott paraméterek (kernel, initramfs, csatolási pontok, squashfs image stb.) alapján történik.
Megjegyzés: A cikk a PXE indítást BIOS módban ismerteti. Jelenleg a gyártók aktívan bevezetik az UEFI indító módot. A PXE esetében a különbség a DHCP-szerver konfigurációjában és egy további betöltő meglétében rejlik.
Tekintsük át egy PXE-szerver konfigurációját (pxelinux menü példája).
A fájl pxelinux.cfg/default:
default menu.c32
prompt 0
timeout 100
menu title X5 PXE Boot Menu
LABEL InstallServer Menu
MENU LABEL InstallServer
KERNEL menu.c32
APPEND pxelinux.cfg/installserver
LABEL VMware Menu
MENU LABEL VMware ESXi Install
KERNEL menu.c32
APPEND pxelinux.cfg/vmware
LABEL toolkit // alapértelmezett menü
MENU LABEL Linux Scripting Toolkits
MENU default
KERNEL menu.c32
APPEND pxelinux.cfg/toolkit // következő menüre ugrásA fájl pxelinux.cfg/toolkit:
prompt 0
timeout 100
menu title X5 PXE Boot Menu
label mainmenu
menu label ^Vissza a Főmenübe
kernel menu.c32
append pxelinux.cfg/default
label x5toolkit-auto // alapértelmezett - automatikus mód
menu label x5 toolkit autoinstall
menu default
kernel toolkit/tkcustom-kernel
append initrd=toolkit/tk-initramfs.gz quiet net.ifnames=0 biosdevname=0 nfs_toolkit_ip=192.168.200.1 nfs_toolkit_path=tftpboot/toolkit nfs_toolkit_script=scripts/mount.sh script_cmd=master-install.sh CMDIS2="…"
label x5toolkit-shell // hibakereséshez - konzol
menu label x5 toolkit shell
kernel toolkit/tkcustom-kernel
append initrd=toolkit/tkcustom-initramfs.gz quiet net.ifnames=0 biosdevname=0 nfs_toolkit_ip=192.168.200.1 nfs_toolkit_path=tftpboot/toolkit nfs_toolkit_script=scripts/mount.sh script_cmd=/bin/bash CMDIS2="…"A kernel és az initramfs ebben a szakaszban egy köztes linux kép, amellyel a szerver főbb előkészítése és beállítása történik.
Ahogy látjuk, a betöltő sok paramétert ad át a kernelnek. Ezek közül néhányat a kernel használ, míg néhányat a saját céljainkra felhasználhatunk. Erről később lesz szó, addig is érdemes megjegyezni, hogy minden átadott paraméter elérhető lesz a köztes linux képen keresztül a /proc/cmdline-on.
Honnan szerezhetjük be a kernelt és az initramfs-t?
Alapként bármilyen linux disztribúciót választhatunk. Mire figyelünk a választás során:
- A boot image must be universal (with drivers included, possibilities for installing additional utilities);
- It is likely that customization of the initramfs will be required.
How is this done in our solution for X5? We chose CentOS 7 as the base. We'll perform the following trick: prepare the future structure of the image, pack it into an archive, and create an initramfs, inside which will be our file system archive. When the image is booted, the archive will be unpacked into the created tmpfs partition. Thus, we will get a minimal yet fully functional live Linux image with all necessary utilities, consisting of just two files: vmkernel and initramfs.
#создаем директории:
mkdir -p /tftpboot/toolkit/CustomTK/rootfs /tftpboot/toolkit/CustomTK/initramfs/bin
#подготавливаем структуру:
yum groups -y install "Minimal Install" --installroot=/tftpboot/toolkit/CustomTK/rootfs/
yum -y install nfs-utils mariadb ntpdate mtools syslinux mdadm tbb libgomp efibootmgr dosfstools net-tools pciutils openssl make ipmitool OpenIPMI-modalias rng-tools --installroot=/tftpboot/toolkit/CustomTK/rootfs/
yum -y remove biosdevname --installroot=/tftpboot/toolkit/CustomTK/rootfs/
# подготавливаем initramfs:
wget https://busybox.net/downloads/binaries/1.31.0-defconfig-multiarch-musl/busybox-x86_64 -O /tftpboot/toolkit/CustomTK/initramfs/bin/busybox
chmod a+x /tftpboot/toolkit/CustomTK/initramfs/bin/busybox
cp /tftpboot/toolkit/CustomTK/rootfs/boot/vmlinuz-3.10.0-957.el7.x86_64 /tftpboot/toolkit/tkcustom-kernel
# создаем /tftpboot/toolkit/CustomTK/initramfs/init (ниже содержание скрипта):
#!/bin/busybox sh
/bin/busybox --install /bin
mkdir -p /dev /proc /sys /var/run /newroot
mount -t proc proc /proc
mount -o mode=0755 -t devtmpfs devtmpfs /dev
mkdir -p /dev/pts /dev/shm /dev/mapper /dev/vc
mount -t devpts -o gid=5,mode=620 devpts /dev/pts
mount -t sysfs sysfs /sys
mount -t tmpfs -o size=4000m tmpfs /newroot
echo -n "Extracting rootfs... "
xz -d -c -f rootfs.tar.xz | tar -x -f - -C /newroot
echo "done"
mkdir -p /newroot/dev /newroot/proc /newroot/sys
mount --move /sys /newroot/sys
mount --move /proc /newroot/proc
mount --move /dev /newroot/dev
exec switch_root /newroot /sbin/init
# упаковываем rootfs и initramfs:
cd /tftpboot/toolkit/CustomTK/rootfs
tar cJf /tftpboot/toolkit/CustomTK/initramfs/rootfs.tar.xz --exclude ./proc --exclude ./sys --exclude ./dev .
cd /tftpboot/toolkit/CustomTK/initramfs
find . -print0 | cpio --null -ov --format=newc | gzip -9 > /tftpboot/toolkit/tkcustom-initramfs-new.gzSo, we specified the kernel and initramfs that should be loaded. As a result, at this stage, loading the intermediate Linux image via PXE will give us an OS console.
Great, but now we need to pass control to our 'automation'.
This can be done as follows.
Suppose after booting the image we plan to pass control to the mount.sh script.
We will include the mount.sh script in the auto-start. For this, it will be necessary to modify the initramfs:
- unpack the initramfs (if we are using the above-provided initramfs option, this is not required)
- include in the auto-start code that will analyze the parameters passed via /proc/cmdline and pass control further;
- pack the initramfs.
Note. In the case of X5, control of the boot process is passed to the script /opt/x5/toolkit/bin/hook.sh с помощью override.conf в getty tty1 (ExecStart=…)
So, the image is booted, in which the mount.sh script starts in auto-start. Next, the mount.sh script analyzes the passed parameters (script_cmd=) during execution and launches the necessary program/script.
label toolkit-auto
kernel …
append … nfs_toolkit_script=scripts/mount.sh script_cmd=master-install.sh
label toolkit-shell
kernel …
append … nfs_toolkit_script=scripts/mount.sh script_cmd=/bin/bash

Here, on the left is the PXE menu, on the right - the control transfer scheme.
We figured out the control transfer. Depending on the choice of PXE menu, either the auto-configuration script or the console for debugging is launched.
In the case of automatic configuration, the necessary directories from the install server are mounted, which include:
- scripts;
- saved BIOS/UEFI templates for various servers;
- firmware;
- utilities for servers;
- logs.
Next, the mount.sh script passes control to the master-install.sh script from the scripts directory.
The script tree (the order of their execution) looks approximately like this:
- master-install
- sharefunctions (common functions)
- info (információk kiírása)
- models (a telepítési paraméterek beállítása a szervermodell alapján)
- prepare_utils (a szükséges segédprogramok telepítése)
- fwupdate (firmware frissítése)
- diag (alapdiagnosztika)
- biosconf (BIOS/UEFI beállítása)
- clockfix (idők beállítása az alaplapon)
- srmconf (a távoli interfész beállítása)
- raidconf (logikai kötetek beállítása)
egyik a következők közül:
- preinstall (az OS vagy hypervisor telepítőt indítja, például ESXi)
- merged-install (az image kibővítésének közvetlen indítása)
Most már tudjuk:
- hogyan kell a szervert PXE-n keresztül betölteni;
- hogyan lehet átadni a vezérlést saját scriptnek.
Folytassuk. A következő kérdések váltak aktuálissá:
- Hogyan azonosítsuk a készülő szervert?
- Milyen segédprogramokat és hogyan állítsuk be a szervert?
- Hogyan kaphatunk beállításokat egy konkrét szerverhez?
Hogyan azonosítsuk a készülő szervert?
Ez egyszerű – DMI:
dmidecode –s system-product-name
dmidecode –s system-manufacturer
dmidecode –s system-serial-numberItt minden szükséges információ megtalálható: gyártó, modell, sorozatszám. Ha nem biztos benne, hogy ez az információ minden szerveren elérhető, akkor a MAC-cím alapján is azonosíthatja őket. Vagy mindkét módszert egyszerre, ha a szervergyártók különbözőek, és egyes modellek esetében a sorozatszám információ egyszerűen hiányzik.
A megszerzett információk alapján hálózati mappák kerülnek becsatolásra az install szerverről, és betöltődik minden szükséges dolog (segédprogramok, firmware stb.).
Milyen segédprogramokat és hogyan állítsuk be a szervert?
Néhány gyártó linuxos segédprogramjait mutatom be. Minden segédprogram elérhető a gyártók hivatalos weboldalain.

A firmware-rel kapcsolatban gondolom, minden világos. Általában tömörített végrehajtható fájlokként érkeznek. A végrehajtható fájl irányítja a firmware frissítési folyamatát, és megadja a visszatérési kódot.
A BIOS és az IPMI általában sablonokon keresztül konfigurálható. Ha szükséges, a sablon szerkeszthető a töltés előtt.
Néhány gyártó RAID segédprogramjai is beállíthatók sablon alapján. Ha nem, akkor egy konfiguráló scriptet kell írni.
A RAID beállításának sorrendje a legtöbb esetben a következő:
- Lekérdezzük a jelenlegi konfigurációt.
- Ha már léteznek logikai tömbök – töröljük azokat.
- Megnézzük, milyen fizikai lemezek vannak és hányan.
- Új logikai tömböt hozunk létre. Hibás működés esetén megállítjuk a folyamatot.
Hogyan kaphatunk beállításokat egy konkrét szerverhez?
Tegyük fel, hogy a szerverek beállításait az installáló szerveren tárolják. Ebben az esetben, hogy válaszoljunk a kérdésünkre, először meg kell határoznunk: milyen módon adjuk át a beállításokat az installáló szervernek.
Kezdetben elegendő lehet szöveges fájlokat használni. (A jövőben a szöveges fájl használható a beállítások tartalék módjaként.)
Megoszthatunk egy szöveges fájlt az installáló szerveren, és hozzáadhatjuk a csatolását a mount.sh szkripthez.
A sorok például a következő formátumban lesznek:
Ez a sor az engineer munkagépéből fog átkerülni egy fájlba, és a szerver beállításakor a konkrét szerver paraméterei a fájlból lesznek olvasva.
De a jövő szempontjából jobb lenne adatbázist használni a beállítások, állapotok és a szerverek telepítési naplójának tárolására.
Természetesen csak egy adatbázis nem elegendő, létre kell hozni egy kliensoldalt is, amellyel a beállításokat átadhatjuk az adatbázisnak. Ezt megvalósítani nehezebb, mint szöveges fájl esetén, de valójában minden nem olyan nehéz, mint amilyennek tűnik. A minimális verziója a kliensnek, amely egyszerűen adatokat ad át az adatbázisnak, elég könnyen megírható. A kliensprogram továbbfejlesztése szabad módon is lehetséges lesz (jelentések, címkék nyomtatása, értesítések küldése és minden más, ami eszünkbe jut).
Egy adott lekérdezés végrehajtása után az adatbázisban, megadva a szerver sorozatszámát, megkaphatjuk a szükséges paramétereket a szerver beállításához.
Továbbá, nem kell a szöveges fájl esetén megoldanunk a párhuzamos hozzáférés blokkolását.
A beállítási naplót minden szakaszban rögzíthetjük az adatbázisban, és a telepítési folyamatot eseményeken és állapotfákon keresztül ellenőrizhetjük.
Most már tudjuk, hogyan:
- szervert indítani PXE-n keresztül;
- átadni a vezérlést a szkripthöz;
- a szükséges szervert azonosítani a sorozatszáma alapján;
- konfigurálni a szervert a megfelelő eszközökkel;
- átadni a beállításokat az installáló szerver adatbázisába a kliensoldal segítségével.
Kiderítettük, hogyan:
- az installálásra kerülő szerver az adatbázisból kapja meg a szükséges beállításokat;
- a felkészülés teljes folyamatát rögzítjük az adatbázisban (naplók, események, állapotok).
Mit szólnak a telepíthető szoftverek különböző típusaihoz? Hogyan telepítsünk hipervizort, másoljunk VM-et és állítsuk be mindezt?
Ha Linux fájlrendszer-képet telepítünk a hardverre, akkor minden elég egyszerű:
- Miután beállítottuk a szerver összes komponensét, telepítjük a képet.
- Telepítjük a grub betöltőt.
- Végrehajtunk egy chroot-ot, és konfigurálunk minden szükséges dolgot.
Hogyan adjuk át az irányítást az operációs rendszer telepítőjének (ESXi példa alapján).
- Szervezzük meg az irányítás átadását a hipervizor telepítőjének a válaszfájl (kickstart) segítségével:
- Töröljük a meglévő partíciókat a lemezen.
- Hozzunk létre egy 500MB méretű partíciót.
- Jelöljük meg boot-pártícióként.
- Formázzuk FAT32-re.
- Másoljuk rá a kezdeti ESXi fájlokat a gyökérbe.
- Telepítjük a syslinux-t.
- Másoljuk a syslinux.cfg-t a /syslinux/ mappába.
default esxi
prompt 1
timeout 50
label esxi
kernel mboot.c32
append -c boot.cfg- Másoljuk az mboot.c32-t a /syslinux/ mappába.
- A boot.cfg fájlban a kernelopt=ks=ftp:///ks_esxi.cfg kell legyen
- Újraindítjuk a szervert.
A szerver újraindítása után a merevlemezéről az ESXi telepítője fog elindulni. Az összes szükséges telepítő fájl betöltődik a memóriába, és ezután megkezdődik az ESXi installáció a megadott válaszfájl szerint.
Itt néhány sort hozok a válaszfájlból, a ks_esxi.cfg-ből:
%firstboot --interpreter=busybox
…
# sorozatszám lekérése
SYSSN=$(esxcli hardware platform get | grep Serial | awk -F " " '{print $3}')
# IP cím lekérése
IPADDRT=$(esxcli network ip interface ipv4 get | grep vmk0 | awk -F " " '{print $2}')
LAST_OCTET=$(echo $IPADDRT | awk -F'.' '{print $4}')
# NFS telepítő szerver csatlakoztatása
esxcli storage nfs add -H is -s \/srv\/nfs_share -v nfsshare1
# ideiglenes ssh beállítások másolása, az ssh kliens használatához
mv \/etc\/ssh \/etc\/ssh.tmp
cp -R \/vmfs\/volumes\/nfsshare1\/ssh \/etc\/
chmod go-r \/etc\/ssh\/ssh_host_rsa_key
# ovftool másolása, a VM-ek telepítéséhez most, és szükség esetén később
cp -R \/vmfs\/volumes\/nfsshare1\/ovftool \/vmfs\/volumes\/datastore1\/
# VM telepítése
\/vmfs\/volumes\/datastore1\/ovftool\/tools\/ovftool --acceptAllEulas --noSSLVerify --datastore=datastore1 --name=VM1 \/vmfs\/volumes\/nfsshare1\/VM_T\/VM1.ova vi:\/\/root:esxi_password@127.0.0.1
\/vmfs\/volumes\/datastore1\/ovftool\/tools\/ovftool --acceptAllEulas --noSSLVerify --datastore=datastore1 --name=VM2 \/vmfs\/volumes\/nfsshare1\/VM_T\/VM2.ova vi:\/\/root:esxi_password@127.0.0.1
# szerverünk beállításait tartalmazó sor lekérése
ssh root@is "mysql -h'192.168.0.1' -D'servers' -u'user' -p'secretpassword' -e "SELECT ... WHERE servers.serial='$SYSSN'"" | grep -v ^$ | sed 's\/NULL//g' > \/tmp\/servers
...
# hálózati beállító script generálása
echo '#!\/bin\/sh' > \/vmfs\/volumes\/datastore1\/netconf.sh
echo "esxcli network ip interface ipv4 set -i=vmk0 -t=static --ipv4=$IPADDR --netmask=$S_SUB || exit 1" >> \/vmfs\/volumes\/datastore1\/netconf.sh
echo "esxcli network ip route ipv4 add -g=$S_GW -n=default || exit 1" >> \/vmfs\/volumes\/datastore1\/netconf.sh
chmod a+x \/vmfs\/volumes\/datastore1\/netconf.sh
# guestinfo.esxihost.id paraméter beállítása, amely a sorozatszámot tartalmazza
echo "guestinfo.esxihost.id = "$SYSSN"" >> \/vmfs\/volumes\/datastore1\/VM1\/VM1.vmx
echo "guestinfo.esxihost.id = "$SYSSN"" >> \/vmfs\/volumes\/datastore1\/VM2\/VM2.vmx
...
# adatbázis frissítése
SYSNAME=$(esxcli hardware platform get | grep Product | sed 's\/Product Name:\/\/g' | sed 's\/^ *//')
UUID=$(vim-cmd hostsvc\/hostsummary | grep uuid | sed 's\/\/g;s\/$//g' | sed 's\/uuid=\
Ezen a ponton a hipervizor telepítve és beállítva van, a virtuális gépek másolva lettek.
Hogyan állíthatjuk be most a virtuális gépeket?
Kicsit ügyeskedtünk: a telepítés során a VM1.vmx fájlban beállítottuk a guestinfo.esxihost.id = "$SYSSN" paramétert, amely a fizikai szerver sorozatszámát tartalmazza.
Most a virtuális gép indítása után (vmware-tools csomaggal telepítve) hozzáférhet ehhez a paraméterhez:
ESXI_SN=$(vmtoolsd --cmd "info-get guestinfo.esxihost.id")A VM can identify itself (it knows the serial number of the physical host), make a request to the install server database, and obtain the parameters that need to be configured. This is all scripted in a command that should be automatically executed upon the start of the guest OS VM (but only once: RunOnce).
Most már tudjuk, hogyan:
- szervert indítani PXE-n keresztül;
- átadni a vezérlést a szkripthöz;
- a szükséges szervert azonosítani a sorozatszáma alapján;
- configure the server with appropriate utilities;
- pass settings to the install server database using the client side;
- configure various types of software, including deploying the ESXi hypervisor and setting up virtual machines (all automatically).
Kiderítettük, hogyan:
- az installálásra kerülő szerver az adatbázisból kapja meg a szükséges beállításokat;
- a felkészülés teljes folyamatát rögzítjük az adatbázisban (naplók, események, állapotok).
Összegzés:
I believe the uniqueness of this solution lies in its flexibility, simplicity, capabilities, and versatility.
Please write in the comments what you think.
Forrás: habr.com
