0.0
No commit activity in last 3 years
No release in over 3 years
Amazon Cloud Formation driver for zergrush
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
2025
2026
 Dependencies

Development

>= 1.0.0
>= 0
>= 0.0.24

Runtime

>= 1.2.1
>= 1.20.0
>= 0.0.5
 Project Readme

Zerg

Zerg is a tool for launching an arbitrary number of virtual machines and running a task on all of them at once.

  • Tested on Ubuntu 12.04
  • YMMV on OSX, however it is recommended you use the provided dev VM
  • JSON config files
  • Supports vagrant virtualbox, vagrant-aws and vagrant-libvirt providers
  • planned support for more hypervisor orchestration tools and providers
  • Ruby 1.9 required

Attributions

Zerg uses a number of open source projects to work properly:

Develop (OSX)

Install Vagrant. Then:

git clone git@github.com:MTNSatelliteComm/zerg.git zerg
cd zerg/dev_env
vagrant plugin install vagrant-berkshelf
vagrant plugin install vagrant-butcher
vagrant plugin install vagrant-omnibus
vagrant up --provision
vagrant ssh
cd /zerg

See if Virtualbox is functioning normally:

VBoxManage --version

Use

From Rubygems:

gem install zergrush

From source:

cd zerg
rake install

cd to a folder where you would like to use zerg from and:

zerg init
zerg rush <task name>

'zerg init' command initializes two example tasks - helloworld and helloaws. Try them with:

zerg rush helloworld

Note that prior to trying the helloaws task you will need to set some environment variables:

  • AWS_ACCESS_KEY_ID - AWS key id
  • AWS_SECRET_ACCESS_KEY - AWS secret key
  • AWS_KEY_PAIR - AWS key pair name
  • AWS_PRIVATE_KEY_PATH - path to the private key .pem
  • AWS_SECURITY_GROUP - name of an AWS security group to use

You will then be able to run the task with:

zerg rush helloaws

Tasks

Zerg task files are json files that are loaded by zerg, validated, and then transformed into a Vagrantfile. Vagrant is then launched against that generated vagrantfile.

Task JSON schema

  • num_instances - number of virtual machines that'll be started
  • synced_folders - array of folders to sync
    • host_path - path to folder on the host
    • guest_path - path to folder on the guest that host_path will map to
    • options - array of options corresponding to Vagrant sync folder options
  • tasks - array of tasks. Task definitions vary by driver type. For example: Vagrant driver schema
  • vm - description of all VM instances.
    • private_ip_range - IP address range in CIDR notation used for all private ip addresses, unless said address is explicitly specified by another option. First host ip in range is always the host machine.
    • driver - properties of a hypervisor 'driver'. Currently only Vagrant is supported
      • drivertype - Type of the 'driver' Only 'vagrant' is currently supported.
      • driveroptions - options for the driver, defined by driver plugin
    • instances - array of detailed descriptions of each/some of the vm instances. Last definition in the array is applied to the rest of remaining instances. For example: if num_instances is 3 and there are 2 items in instances array, then first VM will correspond to the first item, and the other two VMs will correspond to the second.
      • basebox - basebox file location or URL
      • keepalive - keep this instance around after all tasks are finished
      • tasks - array of tasks to run. Task properties are defined by driver plugin
      • synced_folders - array of synchronized folders
        • host_path - path on host
        • guest_path - corresponding path on guest
        • additional - addtional properties defined by driver plugin
      • forwarded_ports - array of port forwarding descriptions
        • guest_port port on guest to be forwarded
        • host_port - port on host to be forwarded to
        • additional - addtional properties defined by driver plugin
      • networks - array of networks to be setup - NAT/bridging/etc. Network options are defined by driver plugin
      • ssh - SSH options
        • username - ssh username
        • host - ssh host, normally autodetected
        • port - host ssh port
        • guest_port - guest ssh port
        • private_key_path - path to the private key file
        • forward_agent - do SSH agent forwarding
        • additional - addtional properties defined by driver plugin

Example task

