Azure: подключение дополнительного диска к VM и миграция Jenkins

 

Диски в Azure

Как и любой компьютер – виртуальная машина в Azure использует диски для размещения операционной системы, приложений и данных.

Всем машины в Azure имеют как минимум два диска – для операционной системы (operating system disk), который создаётся из образа ОС, и диск для временных данных (temporary disk). Кроме того – к машине можно подключить один и более дисков для данных (data disks).

  • Operating system disk: SATA-диск, монтируется по умолчанию как /dev/sda. Максимальный размер – 1023 .GB
  • Temporary disk: /dev/sdb, смонтированный в /mnt. Подробнее про временные диски – тут>>>:
    cat /mnt/DATALOSS_WARNING_README.txt
    WARNING: THIS IS A TEMPORARY DISK.
    Any data stored on this drive is SUBJECT TO LOSS and THERE IS NO WAY TO
    RECOVER IT.
  • Data disk: самый интересный для нас – диск для хранения данных приложений. Является SCSI-диском для ОС, и может иметь размер до 1023 GB. Azure создаёт диск для операционной системы автоматически, при развёртывании образа ВМ. Если образ так же содержит в себе диск для данных – он будет создан, иначе – вы должны создать и подключить его сами, что мы и сделаем дальше.

Больше о дисках – тут>>>.

Задача – поднять виртуальную машину, создать data-диск в Storage Account и подключить этот диск к машине.

Далее – на этот диск будут скопированы данные из $JENKINS_HOME на другом хосте, после чего – запустим Jenkins в Docker с разделом из подключенного диска.

Создание ВМ

Подробнее о создании виртуальной машины в Azure с помощью Azure CLIтут>>>.

Проверяем машины в ресурс-группе:

azure vm list -g jm-testing
info:    Executing command vm list
+ Getting virtual machines
data:    ResourceGroupName  Name               ProvisioningState  PowerState  Location    Size
data:    -----------------  -----------------  -----------------  ----------  ----------  ---------------
data:    jm-testing    jm-webapp-ci-temp  Succeeded          VM running  westeurope  Standard_DS1_v2
data:    jm-testing    WinTools           Succeeded          VM running  westeurope  Standard_DS1_v2
info:    vm list command OK

Создаём новую.

Находим образы:

azure vm image list-offers westeurope Canonical
info:    Executing command vm image list-offers
+ Getting virtual machine image offers (Publisher: "Canonical" Location:"westeurope")
data:    Publisher  Offer                      Location
data:    ---------  -------------------------  ----------
data:    Canonical  Ubuntu15.04Snappy          westeurope
data:    Canonical  Ubuntu15.04SnappyDocker    westeurope
data:    Canonical  UbunturollingSnappy        westeurope
data:    Canonical  UbuntuServer               westeurope
data:    Canonical  Ubuntu_Core                westeurope
data:    Canonical  Ubuntu_Snappy_Core         westeurope
data:    Canonical  Ubuntu_Snappy_Core_Docker  westeurope
info:    vm image list-offers command OK

Находим версии для UbuntuServer:

azure vm image list-skus westeurope Canonical UbuntuServer
info:    Executing command vm image list-skus
+ Getting virtual machine image skus (Publisher:"Canonical" Offer:"UbuntuServer" Location:"westeurope")
data:    Publisher  Offer         sku                Location
data:    ---------  ------------  -----------------  ----------
data:    Canonical  UbuntuServer  12.04.2-LTS        westeurope
...
data:    Canonical  UbuntuServer  16.04-DAILY-LTS    westeurope
data:    Canonical  UbuntuServer  16.04-LTS          westeurope
data:    Canonical  UbuntuServer  16.04.0-LTS        westeurope
data:    Canonical  UbuntuServer  16.10              westeurope
data:    Canonical  UbuntuServer  16.10-DAILY        westeurope
data:    Canonical  UbuntuServer  17.04-DAILY        westeurope

