├── .gitignore ├── LICENSE ├── README.md ├── build.sh ├── isolinux.cfg ├── late_command.sh ├── preseed.cfg └── test ├── Vagrantfile ├── manifests └── default.pp └── test.sh /.gitignore: -------------------------------------------------------------------------------- 1 | build/ 2 | test/ 3 | iso/ 4 | 5 | .DS_Store 6 | 7 | *.box 8 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (C) 2012 Carl Johan Crafoord, Benson Wong 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of 4 | this software and associated documentation files (the "Software"), to deal in 5 | the Software without restriction, including without limitation the rights to 6 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 7 | the Software, and to permit persons to whom the Software is furnished to do so, 8 | subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in all 11 | copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 15 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 16 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 17 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 18 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 19 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## About 2 | 3 | This script will: 4 | 5 | 1. download the Ubuntu 12.04 alternate server, 64bit iso 6 | 2. ... do some magic to turn it into a vagrant box file 7 | 3. output package.box 8 | 9 | ## Usage 10 | 11 | ./build.sh 12 | 13 | This should do everything you need. If you don't have 14 | mkisofs, install [homebrew](http://mxcl.github.com/homebrew/), then: 15 | 16 | brew install cdrtools 17 | 18 | ### Ben's notes 19 | 20 | Forked Carl's repo, and it sort of worked out of the box. Tweaked 21 | office 12.04 release: 22 | 23 | - Downloading 12.04 final release. (Today as of this writing) 24 | - Checking MD5 to make sure it is the right version 25 | - Added a few more checks for external dependencies, mkisofs 26 | - Removed wget, and used curl to reduce dependencies 27 | - Added more output to see what is going on 28 | - Still designed to work on Mac OS X :) 29 | ... though it should work for Linux systems too (maybe w/ a bit of porting) 30 | 31 | ### Carl's original README 32 | 33 | Decided I wanted to learn how to make a vagrant base box. 34 | 35 | Let's target Precise Pangolin since it should be releasing soon, I said. 36 | 37 | Let's automate everything, I said. 38 | 39 | Let's do it all on my macbook, I said. 40 | 41 | Woo. 42 | -------------------------------------------------------------------------------- /build.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # make sure we have dependencies 4 | hash mkisofs 2>/dev/null || { echo >&2 "ERROR: mkisofs not found. Aborting."; exit 1; } 5 | 6 | set -o nounset 7 | set -o errexit 8 | #set -o xtrace 9 | 10 | # Configurations 11 | BOX="ubuntu-precise-64" 12 | ISO_URL="http://releases.ubuntu.com/precise/ubuntu-12.04-alternate-amd64.iso" 13 | ISO_MD5="9fcc322536575dda5879c279f0b142d7" 14 | 15 | # location, location, location 16 | FOLDER_BASE=`pwd` 17 | FOLDER_ISO="${FOLDER_BASE}/iso" 18 | FOLDER_BUILD="${FOLDER_BASE}/build" 19 | FOLDER_VBOX="${FOLDER_BUILD}/vbox" 20 | FOLDER_ISO_CUSTOM="${FOLDER_BUILD}/iso/custom" 21 | FOLDER_ISO_INITRD="${FOLDER_BUILD}/iso/initrd" 22 | 23 | # start with a clean slate 24 | if [ -d "${FOLDER_BUILD}" ]; then 25 | echo "Cleaning build directory ..." 26 | chmod -R u+w "${FOLDER_BUILD}" 27 | rm -rf "${FOLDER_BUILD}" 28 | mkdir -p "${FOLDER_BUILD}" 29 | fi 30 | 31 | # Setting things back up again 32 | mkdir -p "${FOLDER_ISO}" 33 | mkdir -p "${FOLDER_BUILD}" 34 | mkdir -p "${FOLDER_VBOX}" 35 | mkdir -p "${FOLDER_ISO_CUSTOM}" 36 | mkdir -p "${FOLDER_ISO_INITRD}" 37 | 38 | ISO_FILENAME="${FOLDER_ISO}/`basename ${ISO_URL}`" 39 | INITRD_FILENAME="${FOLDER_ISO}/initrd.gz" 40 | ISO_GUESTADDITIONS="/Applications/VirtualBox.app/Contents/MacOS/VBoxGuestAdditions.iso" 41 | 42 | # download the installation disk if you haven't already or it is corrupted somehow 43 | echo "Downloading `basename ${ISO_URL}` ..." 44 | if [ ! -e "${ISO_FILENAME}" ]; then 45 | curl --output "${ISO_FILENAME}" -L "${ISO_URL}" 46 | 47 | # make sure download is right... 48 | ISO_HASH=`md5 -q "${ISO_FILENAME}"` 49 | if [ "${ISO_MD5}" != "${ISO_HASH}" ]; then 50 | echo "ERROR: MD5 does not match. Got ${ISO_HASH} instead of ${ISO_MD5}. Aborting." 51 | exit 1 52 | fi 53 | fi 54 | 55 | # customize it 56 | echo "Creating Custom ISO" 57 | if [ ! -e "${FOLDER_ISO}/custom.iso" ]; then 58 | 59 | echo "Untarring downloaded ISO ..." 60 | tar -C "${FOLDER_ISO_CUSTOM}" -xf "${ISO_FILENAME}" 61 | 62 | # backup initrd.gz 63 | echo "Backing up current init.rd ..." 64 | chmod u+w "${FOLDER_ISO_CUSTOM}/install" "${FOLDER_ISO_CUSTOM}/install/initrd.gz" 65 | mv "${FOLDER_ISO_CUSTOM}/install/initrd.gz" "${FOLDER_ISO_CUSTOM}/install/initrd.gz.org" 66 | 67 | # stick in our new initrd.gz 68 | echo "Installing new initrd.gz ..." 69 | cd "${FOLDER_ISO_INITRD}" 70 | gunzip -c "${FOLDER_ISO_CUSTOM}/install/initrd.gz.org" | cpio -id 71 | cd "${FOLDER_BASE}" 72 | cp preseed.cfg "${FOLDER_ISO_INITRD}/preseed.cfg" 73 | cd "${FOLDER_ISO_INITRD}" 74 | find . | cpio --create --format='newc' | gzip > "${FOLDER_ISO_CUSTOM}/install/initrd.gz" 75 | 76 | # clean up permissions 77 | echo "Cleaning up Permissions ..." 78 | chmod u-w "${FOLDER_ISO_CUSTOM}/install" "${FOLDER_ISO_CUSTOM}/install/initrd.gz" "${FOLDER_ISO_CUSTOM}/install/initrd.gz.org" 79 | 80 | # replace isolinux configuration 81 | echo "Replacing isolinux config ..." 82 | cd "${FOLDER_BASE}" 83 | chmod u+w "${FOLDER_ISO_CUSTOM}/isolinux" "${FOLDER_ISO_CUSTOM}/isolinux/isolinux.cfg" 84 | rm "${FOLDER_ISO_CUSTOM}/isolinux/isolinux.cfg" 85 | cp isolinux.cfg "${FOLDER_ISO_CUSTOM}/isolinux/isolinux.cfg" 86 | chmod u+w "${FOLDER_ISO_CUSTOM}/isolinux/isolinux.bin" 87 | 88 | # add late_command script 89 | echo "Add late_command script ..." 90 | chmod u+w "${FOLDER_ISO_CUSTOM}" 91 | cp "${FOLDER_BASE}/late_command.sh" "${FOLDER_ISO_CUSTOM}" 92 | 93 | echo "Running mkisofs ..." 94 | mkisofs -r -V "Custom Ubuntu Install CD" \ 95 | -cache-inodes -quiet \ 96 | -J -l -b isolinux/isolinux.bin \ 97 | -c isolinux/boot.cat -no-emul-boot \ 98 | -boot-load-size 4 -boot-info-table \ 99 | -o "${FOLDER_ISO}/custom.iso" "${FOLDER_ISO_CUSTOM}" 100 | 101 | fi 102 | 103 | echo "Creating VM Box..." 104 | # create virtual machine 105 | if ! VBoxManage showvminfo "${BOX}" >/dev/null 2>/dev/null; then 106 | VBoxManage createvm \ 107 | --name "${BOX}" \ 108 | --ostype Ubuntu_64 \ 109 | --register \ 110 | --basefolder "${FOLDER_VBOX}" 111 | 112 | VBoxManage modifyvm "${BOX}" \ 113 | --memory 360 \ 114 | --boot1 dvd \ 115 | --boot2 disk \ 116 | --boot3 none \ 117 | --boot4 none \ 118 | --vram 12 \ 119 | --pae off \ 120 | --rtcuseutc on 121 | 122 | VBoxManage storagectl "${BOX}" \ 123 | --name "IDE Controller" \ 124 | --add ide \ 125 | --controller PIIX4 \ 126 | --hostiocache on 127 | 128 | VBoxManage storageattach "${BOX}" \ 129 | --storagectl "IDE Controller" \ 130 | --port 1 \ 131 | --device 0 \ 132 | --type dvddrive \ 133 | --medium "${FOLDER_ISO}/custom.iso" 134 | 135 | VBoxManage storagectl "${BOX}" \ 136 | --name "SATA Controller" \ 137 | --add sata \ 138 | --controller IntelAhci \ 139 | --sataportcount 1 \ 140 | --hostiocache off 141 | 142 | VBoxManage createhd \ 143 | --filename "${FOLDER_VBOX}/${BOX}/${BOX}.vdi" \ 144 | --size 40960 145 | 146 | VBoxManage storageattach "${BOX}" \ 147 | --storagectl "SATA Controller" \ 148 | --port 0 \ 149 | --device 0 \ 150 | --type hdd \ 151 | --medium "${FOLDER_VBOX}/${BOX}/${BOX}.vdi" 152 | 153 | VBoxManage startvm "${BOX}" 154 | 155 | echo -n "Waiting for installer to finish " 156 | while VBoxManage list runningvms | grep "${BOX}" >/dev/null; do 157 | sleep 20 158 | echo -n "." 159 | done 160 | echo "" 161 | 162 | # Forward SSH 163 | VBoxManage modifyvm "${BOX}" \ 164 | --natpf1 "guestssh,tcp,,2222,,22" 165 | 166 | # Attach guest additions iso 167 | VBoxManage storageattach "${BOX}" \ 168 | --storagectl "IDE Controller" \ 169 | --port 1 \ 170 | --device 0 \ 171 | --type dvddrive \ 172 | --medium "${ISO_GUESTADDITIONS}" 173 | 174 | VBoxManage startvm "${BOX}" 175 | 176 | # get private key 177 | curl --output "${FOLDER_BUILD}/id_rsa" "https://raw.github.com/mitchellh/vagrant/master/keys/vagrant" 178 | chmod 600 "${FOLDER_BUILD}/id_rsa" 179 | 180 | # install virtualbox guest additions 181 | ssh -i "${FOLDER_BUILD}/id_rsa" -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -p 2222 vagrant@127.0.0.1 "sudo mount /dev/cdrom /media/cdrom; sudo sh /media/cdrom/VBoxLinuxAdditions.run; sudo umount /media/cdrom; sudo shutdown -h now" 182 | echo -n "Waiting for machine to shut off " 183 | while VBoxManage list runningvms | grep "${BOX}" >/dev/null; do 184 | sleep 20 185 | echo -n "." 186 | done 187 | echo "" 188 | 189 | VBoxManage modifyvm "${BOX}" --natpf1 delete "guestssh" 190 | 191 | # Detach guest additions iso 192 | echo "Detach guest additions ..." 193 | VBoxManage storageattach "${BOX}" \ 194 | --storagectl "IDE Controller" \ 195 | --port 1 \ 196 | --device 0 \ 197 | --type dvddrive \ 198 | --medium emptydrive 199 | fi 200 | 201 | echo "Building Vagrant Box ..." 202 | vagrant package --base "${BOX}" 203 | 204 | # references: 205 | # http://blog.ericwhite.ca/articles/2009/11/unattended-debian-lenny-install/ 206 | # http://cdimage.ubuntu.com/releases/precise/beta-2/ 207 | # http://www.imdb.com/name/nm1483369/ 208 | # http://vagrantup.com/docs/base_boxes.html 209 | -------------------------------------------------------------------------------- /isolinux.cfg: -------------------------------------------------------------------------------- 1 | # unattended installation 2 | default unattended 3 | prompt 0 4 | timeout 0 5 | label unattended 6 | kernel /install/vmlinuz 7 | append vga=788 initrd=/install/initrd.gz quiet -- 8 | -------------------------------------------------------------------------------- /late_command.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # passwordless sudo 4 | echo "%sudo ALL=NOPASSWD: ALL" >> /etc/sudoers 5 | 6 | # public ssh key for vagrant user 7 | mkdir /home/vagrant/.ssh 8 | wget -O /home/vagrant/.ssh/authorized_keys "https://raw.github.com/mitchellh/vagrant/master/keys/vagrant.pub" 9 | chmod 755 /home/vagrant/.ssh 10 | chmod 644 /home/vagrant/.ssh/authorized_keys 11 | chown -R vagrant:vagrant /home/vagrant/.ssh 12 | 13 | # speed up ssh 14 | echo "UseDNS no" >> /etc/ssh/sshd_config 15 | 16 | # get chef 17 | gem install chef --no-rdoc --no-ri 18 | 19 | # display login promt after boot 20 | sed "s/quiet splash//" /etc/default/grub > /tmp/grub 21 | mv /tmp/grub /etc/default/grub 22 | update-grub 23 | 24 | # clean up 25 | apt-get clean 26 | -------------------------------------------------------------------------------- /preseed.cfg: -------------------------------------------------------------------------------- 1 | # People should live in Sweden 2 | d-i debian-installer/country string SE 3 | 4 | # Computers should speak English 5 | d-i debian-installer/language string en 6 | d-i debian-installer/locale string en_US.UTF-8 7 | d-i localechooser/preferred-locale string en_US.UTF-8 8 | d-i localechooser/supported-locales en_US.UTF-8 9 | 10 | # But keyboards are Swedish 11 | d-i console-setup/ask_detect boolean false 12 | d-i keyboard-configuration/layout select Swedish 13 | d-i keyboard-configuration/variant select Swedish 14 | d-i keyboard-configuration/modelcode string pc105 15 | d-i keyboard-configuration/layoutcode string se 16 | d-i keyboard-configuration/xkb-keypam select se 17 | 18 | # Pick any network interface and go with it 19 | d-i netcfg/get_hostname string vagrant-ubuntu-precise 20 | d-i netcfg/get_domain string vagrantup.com 21 | 22 | # What's a vagrant? 23 | d-i passwd/user-fullname string 24 | d-i passwd/username string vagrant 25 | d-i passwd/user-password password vagrant 26 | d-i passwd/user-password-again password vagrant 27 | d-i user-setup/allow-password-weak boolean true 28 | d-i user-setup/encrypt-home boolean false 29 | 30 | # We've got all the time in the world 31 | d-i time/zone string Europe/Stockholm 32 | d-i clock-setup/utc boolean true 33 | 34 | # Need to do something about that disk 35 | d-i partman-auto/method string regular 36 | d-i partman-partitioning/confirm_write_new_label boolean true 37 | d-i partman/choose_partition select finish 38 | d-i partman/confirm boolean true 39 | d-i partman/confirm_nooverwrite boolean true 40 | 41 | # No proxy, please 42 | d-i mirror/http/proxy string 43 | 44 | # Only install the standard system and language packs. 45 | tasksel tasksel/first multiselect 46 | d-i preseed/early_command string . /usr/share/debconf/confmodule; db_get debconf/priority; case $RET in low|medium) db_fset tasksel/first seen false; echo 'tasksel tasksel/first seen false' >>/var/lib/preseed/log ;; esac 47 | d-i pkgsel/language-pack-patterns string 48 | 49 | # No language support packages. 50 | d-i pkgsel/install-language-support boolean false 51 | 52 | # Individual additional packages to install 53 | d-i pkgsel/include string build-essential nfs-common puppet ruby-dev rubygems ssh 54 | 55 | # Whether to upgrade packages after debootstrap. 56 | # Allowed values: none, safe-upgrade, full-upgrade 57 | d-i pkgsel/upgrade select safe-upgrade 58 | 59 | # Go grub, go! 60 | d-i grub-installer/only_debian boolean true 61 | 62 | # Wrapping things up 63 | d-i preseed/late_command string cp /cdrom/late_command.sh /target/tmp/late_command.sh && in-target chmod +x /tmp/late_command.sh && in-target /tmp/late_command.sh 64 | 65 | # Shut down, already 66 | d-i finish-install/reboot_in_progress note 67 | d-i debian-installer/exit/poweroff boolean true 68 | -------------------------------------------------------------------------------- /test/Vagrantfile: -------------------------------------------------------------------------------- 1 | Vagrant::Config.run do |config| 2 | # Setup the box 3 | config.vm.box = "ubuntu-precise-64" 4 | 5 | # Enable the Puppet provisioner 6 | config.vm.provision :puppet 7 | 8 | # Enable and configure the chef solo provisioner 9 | config.vm.provision :chef_solo do |chef| 10 | # We're going to download our cookbooks from the web 11 | chef.recipe_url = "http://files.vagrantup.com/getting_started/cookbooks.tar.gz" 12 | 13 | # Tell chef what recipe to run. In this case, the `vagrant_main` recipe 14 | # does all the magic. 15 | chef.add_recipe("vagrant_main") 16 | end 17 | 18 | # Some NFS testing 19 | config.vm.share_folder("v-root", "/vagrant", ".", :nfs => true) 20 | 21 | # Static host-only IP 22 | config.vm.network :hostonly, "10.0.73.57" 23 | end 24 | -------------------------------------------------------------------------------- /test/manifests/default.pp: -------------------------------------------------------------------------------- 1 | # Basic Puppet Apache manifest 2 | 3 | class apache { 4 | exec { 'apt-get update': 5 | command => '/usr/bin/apt-get update' 6 | } 7 | 8 | package { "apache2": 9 | ensure => present, 10 | } 11 | 12 | service { "apache2": 13 | ensure => running, 14 | require => Package["apache2"], 15 | } 16 | } 17 | 18 | include apache 19 | -------------------------------------------------------------------------------- /test/test.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | if ! vagrant box list | grep ubuntu-precise-64 >/dev/null; then 4 | vagrant box add ubuntu-precise-64 ../package.box 5 | fi 6 | 7 | vagrant up 8 | vagrant ssh 9 | --------------------------------------------------------------------------------