Below example task that:

  • will start 5 virtual machines using vagrant
  • first machine will be backed by VirtualBox
  • other machines will be backed by AWS
  • first machine will run some shell commands and will have a private network and a public network, bridged over host's AirPort adapter. It will also stay up after all other tasks are doen running
  • second machine will have git installed on it with chef client
  • all other machines will run 'starter' cookbook through chef solo
{
    "num_instances": 5,
    "vm": {
        "driver": {
            "drivertype": "vagrant",
            "driveroptions": [
                {
                    "providertype": "virtualbox",
                    "provider_options" : {
                        "gui": false,
                        "memory": 256
                    }
                },
                {
                    "providertype": "aws",
                    "provider_options" : {
                        "instance_type": "t1.micro",
                        "access_key_id": "YOUR_AWS_ACCESS_KEY_ID",
                        "secret_access_key": "YOUR_AWS_SECRET",
                        "keypair_name": "AWS_KEYPAIR_NAME",
                        "ami": "ami-3fec7956",
                        "region": "us-east-1",
                        "security_groups": [ "your_security_group" ]
                    }
                }
            ]
        },
        "private_ip_range": "192.168.50.0/24",
        "instances": [
            {
                "basebox": "http://files.vagrantup.com/precise32.box",
                "keepalive": true,
                "tasks": [
                    {
                        "type": "shell",
                        "inline": "ping -c 3 192.168.50.1; echo \"ZERG RUSH FIRST!\""
                    }        
                ],
                "networks": [
                    {
                        "type": "private_network"
                    },
                    {
                        "type": "public_network",
                        "bridge": "en1: Wi-Fi (AirPort)"
                    }         
                ],
                "synced_folders": [
                    {
                        "host_path": "~",
                        "guest_path": "/zerg/hosthome"
                    }        
                ],
                "forwarded_ports": [
                    {
                        "guest_port": 8080,
                        "host_port": 80
                    }        
                ],
            },
            {
                "basebox": "https://github.com/mitchellh/vagrant-aws/raw/master/dummy.box",
                "keepalive": false,
                "tasks": [
                    {
                        "type": "chef_client",
                        "chef_server_url": "CHEF_URL",
                        "validation_key_path": "CHEF_VALIDATION_KEYPATH",
                        "client_key_path": "CHEF_CLIENT_KEYPATH",
                        "validation_client_name": "CHEF_VALIDATION_CLIENT_NAME",
                        "delete_node": true,
                        "delete_client": true,
                        "run_list": ["recipe[git]"]
                    }        
                ],
                "ssh": {
                    "username": "ubuntu",
                    "private_key_path": "PATH_TO_YOUR_PK"      
                }
            },
            {
                "basebox": "https://github.com/mitchellh/vagrant-aws/raw/master/dummy.box",
                "keepalive": false,
                "tasks": [
                    {
                        "type": "chef_solo",
                        "cookbooks_path": ["~/cookbooks"],
                        "run_list": ["recipe[starter]"]
                    }        
                ],
                "ssh": {
                    "username": "ubuntu",
                    "private_key_path": "PATH_TO_YOUR_PK"      
                }
            }
        ]
    }
}

Other commands

CLI help is available from the gem:

zerg help

Environment variables

By default Zerg will look for '.hive' in the current directory. You can override this location by setting an enviroment variable:

export HIVE_CWD=/path/to/wherever/you/want

Tests

cd zerg
bundle exec cucumber features/

Plugins

Zerg plugins are ruby gems. Each plugin gem must have an 'init.rb' file lib/gem_name/init.rb

required in the init.rb file:

require 'zerg'

class Vagrant < ZergGemPlugin::Plugin "/driver"
    def rush hive_location, task_name, task_hash, debug
        # 'zerg rush <task>' functionality.   
    end

    def clean hive_location, task_name, task_hash, debug
        # 'zerg clean <task>' functionality.
    end

    def halt hive_location, task_name, task_hash, debug
        # 'zerg halt <task>' functionality 
    end

    def task_schema
        # return a chunk of JSON schema for defining task item in tasks array
    end

    def option_schema
        # return a chunk of JSON schema for defining driver options
    end

    def folder_schema
        # return a chunk of JSON schema for defining driver-specific sync_folder options
    end

    def port_schema
        # return a chunk of JSON schema for defining driver-specific port forwarding options
    end

    def ssh_schema
        # return a chunk of JSON schema for defining driver-specific ssh options
    end
end

also, in the gem's gemspec file the following metadata must be present:

Gem::Specification.new do |s|
  s.name        = "your_plugin"
 
 ...

  # metadata that marks this as a zergrush plugin
  s.metadata = { "zergrushplugin" => "driver" }
end

Known issues

Vagrant inside vagrant

Running 64bit virtualbox VMs inside dev_env VM will most likely fail:

https://forums.virtualbox.org/viewtopic.php?f=1&t=20589&start=15

hashicorp/vagrant#572

You should still be able to run 32bit virtualbox boxes inside another VM though.

Security

JSON config files allow for snippets of ruby code to be passed through (#{ENV['BLAH']})

Not a problem locally, but would be BAD for a REST API