Получаем URN ресурса:

azure vm image list westeurope Canonical UbuntuServer 16.04-LTS
info:    Executing command vm image list
+ Getting virtual machine images (Publisher:"Canonical" Offer:"UbuntuServer" Sku: "16.04-LTS" Location:"westeurope")
data:    Publisher  Offer         Sku        OS     Version          Location    Urn
data:    ---------  ------------  ---------  -----  ---------------  ----------  ------------------------------------------------
data:    Canonical  UbuntuServer  16.04-LTS  Linux  16.04.201611220  westeurope  Canonical:UbuntuServer:16.04-LTS:16.04.201611220
...
data:    Canonical  UbuntuServer  16.04-LTS  Linux  16.04.201702020  westeurope  Canonical:UbuntuServer:16.04-LTS:16.04.201702020

Создаём машину:

azure vm quick-create -g jm-testing -n jmcivm1 -l westeurope -y Linux -Q Canonical:UbuntuServer:16.04-LTS:16.04.201611220 -u username -p password
info:    Executing command vm quick-create
+ Listing virtual machine sizes available in the location "westeurope"
+ Looking up the VM "jmcivm1"
...
+ Creating public ip "jmciv-weste-sfflg33fs60n-pip"
+ Looking up the public ip "jmciv-weste-sfflg33fs60n-pip"
+ Creating NIC "jmciv-weste-sfflg33fs60n-nic"
+ Looking up the NIC "jmciv-weste-sfflg33fs60n-nic"
+ Looking up the storage account clisto4154840500jmcivm1
+ Creating VM "jmcivm1"
...
info:    vm quick-create command OK

error:   Parameter adminPassword must be at least 8 character in length, it must contain a lower case, an upper case, a number and a special character such as !@#$%^&+=

Бесит такая забота.

Проверяем:

azure vm show -g jm-testing -n jmcivm1
info:    Executing command vm show
+ Looking up the VM "jmcivm1"
...
data:    Storage Profile:
data:      Image reference:
data:        Publisher                   :Canonical
data:        Offer                       :UbuntuServer
data:        Sku                         :16.04-LTS
data:        Version                     :16.04.201611220
data:
data:      OS Disk:
data:        OSType                      :Linux
...

Логинимся:

ssh username@104.47.162.197
...
username@jmcivm1:~$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 16.04.1 LTS
Release:        16.04
Codename:       xenial

Имеющиеся диски и разделы:

lsblk -f
NAME   FSTYPE LABEL                      UUID                                 MOUNTPOINT
fd0
sda
└─sda1 ext4   cloudimg-rootfs            77227c68-c4c2-4ebe-b766-aa693e9a450f /
sdb
└─sdb1 ext4                              9cce3007-3826-4166-91c3-e601dafeed5d /mnt
sr0    udf    rd_rdfe_stable.161107-1031 0B050C5872645f72

Создание Storage Account

Проверяем текущий Storage Account для созданной машины:

azure vm show -g jm-testing -n jmcivm1 | grep Storage
data:    Storage Profile:
data:      BootDiagnostics StorageUri    :https://clisto4154840500jmcivm1.blob.core.windows.net/

Диски виртуальных машин хранятся в Blob-сторейджах в VHD-формате:

azure vm show -g jm-testing -n jmcivm1 | grep -A 5 "Data Disk"
data:      Data Disks:
data:        Data Disk 1:
data:          Size                      :128 GB
data:          Name                      :vhd-test1
data:          Vhd Uri                   :https://stoxorceoyixe6o.blob.core.windows.net/vhds/vhd-test1.vhd
data:          Caching                   :ReadWrite
data:          CreateOption              :Empty

Проверяем содержимое контейнера в хранилище:

