#!/usr/bin/python | |
# NOTE: We need the system wide Python(2.6) because that's where | |
# the guestfs libs are installed (RHEL6.X) | |
# rpm package python-libguestfs is required for this to work | |
# | |
# yum install python-libguestfs | |
# | |
# Provide the disk image name as the only argument to this script | |
# | |
import guestfs | |
import sys, string | |
assert (len (sys.argv) == 2) | |
disk = sys.argv[1] | |
# For return values we want a dict object | |
g = guestfs.GuestFS (python_return_dict=True) | |
# Add our image | |
g.add_drive_opts (disk) | |
# Launch the guestfs back-end (same as run) | |
g.launch() | |
# Ask libguestfs to inspect for operating systems. | |
roots = g.inspect_os() | |
if len(roots) == 0: | |
raise (Error ("inspect_vm: no operating systems found")) | |
# We should get one device back, likely /dev/sda | |
devs = g.list_devices() | |
if len(devs) == 1: | |
dev = devs[0] | |
print "Found one device: %s" % dev | |
else: | |
print "Found more than one dev, please specify which one you want to operate on.." | |
sys.exit(1) | |
# We are expecting 2 partitions back from this device | |
# 1st part is boot partition | |
# 2nd part is pvs with root.fs and swap.vol in it | |
partitions = g.part_list(dev) | |
if len(partitions) == 2: | |
print "Found 2 partitions" | |
# double check that 2nd part is actually #2 and get it's start location | |
if partitions[1]['part_num'] == 2: | |
part_start = partitions[1]['part_start'] | |
dev_part = dev + str(partitions[1]['part_num']) | |
else: | |
print "cant find 2nd partition to modify.." | |
sys.exit(2) | |
else: | |
print "expected 2 partitions found %i instead" % len(partitions) | |
# Get block size | |
blk_size = g.blockdev_getss(dev) | |
print "Block size: %i" % blk_size | |
# Calculate start sector | |
start_sector = part_start / blk_size | |
print "Caclulated start sector: %i" % start_sector | |
# Delete 2nd partition on image | |
if g.part_del(dev, 2): | |
print "Parition delete failed.. Exiting" | |
sys.exit(3) | |
print "Old partition removed" | |
# Flush device | |
print "Flushing buffers.." | |
g.blockdev_flushbufs(dev) | |
# Recreate 2nd partition -1 means last sector | |
# NOTE: This command will issue a warning about the kernel failing to re-read the part table, this is ok and expected | |
# Actually it returns -1 even though it succeeds | |
try: | |
g.part_add(dev, 'p', start_sector, -1) | |
except RuntimeError as msg: | |
print "Part add failed due to re-read of partition table, this is normal and expected.. Ignored.." | |
print "Partition created/expanded" | |
# Shutdown and restart guestfs to get our newly expanded partition table to be seen | |
print "Restarting guestfs (this takes a second)" | |
g.shutdown() | |
g.add_drive_opts(disk) | |
g.launch() | |
# Resize the PV | |
if g.pvresize(dev_part): | |
print "pvresize failed.. Exiting" | |
sys.exit(5) | |
print "pv resized" | |
# Find and resize our volumes now | |
vols = g.lvs() | |
for vol in vols: | |
if string.find(string.split(vol, '/')[-1], "root.fs") >= 0: | |
print "root vol is: %s" % vol | |
root_vol = vol | |
if string.find(string.split(vol, '/')[-1], "swap.vol") >= 0: | |
print "swap vol is: %s" % vol | |
swap_vol = vol | |
if g.lvresize(swap_vol, 6144): | |
print "lvresize on swap failed.. Exiting" | |
sys.exit(6) | |
print "lvresize on swap succeeded" | |
if g.lvresize_free(root_vol, 100): | |
print "lvresize on root failed.. Exiting" | |
sys.exit(7) | |
print "lvresize on root succeeded" | |
if g.resize2fs(root_vol): | |
print "resize2fs on root vol failed.. Exiting" | |
sys.exit(8) | |
print "resize2fs on root succeeded" | |
if g.e2fsck(root_vol, correct=True): | |
print "e2fsck on root vol failed.. Exiting" | |
sys.exit(9) | |
print "e2fsck on root succeeded" | |
print "Resize completed, go ahead and boot the vm now" | |
g.shutdown() | |
g.close() | |
sys.exit(0) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment