FreeBSD virtual environment management and repository

Цели проекта

CBSD разрабатывалась с точки зрения user-friendly, с учетом удобств для пользователя при интерактивной работе. Вы можете спросить - что ж, интерактивные диалоги - это прекрасно. Но что, если у вас стоит задача построить масштабируемый кластер, где виртуальными машинами будет управлять логика более высокого уровня и по этой причине, нам нет нужды в интерактивных командах - может ли CBSD чем-то быть вам полезной в этом случае?

В этой статье описан пример создания и управления кластером CBSD через асинхронный интерфейс с использованием минималистического и быстрого брокера на базе net/beanstalkd. Вместо beanstalkd может выступать любой брокер, такой как ActiveMQ, ZeroMQ, RabbitMQ или Kafka. Условно, назовем это низким уровенем управления виртуальными машинами, который обеспечивает доставку и возвращение результата при управлении виртуальными машинами, такие как создание ВМ, добавление диска, создание снапшота, миграция, клонирование, изменение VNC порта и тд. На более высоком уровне может быть ваше приложение (контроллер).

Здесь мы будем использовать множественные рабочие окружения CBSD, когда часть ресурсов может быть проинициализирована в одном каталоге, другая - в другом. Это открывает широкие возможности при построении pool-binded методов размещения виртуальных машин. Pool binded кластер означает, что все сервисы или виртуальные машины кластера будут привязаны к тому или иному пулу, который может переходить от одного сервера к другому при аварийных ситуациях, при работе DRS или обслуживания оборудования. Таким образом, это может стать базой для построения 'shared nothing cluster' на базе FreeBSD и CBSD.

Построение отказоустойчивого кластера будет описано в более расширенной статье, здесь мы ограничимся лишь множественными рабочими окружениями CBSD, чтобы продемонстрировать работу асинхронного интерфейса через брокер. Предполагаем, что CBSD уже установлена и настроена на сервере. Нам необходим сервис beanstalkd, выступающий в качестве общей шины для всех агентов. Давайте запустим его в jail на нашем сервере. Для этого создаем jail с произвольным именем, в котором будет запущен beanstalkd, например bs1 (назначьте контейнеру корректный рабочий IP адрес, он нам потребуется):

		cbsd jconstruct-tui
		cbsd pkg jname=bs1 mode=update
		cbsd pkg jname=bs1 mode=install net/beanstalkd
		cbsd sysrc jname=bs1 beanstalkd_enable=YES
		cbsd jstart bs1
		

Затем, проинициализируем два независимых окружения (в настоящем кластере это могут быть разные пулы и их, разумеется, может быть больше), например в /pool1 и /pool2 директориях:

		env workdir=/pool1 /usr/local/cbsd/sudoexec/initenv
		

на вопрос изменения rc.conf файла, отвечайте 'n', эта инициализация не должна модифицировать ваши основные конфигурационные файлы.

на вопрос включения NAT ( nat_enable: Enable NAT for RFC1918 networks? ) отвечайте 'нет' - у вас он уже должен работать в основной системе.

Тоже самое повторите для второго окружения:

		env workdir=/pool2 /usr/local/cbsd/sudoexec/initenv
		

с аналогичными ответами.

Теперь, CBSD может работать в этих окружениях через переменную workdir, например:

		env workdir=/pool1 cbsd jconstruct-tui
		env workdir=/pool2 cbsd jconstruct-tui
		

и тд.

Каждое окружение будет обслуживать небольшой агент (назовем его bs_router) который будет подключаться к beanstalkd и обрабатывать запросы. Склонируем его:

		cd /root
		git clone https://github.com/cbsd/bs_router.git /root/bs_router
		

Пример написан на golang, поэтому для сборки проекта нам потребуется go:

		pkg install -y lang/go
		

Собираем:

		cd bs_router
		setenv GOPATH /root/bs_router
		go get
		go build
		cp -a bs_router /usr/local/sbin
		

Теперь скопируем конфигурационный файл и откорректируем для каждого пула:

		cp -a config.json /usr/local/etc/pool1.json
		cp -a config.json /usr/local/etc/pool2.json
		

В обоих файлах измените:

  • uri - с 127.0.0.1:1130 на адрес jail, в котором установлен и запущен beanstalkd, например: 172.16.0.3:1130 (если контейнер bs1 имеет IP 172.16.0.3)
  • cbsdenv - в файле pool1.json это будет /pool1, в файле pool2.json - /pool2
  • tube - на какую трубу подписываемся, для pool1.json пусть это будет "cbsd_pool1", для pool2.json - cbsd_pool2
  • reply_tube_prefix какую трубу используем для ответов, для pool1.json пусть это будет: cbsd_pool1_result_id, для pool2.json - cbsd_pool2_result_id

Запускаем оба агента с указанием конфигурационного файла:

		/usr/local/sbin/bs_router -config /usr/local/etc/pool1.json
		/usr/local/sbin/bs_router -config /usr/local/etc/pool2.json
		

Все, теперь все, что мы будем отправлять в beanstalk очередь с соответствующим именем и соответствующем payload в формате json, будет передано CBSD и получен ответ.

В качестве примера, склонируем семпл клиента к нашему агенту CBSD, который будет подключаться к beanstalkd и слать запросы:

		cd /root
		git clone https://github.com/cbsd/bs_router-client.git
		cd bs_router-client
		setenv GOPATH /root/bs_router-client
		go get
		go build
		

В результате получили бинарный файл bs_router-client, который можно теперь использовать для отправки и приеме задач в разные окружения CBSD. Посмотрите на каталог bin.jail и bin.bhyve, в которых находятся примеры использования.

Работая с cloud образами, есть смысл сначала 'прогреть' все образы, чтобы создание первой виртуальной машины не тормозило процесс, например для pool1 это можно сделать так:

		env workdir=/pool1 cbsd fetch_iso keepname=0 conv2zvol=1 cloud=1 dstdir=default
		

После этой команды, вы сможете воспользоваться результатом выполнения скриптов /root/bs_router-client/bin.bhyve/bcreate.sh и /root/bs_router-client/bin.bhyve/bstart.sh без промедления.