azure storage container list -a stoxorceoyixe6o -k DuGF***qJkA==
info:    Executing command storage container list
+ Getting storage containers
data:    Name  Public Access  Last Modified
data:    ----  -------------  -----------------------------
data:    vhds  Off            Wed, 08 Feb 2017 11:04:59 GMT

Создаём новый диск размером 10gb и подключаем его к созданной ВМ:

azure vm disk attach-new -g jm-testing -n jmcivm1 10 ci-disk-1
info:    Executing command vm disk attach-new
+ Looking up the VM "jmcivm1"
info:    New data disk location: https://stoxorceoyixe6o.blob.core.windows.net/vhds/ci-disk-1.vhd
+ Updating VM "jmcivm1"
info:    vm disk attach-new command OK

Проверяем харнилище:

azure storage blob list --container vhds -a stoxorceoyixe6o -k DuGF***qJkA==
info:    Executing command storage blob list
+ Getting blobs in container vhds
data:    Name                                      Blob Type  Length       Content Type              Last Modified                  Snapshot Time
data:    ----------------------------------------  ---------  -----------  ------------------------  -----------------------------  -------------
data:    ci-disk-1.vhd                             PageBlob   10737418752  application/octet-stream  Wed, 08 Feb 2017 12:25:06 GMT
data:    clidbfd4f78689ffadd-os-1486551711243.vhd  PageBlob   31457280512  application/octet-stream  Wed, 08 Feb 2017 12:26:02 GMT
info:    storage blob list command OK

clidbfd4f78689ffadd-os-1486551711243.vhd – “системный” диск (образ с Ubuntu), ci-disk-1.vhd – только что добавленный нами.

Подключаемся к машине, проверяем диски:

lsblk -f
NAME   FSTYPE LABEL                      UUID                                 MOUNTPOINT
fd0
sda
└─sda1 ext4   cloudimg-rootfs            77227c68-c4c2-4ebe-b766-aa693e9a450f /
sdb
└─sdb1 ext4                              9cce3007-3826-4166-91c3-e601dafeed5d /mnt
sdc

sdc – появился.

Далее – как обычно: создать файловую систему, смонтировать – и готово.

Создаём раздел на диске:

sudo -s
fdisk /dev/sdc
...
Command (m for help): n
Partition type
p   primary (0 primary, 0 extended, 4 free)
e   extended (container for logical partitions)
Select (default p):
Using default response p.
Partition number (1-4, default 1):
First sector (2048-20971519, default 2048):
Last sector, +sectors or +size{K,M,G,T,P} (2048-20971519, default 20971519):
Created a new partition 1 of type 'Linux' and of size 10 GiB.
Command (m for help): p
...
Device     Boot Start      End  Sectors Size Id Type
/dev/sdc1        2048 20971519 20969472  10G 83 Linux
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
Syncing disks.

Проверяем:

lsblk -f /dev/sdc
NAME   FSTYPE LABEL UUID MOUNTPOINT
sdc
└─sdc1

Создаём файловую систему:

mkfs.ext4 /dev/sdc1
mke2fs 1.42.13 (17-May-2015)
Discarding device blocks: done
Creating filesystem with 2621184 4k blocks and 655360 inodes
Filesystem UUID: 9cc937e7-693d-4259-92ba-61cd44b25abc
Superblock backups stored on blocks:
32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632
Allocating group tables: done
Writing inode tables: done
Creating journal (32768 blocks): done
Writing superblocks and filesystem accounting information: done

Монтируем диск:

mkdir /jenkins
mount /dev/sdc1 /jenkins/
ls -l /jenkins/
total 16
drwx------ 2 root root 16384 Feb  8 12:31 lost+found

Готовим fstab, что бы диск смотировался при перезапуске машины.

Находим UUID диска:

blkid /dev/sdc1
/dev/sdc1: UUID="9cc937e7-693d-4259-92ba-61cd44b25abc" TYPE="ext4" PARTUUID="8ec89fdc-01"

Правим /etc/fstab, добавляем строку:

