solar/Vagrantfile
Bogdan Dobrelya 467d84c620 Add centos7 docker support
* Separate OSTYPE specific tasks/files.
* Keep only common tasks and files in the
playbooks dir.

TODO pxe case to be working for centos as well
note, the cmtools.sh installs ansible 2.0.1.0
  in centos7, while we have 2.0.0.2 for ubuntu trusty
note, the base.yaml installs python-keystoneclient
  1:1.3.0-1.el7 from kilo-2 (no juno for centos7),
  while for ubuntu we have one from juno
note, there is no pygraphviz for centos7, see also
  https://bugs.launchpad.net/fuel/+bug/1510884

Closes-bug: #1548851

Change-Id: Icec5637f9242104322d1104725f9f132d1ca16f0
Signed-off-by: Bogdan Dobrelya <bdobrelia@mirantis.com>
2016-03-02 11:16:23 +01:00

303 lines
11 KiB
Ruby

# -*- mode: ruby -*-
# vi: set ft=ruby :
# Copyright 2015 Mirantis, Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
Vagrant.require_version ">= 1.7.4"
require 'etc'
require 'log4r'
require 'yaml'
# Vagrantfile API/syntax version. Don't touch unless you know what you're doing!
VAGRANTFILE_API_VERSION = "2"
HOME=Etc.getpwuid.dir
# Solar specific key paths mappings
INSECURE_KEY="#{HOME}/.vagrant.d/insecure_private_key"
KEY_PATH1="/vagrant/tmp/keys/ssh_private"
def get_machine_key (index = '')
"/vagrant/.vagrant/machines/solar-dev#{index}/virtualbox/private_key"
end
# configs, custom updates _defaults
@logger = Log4r::Logger.new("vagrant::docker::driver")
defaults_cfg = YAML.load_file('vagrant-settings.yaml_defaults')
if File.exist?('vagrant-settings.yaml')
custom_cfg = YAML.load_file('vagrant-settings.yaml')
cfg = defaults_cfg.merge(custom_cfg)
else
cfg = defaults_cfg
end
SLAVES_COUNT = cfg["slaves_count"]
SLAVES_RAM = cfg["slaves_ram"]
SLAVES_IPS = cfg["slaves_ips"]
SLAVES_IMAGE = cfg["slaves_image"]
SLAVES_IMAGE_VERSION = cfg["slaves_image_version"]
MASTER_RAM = cfg["master_ram"]
MASTER_IPS = cfg["master_ips"]
MASTER_IMAGE = cfg["master_image"]
MASTER_IMAGE_VERSION = cfg["master_image_version"]
SYNC_TYPE = cfg["sync_type"]
MASTER_CPUS = cfg["master_cpus"]
SLAVES_CPUS = cfg["slaves_cpus"]
PARAVIRT_PROVIDER = cfg.fetch('paravirtprovider', false)
PREPROVISIONED = cfg.fetch('preprovisioned', true)
DOCKER_MASTER_IMAGE=cfg['docker_master_image']
DOCKER_SLAVES_IMAGE=cfg['docker_slaves_image']
DOCKER_CMD=cfg['docker_cmd']
SOLAR_DB_BACKEND = cfg.fetch('solar_db_backend', 'riak')
# Initialize noop plugins only in case of PXE boot
require_relative 'bootstrap/vagrant_plugins/noop' unless PREPROVISIONED
# FIXME(bogdando) more natively to distinguish a provider specific logic
provider = (ARGV[2] || ENV['VAGRANT_DEFAULT_PROVIDER'] || :docker).to_sym
def ansible_playbook_command(filename, args=[])
ansible_script_crafted = "ansible-playbook -v -i \"localhost,\" -c local /vagrant/bootstrap/playbooks/#{filename} #{args.join ' '}"
@logger.info("Crafted ansible-script: #{ansible_script_crafted})")
ansible_script_crafted
end
def shell_script(filename, env=[], args=[])
shell_script_crafted = "/bin/bash -c \"#{env.join ' '} #{filename} #{args.join ' '} 2>/dev/null\""
@logger.info("Crafted shell-script: #{shell_script_crafted})")
shell_script_crafted
end
# W/a unimplemented docker-exec, see https://github.com/mitchellh/vagrant/issues/4179
# Use docker exec instead of the SSH provisioners
# TODO(bogdando) lxc-docker support (there is no exec)
def docker_exec (name, script)
@logger.info("Executing docker-exec at #{name}: #{script}")
system "docker exec -it #{name} #{script}"
end
solar_script = ansible_playbook_command("solar.yaml")
solar_agent_script = ansible_playbook_command("solar-agent.yaml")
master_pxe = ansible_playbook_command("pxe.yaml")
fix_six = shell_script("/vagrant/bootstrap/playbooks/fix_centos7_six.sh")
solar_exec = shell_script("#{solar_script}", ["SOLAR_DB_BACKEND=#{SOLAR_DB_BACKEND}"])
if provider == :docker
# Prepare docker volumes and workaround missing machines' ssh_keys
# and virtualbox hardcoded paths in Solar
key=get_machine_key
docker_volumes = ["-v", "#{INSECURE_KEY}:#{KEY_PATH1}:ro"]
docker_volumes << ["-v", "#{INSECURE_KEY}:#{key}:ro",
"-v", "/var/tmp/vagrant:/var/tmp/vagrant",
"-v", "/sys/fs/cgroup:/sys/fs/cgroup",
"-v", "/var/run/docker.sock:/var/run/docker.sock" ]
SLAVES_COUNT.times do |i|
index = i + 1
key = get_machine_key index.to_s
docker_volumes << ["-v", "#{INSECURE_KEY}:#{key}:ro"]
end
docker_volumes.flatten!
@logger.info("Crafted docker volumes: #{docker_volumes}")
end
Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
if provider == :docker
# W/a unimplemented docker networking, see
# https://github.com/mitchellh/vagrant/issues/6667.
# Create or delete the solar net (depends on the vagrant action)
# TODO(bogdando) use https://github.com/jpetazzo/pipework for multi net.
# Hereafter, we will use only the 1st IP address and a single interface.
config.trigger.before :up do
system <<-SCRIPT
if ! docker network inspect solar >/dev/null 2>&1 ; then
docker network create -d bridge \
-o "com.docker.network.bridge.enable_icc"="true" \
-o "com.docker.network.bridge.enable_ip_masquerade"="true" \
-o "com.docker.network.driver.mtu"="1500" \
--gateway=#{SLAVES_IPS[0]}1 \
--ip-range=#{SLAVES_IPS[0]}0/24 \
--subnet=#{SLAVES_IPS[0]}0/24 \
solar >/dev/null 2>&1
fi
SCRIPT
end
config.trigger.after :destroy do
system <<-SCRIPT
docker network rm solar >/dev/null 2>&1
SCRIPT
end
config.vm.provider :docker do |d, override|
d.image = DOCKER_MASTER_IMAGE
d.remains_running = false
d.has_ssh = false
d.cmd = DOCKER_CMD.split(' ')
end
else
config.vm.box = MASTER_IMAGE
config.vm.box_version = MASTER_IMAGE_VERSION
end
config.vm.define "solar-dev", primary: true do |config|
config.vm.host_name = "solar-dev"
if provider == :docker
config.vm.provider :docker do |d, override|
d.name = "solar-dev"
d.create_args = ["-i", "-t", "--privileged", "--ip=#{MASTER_IPS[0]}", "--net=solar",
docker_volumes].flatten
end
config.trigger.after :up, :option => { :vm => 'solar-dev'} do
docker_exec("solar-dev","/usr/sbin/rsyslogd >/dev/null 2>&1")
docker_exec("solar-dev","/usr/sbin/sshd >/dev/null 2>&1")
docker_exec("solar-dev","#{fix_six} >/dev/null 2>&1")
docker_exec("solar-dev","#{solar_exec}")
docker_exec("solar-dev","#{master_pxe} >/dev/null 2>&1") unless PREPROVISIONED
end
else
# not the docker provider
config.vm.provision "shell", inline: solar_script, privileged: true, env: {"SOLAR_DB_BACKEND": SOLAR_DB_BACKEND}
config.vm.provision "shell", inline: master_pxe, privileged: true unless PREPROVISIONED
config.vm.provision "file", source: INSECURE_KEY, destination: KEY_PATH1
config.vm.provider :virtualbox do |v|
v.memory = MASTER_RAM
v.cpus = MASTER_CPUS
v.customize [
"modifyvm", :id,
"--memory", MASTER_RAM,
"--cpus", MASTER_CPUS,
"--ioapic", "on",
]
if PARAVIRT_PROVIDER
v.customize ['modifyvm', :id, "--paravirtprovider", PARAVIRT_PROVIDER] # for linux guest
end
v.name = "solar-dev"
end
config.vm.provider :libvirt do |libvirt|
libvirt.driver = 'kvm'
libvirt.memory = MASTER_RAM
libvirt.cpus = MASTER_CPUS
libvirt.nested = true
libvirt.cpu_mode = 'host-passthrough'
libvirt.volume_cache = 'unsafe'
libvirt.disk_bus = "virtio"
end
ind = 0
MASTER_IPS.each do |ip|
config.vm.network :private_network, ip: "#{ip}", :dev => "solbr#{ind}", :mode => 'nat'
ind = ind + 1
end
if SYNC_TYPE == 'nfs'
config.vm.synced_folder ".", "/vagrant", type: "nfs"
end
if SYNC_TYPE == 'rsync'
config.vm.synced_folder ".", "/vagrant", type: "rsync",
rsync__args: ["--verbose", "--archive", "--delete", "-z"]
end
end
end
SLAVES_COUNT.times do |i|
index = i + 1
ip_index = i + 3
config.vm.define "solar-dev#{index}" do |config|
config.vm.host_name = "solar-dev#{index}"
if provider == :docker
config.vm.provider :docker do |d, override|
d.name = "solar-dev#{index}"
d.image = DOCKER_SLAVES_IMAGE
d.create_args = ["-i", "-t", "--privileged", "--ip=#{SLAVES_IPS[0]}#{ip_index}", "--net=solar",
docker_volumes].flatten
end
config.trigger.after :up, :option => { :vm => "solar-dev#{index}" } do
docker_exec("solar-dev#{index}","/usr/sbin/rsyslogd >/dev/null 2>&1")
docker_exec("solar-dev#{index}","/usr/sbin/sshd >/dev/null 2>&1")
docker_exec("solar-dev#{index}","#{fix_six} >/dev/null 2>&1")
docker_exec("solar-dev#{index}","#{solar_agent_script}") if PREPROVISIONED
end
else
# not the docker provider
# Standard box with all stuff preinstalled
config.vm.box = SLAVES_IMAGE
config.vm.box_version = SLAVES_IMAGE_VERSION
if PREPROVISIONED
config.vm.provision "shell", inline: solar_agent_script, privileged: true
#TODO(bogdando) figure out how to configure multiple interfaces when was not PREPROVISIONED
ind = 0
SLAVES_IPS.each do |ip|
config.vm.network :private_network, ip: "#{ip}#{ip_index}", :dev => "solbr#{ind}", :mode => 'nat'
ind = ind + 1
end
else
# Disable attempts to install guest os and check that node is booted using ssh,
# because nodes will have ip addresses from dhcp, and vagrant doesn't know
# which ip to use to perform connection
config.vm.communicator = :noop
config.vm.guest = :noop_guest
# Configure network to boot vm using pxe
config.vm.network "private_network", adapter: 1, ip: "10.0.0.#{ip_index}"
config.vbguest.no_install = true
config.vbguest.auto_update = false
end
config.vm.provider :virtualbox do |v|
boot_order(v, ['net', 'disk'])
v.customize [
"modifyvm", :id,
"--memory", SLAVES_RAM,
"--cpus", SLAVES_CPUS,
"--ioapic", "on",
"--macaddress1", "auto",
]
if PARAVIRT_PROVIDER
v.customize ['modifyvm', :id, "--paravirtprovider", PARAVIRT_PROVIDER] # for linux guest
end
v.name = "solar-dev#{index}"
end
config.vm.provider :libvirt do |libvirt|
libvirt.driver = 'kvm'
libvirt.memory = SLAVES_RAM
libvirt.cpus = SLAVES_CPUS
libvirt.nested = true
libvirt.cpu_mode = 'host-passthrough'
libvirt.volume_cache = 'unsafe'
libvirt.disk_bus = "virtio"
end
if PREPROVISIONED
if SYNC_TYPE == 'nfs'
config.vm.synced_folder ".", "/vagrant", type: "nfs"
end
if SYNC_TYPE == 'rsync'
config.vm.synced_folder ".", "/vagrant", type: "rsync",
rsync__args: ["--verbose", "--archive", "--delete", "-z"]
end
end
end
end
end
end
def boot_order(virt_config, order)
# Boot order is specified with special flag:
# --boot<1-4> none|floppy|dvd|disk|net
4.times do |idx|
device = order[idx] || 'none'
virt_config.customize ['modifyvm', :id, "--boot#{idx + 1}", device]
end
end