* Finish the EBS creation script. It now takes a --region option to

specify the EC2 region in which the AMI is to be created.  It also
  starts an instance booted from the newly created AMI to test it.

svn path=/nixos/trunk/; revision=33771
This commit is contained in:
Eelco Dolstra 2012-04-13 11:26:22 +00:00
parent 2821289aeb
commit bcc24c1b86
2 changed files with 67 additions and 9 deletions

View file

@ -4,8 +4,21 @@ import sys
from charon import deployment
from boto.ec2.blockdevicemapping import BlockDeviceMapping, BlockDeviceType
import charon.util
import time
import argparse
depl = deployment.Deployment("./ebs-creator.json", create=True, nix_exprs=["./ebs-creator.nix"])
parser = argparse.ArgumentParser(description='Create an EBS-backed NixOS AMI')
parser.add_argument('--region', dest='region', required=True, help='EC2 region')
parser.add_argument('--keep', dest='keep', action='store_true', help='keep Charon machine after use')
args = parser.parse_args()
# Start a NixOS machine in the given region.
f = open("ebs-creator-zone.nix", "w")
f.write('{{ machine.deployment.ec2.region = "{0}"; }}'.format(args.region))
f.close()
depl = deployment.Deployment("./ebs-creator.json", create=True, nix_exprs=["./ebs-creator.nix", "./ebs-creator-zone.nix"])
if not args.keep: depl.destroy_vms()
depl.deploy()
m = depl.machines['machine']
@ -17,16 +30,22 @@ m.run_command("mkdir -p /mnt")
m.run_command("mount /dev/xvdg /mnt")
m.run_command("touch /mnt/.ebs")
m.run_command("mkdir -p /mnt/etc/nixos")
m.run_command("cp /etc/nixos/configuration.nix /mnt/etc/nixos/") # FIXME
m.run_command("nixos-checkout") # FIXME
m.run_command("cp -f /etc/nixos/nixos/modules/virtualisation/amazon-config.nix /mnt/etc/nixos/configuration.nix")
m.run_command("echo -n pre$(svnversion -c /etc/nixos/nixos | sed 's/.*://')-$(svnversion -c /etc/nixos/nixpkgs | sed 's/.*://') > /etc/nixos/nixos/.version-suffix")
version = m.run_command("nixos-option system.nixosVersion", capture_stdout=True).replace('"', '').rstrip()
print >> sys.stderr, "NixOS version is {0}".format(version)
m.run_command("nixos-install")
m.run_command("rm -rf /mnt/etc/nixos/nixos/.svn /mnt/etc/nixos/nixpkgs/.svn")
m.run_command("umount /mnt")
ami_name = "nixos-{0}-x86_64-ebs".format(version)
description = "NixOS {0} (x86_64; EBS root)".format(version)
# Create a snapshot.
m.connect()
volume = m._conn.get_all_volumes([], filters={'attachment.instance-id': m._instance_id, 'attachment.device': "/dev/sdg"})[0]
snapshot = volume.create_snapshot(description="NixOS EBS root disk")
#snapshot = m._conn.get_all_snapshots(["snap-f1c9679a"])[0]
snapshot = volume.create_snapshot(description=description)
print >> sys.stderr, "created snapshot {0}".format(snapshot.id)
# Wait for the snapshot to finish.
@ -36,19 +55,59 @@ def check():
return status == '100%'
charon.util.check_wait(check, max_tries=120)
m._conn.create_tags([snapshot.id], {'Name': ami_name})
if not args.keep: depl.destroy_vms()
# Register the image.
aki = m._conn.get_all_images(filters={'manifest-location': '*pv-grub-hd0_1.03-x86_64*'})[0]
print >> sys.stderr, "using kernel image %s - %s" %(aki.id, aki.location)
print >> sys.stderr, "using kernel image {0} - {1}".format(aki.id, aki.location)
block_map = BlockDeviceMapping()
block_map['/dev/sda'] = BlockDeviceType(snapshot_id=snapshot.id, delete_on_termination=True)
block_map['/dev/sdb'] = BlockDeviceType(ephemeral_name="ephemeral0")
block_map['/dev/sdc'] = BlockDeviceType(ephemeral_name="ephemeral1")
block_map['/dev/sdd'] = BlockDeviceType(ephemeral_name="ephemeral2")
block_map['/dev/sde1'] = BlockDeviceType(ephemeral_name="ephemeral3")
block_map['/dev/sde'] = BlockDeviceType(ephemeral_name="ephemeral3")
ami_id = m._conn.register_image(
name="nixos-x86-64-ebs-test-9", description="NixOS (x86_64) EBS test", architecture="x86_64",
root_device_name="/dev/sda", kernel_id=aki.id, block_device_map=block_map)
name=ami_name,
description=description,
architecture="x86_64",
root_device_name="/dev/sda",
kernel_id=aki.id,
block_device_map=block_map)
print >> sys.stderr, "registered AMI {0}".format(ami_id)
time.sleep(5)
print >> sys.stderr, "making image public..."
image = m._conn.get_all_images(image_ids=[ami_id])[0]
image.set_launch_permissions(user_ids=[], group_names=["all"])
m._conn.create_tags([ami_id], {'Name': ami_name})
# Do a test deployment to make sure that the AMI works.
f = open("ebs-test.nix", "w")
f.write(
'''
{{ network.description = "NixOS EBS test";
machine.deployment.targetEnv = "ec2";
machine.deployment.ec2.region = "{0}";
machine.deployment.ec2.instanceType = "m1.small";
machine.deployment.ec2.keyPair = "eelco";
machine.deployment.ec2.securityGroups = [ "eelco-test" ];
machine.deployment.ec2.ami = "{1}";
}}
'''.format(args.region, ami_id))
f.close()
test_depl = deployment.Deployment("./ebs-test.json", create=True, nix_exprs=["./ebs-test.nix"])
test_depl.deploy(create_only=True)
test_depl.machines['machine'].run_command("nixos-version")
if not args.keep: test_depl.destroy_vms()
# Log the AMI ID.
f = open("{0}.ebs.ami-id".format(args.region), "w")
f.write("{0}".format(ami_id))
f.close()

View file

@ -4,7 +4,6 @@
machine =
{ config, pkgs, ... }:
{ deployment.targetEnv = "ec2";
deployment.ec2.region = "eu-west-1";
deployment.ec2.instanceType = "m1.small";
deployment.ec2.keyPair = "eelco";
deployment.ec2.securityGroups = [ "eelco-test" ];