UUID=9cc937e7-693d-4259-92ba-61cd44b25abc /jenkins ext4 defaults 0 1

Полностью файл теперь выглядит так:

cat /etc/fstab
CLOUD_IMG: This file was created/modified by the Cloud Image build process
UUID=77227c68-c4c2-4ebe-b766-aa693e9a450f       /        ext4   defaults,discard        0 0
/dev/disk/cloud/azure_resource-part1    /mnt    auto    defaults,nofail,comment=cloudconfig     0       2
UUID=9cc937e7-693d-4259-92ba-61cd44b25abc /jenkins ext4 defaults 0 1

Готово.

Перезапускаем машину:

reboot

И после перезагрузки – проверяем:

lsblk
NAME   MAJ:MIN RM  SIZE RO TYPE MOUNTPOINT
fd0      2:0    1    4K  0 disk
sda      8:0    0 29.3G  0 disk
└─sda1   8:1    0 29.3G  0 part /
sdb      8:16   0    7G  0 disk
└─sdb1   8:17   0    7G  0 part /mnt
sdc      8:32   0   10G  0 disk
└─sdc1   8:33   0   10G  0 part /jenkins
sr0     11:0    1  1.1M  0 rom
ls -l /jenkins/
total 16
drwx------ 2 root root 16384 Feb  8 12:31 lost+found

Аналогично можно подключить любой диск из любого Storage Account с помощью azure vm disk attach:

azure vm disk -h
help:    Commands to manage your Virtual Machine data disks
help:
help:    Attach a new data-disk to a VM in a resource group
help:      vm disk attach-new [options] <resource-group> <vm-name> <size-in-gb> [vhd-name]
help:
help:    Detach a data-disk attached to a VM in a resource group
help:      vm disk detach [options] <resource-group> <vm-name> <lun>
help:
help:    Attach a new data-disk to a VM in a resource group
help:      vm disk attach [options] <resource-group> <vm-name> [vhd-url]
help:
help:    Get all data disks of a VM in a resource group
help:      vm disk list [options] <resource-group> <vm-name>
...

Миграция Jenkins

Устанавливаем Docker:

apt-get update && apt-get install curl linux-image-extra-$(uname -r)  linux-image-extra-virtual
apt-get install apt-transport-https software-properties-common ca-certificates
curl -fsSL https://yum.dockerproject.org/gpg | sudo apt-key add -
add-apt-repository  "deb https://apt.dockerproject.org/repo/ ubuntu-$(lsb_release -cs) main"
apt-get update && apt-get install docker-engine

Копируем данные Jenkins-а со старого хоста:

scp -r username@52.174.91.198:/jenkins/* /jenkins/
username@52.174.91.198's password:
jenkins.model.ArtifactManagerConfiguration.xml
...

Пока копируются данные из $JENKINS_HOME – создаём пользователя и добавляем его в группу docker:

useradd jenkins
usermod -a -G docker jenkins

Меняем пользователя каталога /jenkins:

chown -R jenkins:jenkins /jenkins/

Находим его ID:

id jenkins
uid=1001(jenkins) gid=1001(jenkins) groups=1001(jenkins),999(docker)

Запускаем контейнер с Jenkins от имени пользователя jenkins:

docker run -u 1001 -dti -p 80:8080 \
>  -v /usr/bin/docker:/usr/bin/docker \
>  -v /etc/passwd:/etc/passwd \
>  -v /jenkins/:/var/jenkins_home/ \
>  -v /var/run/docker.sock:/var/run/docker.sock \
>  -e JENKINS_HOME=/var/jenkins_home/ jenkins
Unable to find image 'jenkins:latest' locally
latest: Pulling from library/jenkins
...

Готово. Вводим пароль – и получаем копию Jenkins с другого хоста:

cat /jenkins/secrets/initialAdminPassword
62902e8f531346c08e5f0da9d4775f5c