From bed4b3ff68b211b4a921f034d564f8c0380aea3d Mon Sep 17 00:00:00 2001 From: Monty Taylor Date: Sat, 17 Oct 2015 16:04:08 -0400 Subject: [PATCH] Retire stackforge/openvz-nova-driver --- .gitignore | 38 - .gitreview | 4 - README.md | 11 - README.rst | 7 + debian/changelog | 15 - debian/compat | 1 - debian/control | 15 - debian/copyright | 0 debian/rules | 38 - debian/source/format | 1 - etc/nova/rootwrap.d/openvz.filters | 85 - ovznovadriver/__init__.py | 12 - ovznovadriver/localization.py | 3 - ovznovadriver/openvz/__init__.py | 20 - ovznovadriver/openvz/container.py | 606 ----- ovznovadriver/openvz/driver.py | 1810 --------------- ovznovadriver/openvz/file.py | 224 -- ovznovadriver/openvz/file_ext/__init__.py | 16 - ovznovadriver/openvz/file_ext/boot.py | 43 - ovznovadriver/openvz/file_ext/ext_storage.py | 118 - ovznovadriver/openvz/file_ext/shutdown.py | 45 - ovznovadriver/openvz/file_ext/start.py | 33 - ovznovadriver/openvz/file_ext/stop.py | 33 - ovznovadriver/openvz/migration.py | 386 ---- .../openvz/migration_drivers/__init__.py | 16 - .../openvz/migration_drivers/rsync.py | 66 - .../openvz/migration_drivers/transport.py | 73 - ovznovadriver/openvz/network.py | 201 -- .../openvz/network_drivers/__init__.py | 16 - .../openvz/network_drivers/network_bridge.py | 59 - ovznovadriver/openvz/network_drivers/tc.py | 284 --- .../templates/tc_container_start.template | 8 - .../templates/tc_container_stop.template | 6 - .../templates/tc_host_start.template | 5 - .../templates/tc_host_stop.template | 1 - ovznovadriver/openvz/resources.py | 405 ---- ovznovadriver/openvz/utils.py | 610 ----- ovznovadriver/openvz/volume.py | 497 ---- .../openvz/volume_drivers/__init__.py | 16 - ovznovadriver/openvz/volume_drivers/iscsi.py | 194 -- ovznovadriver/tests/openvz/__init__.py | 16 - ovznovadriver/tests/openvz/fakes.py | 826 ------- ovznovadriver/tests/openvz/test_driver.py | 2024 ----------------- .../tests/openvz/test_ext_storage.py | 107 - ovznovadriver/tests/openvz/test_file.py | 126 - ovznovadriver/tests/openvz/test_network.py | 220 -- ovznovadriver/tests/openvz/test_utils.py | 302 --- setup.py | 33 - 48 files changed, 7 insertions(+), 9668 deletions(-) delete mode 100644 .gitignore delete mode 100644 .gitreview delete mode 100644 README.md create mode 100644 README.rst delete mode 100644 debian/changelog delete mode 100644 debian/compat delete mode 100644 debian/control delete mode 100644 debian/copyright delete mode 100755 debian/rules delete mode 100644 debian/source/format delete mode 100644 etc/nova/rootwrap.d/openvz.filters delete mode 100644 ovznovadriver/__init__.py delete mode 100644 ovznovadriver/localization.py delete mode 100644 ovznovadriver/openvz/__init__.py delete mode 100644 ovznovadriver/openvz/container.py delete mode 100644 ovznovadriver/openvz/driver.py delete mode 100644 ovznovadriver/openvz/file.py delete mode 100644 ovznovadriver/openvz/file_ext/__init__.py delete mode 100644 ovznovadriver/openvz/file_ext/boot.py delete mode 100644 ovznovadriver/openvz/file_ext/ext_storage.py delete mode 100644 ovznovadriver/openvz/file_ext/shutdown.py delete mode 100644 ovznovadriver/openvz/file_ext/start.py delete mode 100644 ovznovadriver/openvz/file_ext/stop.py delete mode 100644 ovznovadriver/openvz/migration.py delete mode 100644 ovznovadriver/openvz/migration_drivers/__init__.py delete mode 100644 ovznovadriver/openvz/migration_drivers/rsync.py delete mode 100644 ovznovadriver/openvz/migration_drivers/transport.py delete mode 100644 ovznovadriver/openvz/network.py delete mode 100644 ovznovadriver/openvz/network_drivers/__init__.py delete mode 100644 ovznovadriver/openvz/network_drivers/network_bridge.py delete mode 100644 ovznovadriver/openvz/network_drivers/tc.py delete mode 100644 ovznovadriver/openvz/network_drivers/templates/tc_container_start.template delete mode 100644 ovznovadriver/openvz/network_drivers/templates/tc_container_stop.template delete mode 100644 ovznovadriver/openvz/network_drivers/templates/tc_host_start.template delete mode 100644 ovznovadriver/openvz/network_drivers/templates/tc_host_stop.template delete mode 100644 ovznovadriver/openvz/resources.py delete mode 100644 ovznovadriver/openvz/utils.py delete mode 100644 ovznovadriver/openvz/volume.py delete mode 100644 ovznovadriver/openvz/volume_drivers/__init__.py delete mode 100644 ovznovadriver/openvz/volume_drivers/iscsi.py delete mode 100644 ovznovadriver/tests/openvz/__init__.py delete mode 100644 ovznovadriver/tests/openvz/fakes.py delete mode 100644 ovznovadriver/tests/openvz/test_driver.py delete mode 100644 ovznovadriver/tests/openvz/test_ext_storage.py delete mode 100644 ovznovadriver/tests/openvz/test_file.py delete mode 100644 ovznovadriver/tests/openvz/test_network.py delete mode 100644 ovznovadriver/tests/openvz/test_utils.py delete mode 100644 setup.py diff --git a/.gitignore b/.gitignore deleted file mode 100644 index 61ec8e4..0000000 --- a/.gitignore +++ /dev/null @@ -1,38 +0,0 @@ -*.py[cod] - -# C extensions -*.so - -# Packages -*.egg -*.egg-info -dist -build -eggs -parts -bin -var -sdist -develop-eggs -.installed.cfg -lib -lib64 - -# Installer logs -pip-log.txt - -# Unit test / coverage reports -.coverage -.tox -nosetests.xml - -# Translations -*.mo - -# Mr Developer -.mr.developer.cfg -.project -.pydevproject - -# Pycharm -.idea diff --git a/.gitreview b/.gitreview deleted file mode 100644 index 3992dd9..0000000 --- a/.gitreview +++ /dev/null @@ -1,4 +0,0 @@ -[gerrit] -host=review.openstack.org -port=29418 -project=stackforge/openvz-nova-driver.git diff --git a/README.md b/README.md deleted file mode 100644 index 0891332..0000000 --- a/README.md +++ /dev/null @@ -1,11 +0,0 @@ -openvz-nova-driver -================== - -Virt driver that allows openstack nova to control openvz containers. - -Once installed simply set these flags in the nova.conf file: - - -compute_driver=openvz - - diff --git a/README.rst b/README.rst new file mode 100644 index 0000000..9006052 --- /dev/null +++ b/README.rst @@ -0,0 +1,7 @@ +This project is no longer maintained. + +The contents of this repository are still available in the Git source code +management system. To see the contents of this repository before it reached +its end of life, please check out the previous commit with +"git checkout HEAD^1". + diff --git a/debian/changelog b/debian/changelog deleted file mode 100644 index 3d65cf1..0000000 --- a/debian/changelog +++ /dev/null @@ -1,15 +0,0 @@ -openvz-nova-driver (1.3-01) precise; urgency=low - - * Added setting numtcpsock to instance sizing - - -- Daniel Salinas Wed, 26 June 2013 16:08:03 -0500 - - -openvz-nova-driver (1.1-02) precise; urgency=low - - * Released for known working distributions. (Closes: #XXXXXX) - * Releasing as noarch - * Released Migrations - * Fixed broken copyright headers - - -- Daniel Salinas Mon, 07 May 2013 15:51:03 -0500 diff --git a/debian/compat b/debian/compat deleted file mode 100644 index 45a4fb7..0000000 --- a/debian/compat +++ /dev/null @@ -1 +0,0 @@ -8 diff --git a/debian/control b/debian/control deleted file mode 100644 index 5ab44a6..0000000 --- a/debian/control +++ /dev/null @@ -1,15 +0,0 @@ -Source: openvz-nova-driver -Maintainer: Daniel Salinas -Section: python -Priority: optional -Build-Depends: debhelper (>= 7.4.3), python-support (>= 0.8.4) -Standards-Version: 3.9.3 - -Package: openvz-nova-driver -Architecture: all -Depends: ${misc:Depends}, - ${python:Depends}, - python-nova, nova-compute -XB-Python-Version: ${python:Versions} -Provides: ${python:Provides} -Description: Nova virt driver for OpenVz \ No newline at end of file diff --git a/debian/copyright b/debian/copyright deleted file mode 100644 index e69de29..0000000 diff --git a/debian/rules b/debian/rules deleted file mode 100755 index 7992b3b..0000000 --- a/debian/rules +++ /dev/null @@ -1,38 +0,0 @@ -#! /usr/bin/make -f - -SHELL = /bin/bash - -# all versions -PYVERS := $(shell pyversions -vs) -VER := $(shell /usr/bin/python -c 'import sys; print sys.version[:3]') - -clean: - : # rm -rf *-stamp build-python* build - : # rm -rf $(addprefix debian/,$(packages)) debian/files debian/substvars - : # rm -rf _trial_temp test.log - : # find . -name "*.pyc" |xargs -r rm - dh_clean - -binary-arch: binary-indep - -binary-indep: - dh_installdirs /usr/lib/python$(PYVERS)/dist-packages/ovznovadriver /usr/lib/python$(PYVERS)/dist-packages/nova/tests /etc/nova/rootwrap.d - cp -R $(CURDIR)/ovznovadriver/openvz $(CURDIR)/debian/openvz-nova-driver/usr/lib/python$(PYVERS)/dist-packages/ovznovadriver - cp -R $(CURDIR)/ovznovadriver/tests/openvz $(CURDIR)/debian/openvz-nova-driver/usr/lib/python$(PYVERS)/dist-packages/nova/tests - install -d -m 755 $(CURDIR)/debian/openvz-nova-driver/usr/lib/python$(PYVERS)/dist-packages/ovznovadriver - install -d -m 755 $(CURDIR)/debian/openvz-nova-driver/usr/lib/python$(PYVERS)/dist-packages/nova/tests - install -D -m 0400 $(CURDIR)/etc/nova/rootwrap.d/openvz.filters $(CURDIR)/debian/openvz-nova-driver/etc/nova/rootwrap.d/ - dh_testdir - dh_testroot - dh_installchangelogs -i - dh_installdocs -i -A README.md - dh_installmenu -i - dh_compress -i -X.py - dh_fixperms -i - dh_installdeb -i - dh_gencontrol -i - dh_md5sums -i - dh_builddeb -i - -binary: binary-indep -.PHONY: build clean binary-indep binary diff --git a/debian/source/format b/debian/source/format deleted file mode 100644 index d3827e7..0000000 --- a/debian/source/format +++ /dev/null @@ -1 +0,0 @@ -1.0 diff --git a/etc/nova/rootwrap.d/openvz.filters b/etc/nova/rootwrap.d/openvz.filters deleted file mode 100644 index d6aea44..0000000 --- a/etc/nova/rootwrap.d/openvz.filters +++ /dev/null @@ -1,85 +0,0 @@ -# nova-rootwrap command filters for openvz nodes -# This file should be owned by (and only-writeable by) the root user - -[Filters] -# ovznovadriver/openvz/utils.py: 'mount', '-o', 'defaults' ... -mount: CommandFilter, /bin/mount, root - -# ovznovadriver/openvz/utils.py: 'umount' -umount: CommandFilter, /bin/umount, root - -# ovznovadriver/openvz/utils.py: 'mkdir', path -mkdir: CommandFilter, /bin/mkdir, root - -# ovznovadriver/openvz/utils.py: 'chown', owner_uid, path -chown: CommandFilter, /bin/chown, root - -# ovznovadriver/openvz/utils.py: 'chmod' -chmod: CommandFilter, /bin/chmod, root - -# ovznovadriver/openvz/volume_drivers/iscsi.py: 'iscsiadm', '-m', ... -iscsiadm: CommandFilter, iscsiadm, root - -# ovznovadriver/openvz/volume.py: fdisk %(dev_path)s -fdisk: CommandFilter, /sbin/fdisk, root - -# ovznovadriver/openvz/driver.py: 'arping', '-U', floating_ip, '-A', '-I', ... -arping: CommandFilter, arping, root - -# ovznovadriver/openvz/file.py: 'touch', target -touch: CommandFilter, /usr/bin/touch, root - -# Rackspace Openvz starts here -# nova/compute/manager.py: 'blockdev', '--getsize64', host_device -blockdev: CommandFilter, /sbin/blockdev, root - -# ovznovadriver/openvz/driver.py: '/usr/sbin/vzlist' -vzlist: CommandFilter, /usr/sbin/vzlist, root - -# ovznovadriver/openvz/driver.py: '/usr/sbin/vzctl' -vzctl: CommandFilter, /usr/sbin/vzctl, root - -# ovznovadriver/openvz/driver.py: '/bin/rm' -rm: CommandFilter, /bin/rm, root - -# ovznovadriver/openvz/driver.py: -cpuinfo: ReadFileFilter, /proc/cpuinfo - -# ovznovadriver/openvz/driver.py: -meminfo: ReadFileFilter, /proc/meminfo - -# ovznovadriver/openvz/driver.py: '/usr/sbin/vzcpucheck' -vzcpucheck: CommandFilter, /usr/sbin/vzcpucheck, root - -# ovznovadriver/openvz/driver.py: '/bin/rmdir' -rmdir: CommandFilter, /bin/rmdir, root - -# ovznovadriver/openvz/volume_drivers/iscsi.py: '/usr/bin/iscsiadm' -iscsiadm_usrsbin: CommandFilter, /usr/bin/iscsiadm, root - -# ovznovadriver/openvz/utils.py: '/sbin/blkid' -blkid: CommandFilter, /sbin/blkid, root - -# ovznovadriver/openvz/network_plugins/tc.py -tc: CommandFilter, /sbin/tc, root - -# ovznovadriver/openvz/volume.py -ls: CommandFilter, /bin/ls, root - -# ovznovadriver/openvz/volume.py -sfdisk: CommandFilter, /sbin/sfdisk, root - -# ovznovadriver/openvz/volume.py -mknod: CommandFilter, /bin/mknod, root - -# ovznovadriver/openvz/driver.py -vzmigrate: CommandFilter, /usr/sbin/vzmigrate, root - -# ovznovadriver/openvz/migrate.py -cp: CommandFilter, /bin/cp, root - -# ovznovadriver/openvz/utils.py -tar: CommandFilter, /bin/tar, root - -# ovznovadriver/openvz/migration_drivers/rsync.py -rsync: CommandFilter, /usr/bin/rsync, root diff --git a/ovznovadriver/__init__.py b/ovznovadriver/__init__.py deleted file mode 100644 index 88eeaef..0000000 --- a/ovznovadriver/__init__.py +++ /dev/null @@ -1,12 +0,0 @@ -""" -OpenVZ Nova Driver ------------------- - -This is included in this oddly named directory instead of "nova/virt" since in -the later case it wouldn't be possible to have a setup.py and thus develop on -it at the same time without shadowing the real nova package. - -If you don't like that, complain to the Nova core team so they accept this -driver into the actual Nova codebase, or go write a ton of code for libvirt. -""" - diff --git a/ovznovadriver/localization.py b/ovznovadriver/localization.py deleted file mode 100644 index 4bd5b47..0000000 --- a/ovznovadriver/localization.py +++ /dev/null @@ -1,3 +0,0 @@ -#TODO(tim.simpson): Figure out some way to link this to Nova's localization -# function. -_ = str diff --git a/ovznovadriver/openvz/__init__.py b/ovznovadriver/openvz/__init__.py deleted file mode 100644 index 02ca0d1..0000000 --- a/ovznovadriver/openvz/__init__.py +++ /dev/null @@ -1,20 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -from ovznovadriver.openvz import driver - -OpenVzDriver = driver.OpenVzDriver diff --git a/ovznovadriver/openvz/container.py b/ovznovadriver/openvz/container.py deleted file mode 100644 index 33db4aa..0000000 --- a/ovznovadriver/openvz/container.py +++ /dev/null @@ -1,606 +0,0 @@ -# Copyright 2014 Rackspace -# All Rights Reserved. -# -# 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. - -import itertools -import json -import os - -from nova import exception -from nova.openstack.common import lockutils -from nova.openstack.common import log as logging -from oslo.config import cfg -from ovznovadriver.localization import _ -from ovznovadriver.openvz import utils as ovz_utils - -CONF = cfg.CONF - -LOG = logging.getLogger(__name__) - -# More of the openvz logic belongs in here, but it was hard to de-tangle it -# from all the libraries, so a minimal subset to get the desired outcome -# was ported with the hope that future commits will further improve upon it - -def _is_int(value): - - try: - int(value) - return True - except ValueError: - return False - - -class OvzContainer(object): - """ - A class for objects that represent OpenVZ containers. - - All methods for interacting with OpenVZ containers spawn from here. - """ - - def __init__(self, ovz_id, nova_id=None, name=None, uuid=None, - host=None, state=None): - self.ovz_data = { - 'ovz_id': ovz_id, - 'nova_id': nova_id, - 'name': name, - 'uuid': uuid, - 'host': host, - } - if state is not None: - self.ovz_data['state'] = state - - @property - def ovz_id(self): - return self.ovz_data['ovz_id'] - - @property - def nova_id(self): - return self.ovz_data['nova_id'] - - @property - def name(self): - return self.ovz_data['name'] - - @property - def uuid(self): - return self.ovz_data['uuid'] - - @property - def host(self): - return self.ovz_data['host'] - - @property - def state(self): - if 'state' in self.ovz_data: - return self.ovz_data['state'] - - self._load_state() - return self.ovz_data['state'] - - @classmethod - def create(cls, image, **kwargs): - """ - Create an OpenVZ container with the specified arguments. - """ - - # TODO(imsplitbit): This needs to set an os template for the image - # as well as an actual OS template for OpenVZ to know what config - # scripts to use. This can be problematic because there is no concept - # of OS name, it is arbitrary so we will need to find a way to - # correlate this to what type of disto the image actually is because - # this is the clue for openvz's utility scripts. For now we will have - # to set it to 'ubuntu' - - - container = OvzContainer(ovz_id=cls.get_next_id(), **kwargs) - - create_cmd = ['vzctl', 'create', container.ovz_id, '--ostemplate', - image] - - if CONF.ovz_layout: - create_cmd.append('--layout') - create_cmd.append(CONF.ovz_layout) - - ovz_utils.execute(*create_cmd, run_as_root=True) - container.save_ovz_metadata() - return container - - @classmethod - @lockutils.synchronized('OVZ_DRIVER_GET_NEXT_ID') - def get_next_id(cls): - """ - Gets the next available local openvz id. - """ - # openvz reserves ids 0-100, so start at 101 - # We wish to know all vz directories that currently exist - # since a container that has been deleted could have not - # been completely cleaned up - ovz_id = str(max(OvzContainers.ctid_in_use()) + 1) - - # Create a lock dir to workaround a concurrency issue where multiple - # create calls can get the same next_id. - lock_dir = os.path.join(CONF.ovz_lock_dir, ovz_id) - ovz_utils.execute('mkdir', '-p', lock_dir, run_as_root=True) - return ovz_id - - def save_ovz_metadata(self): - """ - Save information important to associate nova information with this - instance. - """ - description = json.dumps({ - 'host': CONF.host, - 'name': self.name, - 'nova_id': str(self.nova_id), - 'uuid': self.uuid, - }) - - # setting the name to the uuid lets you use the uuid with vzctl - ovz_utils.execute( - 'vzctl', 'set', self.ovz_id, '--save', '--name', self.uuid, - '--description', description, run_as_root=True) - - def _load_state(self): - """ - Load the current state data from OpenVZ. - """ - out = ovz_utils.execute('vzlist', '--no-header', '--all', - '--output', 'status', self.ovz_id, - raise_on_error=False, run_as_root=True) - if not out: - raise exception.InstanceNotFound( - _('Instance %s doesnt exist') % self.ovz_id) - - out = out.split() - self.ovz_data.state = out[0] - - @classmethod - def find(cls, ovz_id=None, name=None, nova_id=None, uuid=None): - """ - Find a specific OpenVZ container by name, ovz_id (ctid), - nova_id (instance id), or uuid. - """ - - if (ovz_id): - return cls._find(ovz_id) - - if (name): - name_wildcard = '*"name": "' + name + '"*' - return cls._find('--description', name_wildcard) - - if (uuid): - uuid_wildcard = '*"uuid": "' + uuid + '"*' - return cls._find('--description', uuid_wildcard) - - if (nova_id): - nova_id_wildcard = '*"nova_id": "' + str(nova_id) + '"*' - return cls._find('--description', nova_id_wildcard) - - @classmethod - def _find(cls, *params): - vzlist_cmd = ['vzlist', '--no-header', '--all', - '--output', 'ctid,status,description'] - vzlist_cmd.extend(params) - out = ovz_utils.execute(*vzlist_cmd, raise_on_error=False, - run_as_root=True) - - # for testing, we allow multiple nova hosts per node. We don't want - # to load containers for the other hosts, so pretend they don't exist - found = None - if out is not None: - lines = out.splitlines() - for line in lines: - possible = cls._load_from_vzlist(line) - if CONF.host == possible.host: - found = possible - break - - if found is None: - raise exception.InstanceNotFound( - _('Instance %s does not exist') % str(params)) - - LOG.debug(_('Loading container from vzlist %(params)s: %(ovz_data)s') % - {'params': params, 'ovz_data': found.ovz_data}) - - return found - - @classmethod - def _load_from_vzlist(cls, line): - # since the JSON bits have spaces in them, limit how many splits we do - raw = line.split(None, 2) - ovz_data = {} - if raw[2] is not None and raw[2] != '-': - try: - ovz_data = json.loads(raw[2]) - except BaseException, e: - LOG.error("ERROR parsing json %s: %s" % (raw[2], e)) - ovz_data['ovz_id'] = raw[0] - ovz_data['state'] = raw[1] - return OvzContainer(**ovz_data) - - def prep_for_migration(self): - # this only really happens in development VMs, but we can't have two - # containers with the same name, so we need to rename the old one - temp_name = '%s-migrated' % self.uuid - ovz_utils.execute( - 'vzctl', 'set', self.ovz_id, '--save', '--name', temp_name, - run_as_root=True) - - def delete(self): - """ - Remove the OpenVZ container this object represents. - """ - ovz_utils.execute('vzctl', 'destroy', self.ovz_id, run_as_root=True) - - # Clean up the folders if they get left behind. - root_dir = os.path.join(CONF.ovz_ve_root_dir, self.ovz_id) - private_dir = os.path.join(CONF.ovz_ve_private_dir, self.ovz_id) - lock_dir = os.path.join(CONF.ovz_lock_dir, self.ovz_id) - confs = ( - os.path.join(CONF.ovz_ve_conf_dir, f) - for f in os.listdir(CONF.ovz_ve_conf_dir) - if f.startswith(self.ovz_id + '.') - ) - for pth in itertools.chain((root_dir, private_dir, lock_dir), confs): - ovz_utils.execute('rm', '-rf', pth, run_as_root=True) - - def apply_config(self, config): - """ - This adds the container root into the vz meta data so that - OpenVz acknowledges it as a container. Punting to a basic - config for now. - - Run the command: - - vzctl set --save --applyconfig - - This sets the default configuration file for openvz containers. This - is a requisite step in making a container from an image tarball. - - If this fails to run successfully an exception is raised because the - container this executes against requires a base config to start. - """ - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--applyconfig', config, run_as_root=True) - - def set_vz_os_hint(self, ostemplate='ubuntu'): - """ - This exists as a stopgap because currently there are no os hints - in the image managment of nova. There are ways of hacking it in - via image_properties but this requires special case code just for - this driver. - - Run the command: - - vzctl set --save --ostemplate - - Currently ostemplate defaults to ubuntu. This facilitates setting - the ostemplate setting in OpenVZ to allow the OpenVz helper scripts - to setup networking, nameserver and hostnames. Because of this, the - openvz driver only works with debian based distros. - - If this fails to run an exception is raised as this is a critical piece - in making openvz run a container. - """ - - # This sets the distro hint for OpenVZ to later use for the setting - # of resolver, hostname and the like - - # TODO(imsplitbit): change the ostemplate default value to a flag - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--ostemplate', ostemplate, run_as_root=True) - - def set_numflock(self, max_file_descriptors): - """ - Run the command: - - vzctl set --save --numflock - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--numflock', max_file_descriptors, - run_as_root=True) - - def set_numfiles(self, max_file_descriptors): - """ - Run the command: - - vzctl set --save --numfile - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--numfile', max_file_descriptors, - run_as_root=True) - - # TODO(jcru) looks like this method is not being used anywhere, delete? - # TODO(jcru) extract calculations from here and only pass tcp_sockets to - # function. - def set_numtcpsock(self, memory_mb): - """ - Run the commnand: - - vzctl set --save --numtcpsock - - :param instance: - :return: - """ - try: - tcp_sockets = CONF.ovz_numtcpsock_map[str(memory_mb)] - except (ValueError, TypeError, KeyError, cfg.NoSuchOptError): - LOG.error(_('There was no acceptable tcpsocket number found ' - 'defaulting to %s') % CONF.ovz_numtcpsock_default) - tcp_sockets = CONF.ovz_numtcpsock_default - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--numtcpsock', tcp_sockets, run_as_root=True) - - def set_vmguarpages(self, num_pages): - """ - Set the vmguarpages attribute for a container. This number represents - the number of 4k blocks of memory that are guaranteed to the container. - This is what shows up when you run the command 'free' in the container. - - Run the command: - - vzctl set --save --vmguarpages - - If this fails to run then an exception is raised because this affects - the memory allocation for the container. - """ - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--vmguarpages', num_pages, run_as_root=True) - - def set_privvmpages(self, num_pages): - """ - Set the privvmpages attribute for a container. This represents the - memory allocation limit. Think of this as a bursting limit. For now - We are setting to the same as vmguarpages but in the future this can be - used to thin provision a box. - - Run the command: - - vzctl set --save --privvmpages - - If this fails to run an exception is raised as this is essential for - the running container to operate properly within it's memory - constraints. - """ - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--privvmpages', num_pages, run_as_root=True) - - def set_kmemsize(self, kmem_barrier, kmem_limit): - """ - Set the kmemsize attribute for a container. This represents the - amount of the container's memory allocation that will be made - available to the kernel. This is used for tcp connections, unix - sockets and the like. - - This runs the command: - - vzctl set --save --kmemsize : - - If this fails to run an exception is raised as this is essential for - the container to operate under a normal load. Defaults for this - setting are completely inadequate for any normal workload. - """ - kmemsize = '%d:%d' % (kmem_barrier, kmem_limit) - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--kmemsize', kmemsize, run_as_root=True) - - def set_cpuunits(self, units): - """ - Set the cpuunits setting for the container. This is an integer - representing the number of cpu fair scheduling counters that the - container has access to during one complete cycle. - - Run the command: - - vzctl set --save --cpuunits - - If this fails to run an exception is raised because this is the secret - sauce to constraining each container within it's subscribed slice of - the host node. - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--cpuunits', units, run_as_root=True) - - def set_cpulimit(self, cpulimit): - """ - This is a number in % equal to the amount of cpu processing power - the container gets. NOTE: 100% is 1 logical cpu so if you have 12 - cores with hyperthreading enabled then 100% of the whole host machine - would be 2400% or --cpulimit 2400. - - Run the command: - - vzctl set --save --cpulimit - - If this fails to run an exception is raised because this is the secret - sauce to constraining each container within it's subscribed slice of - the host node. - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--cpulimit', cpulimit, run_as_root=True) - - def set_cpus(self, vcpus): - """ - The number of logical cpus that are made available to the container. - Default to showing 2 cpus to each container at a minimum. - - Run the command: - - vzctl set --save --cpus - - If this fails to run an exception is raised because this limits the - number of cores that are presented to each container and if this fails - to set *ALL* cores will be presented to every container, that be bad. - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', '--cpus', - vcpus, run_as_root=True) - - def set_ioprio(self, ioprio): - """ - Set the IO priority setting for a given container. This is represented - by an integer between 0 and 7. - Run the command: - - vzctl set --save --ioprio - - If this fails to run an exception is raised because all containers are - given the same weight by default which will cause bad performance - across all containers when there is input/output contention. - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--ioprio', ioprio, run_as_root=True) - - def set_diskspace(self, soft_limit, hard_limit): - """ - Implement OpenVz disk quotas for local disk space usage. - This method takes a soft and hard limit. This is also the amount - of diskspace that is reported by system tools such as du and df inside - the container. If no argument is given then one will be calculated - based on the values in the instance_types table within the database. - - Run the command: - - vzctl set --save --diskspace - - If this fails to run an exception is raised because this command - limits a container's ability to hijack all available disk space. - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--diskspace', '%s:%s' % (soft_limit, hard_limit), - run_as_root=True) - - def set_vswap(self, ram, swap): - """ - Implement OpenVz vswap memory management model (The other being user - beancounters). - - The sum of physpages_limit and swappages_limit limits the maximum - amount of memory which can be used by a container. When physpages limit - is reached, memory pages belonging to the container are pushed out to - so called virtual swap (vswap). The difference between normal swap and - vswap is that with vswap no actual disk I/O usually occurs. Instead, a - container is artificially slowed down, to emulate the effect of the - real swapping. Actual swap out occurs only if there is a global memory - shortage on the system. - - Run the command: - - vzctl set --ram --swap - """ - - ovz_utils.execute('vzctl', 'set', self.ovz_id, '--save', - '--ram', ram, '--swap', swap, run_as_root=True) - - -class OvzContainers(object): - - @classmethod - def _list(cls, fields, host=CONF.host): - # it's important that description is the last field so it doesn't get - # truncated. Alternatively, the --no-trim option added in openvz 3.2 - # will make the point moot, if we want to force that dependency - vzlist_cmd = ['vzlist', '--all', '--no-header', - '--output', fields] - if host is not None: - host_wildcard = '*"host": "' + host + '"*' - vzlist_cmd.extend(['--description', host_wildcard]) - out = ovz_utils.execute(*vzlist_cmd, - raise_on_error=False, run_as_root=True) - if out: - return out.splitlines() - - return list() - - @classmethod - def list(cls, host=CONF.host): - results = list() - - lines = cls._list('ctid,status,description', host=host) - for line in lines: - results.append(OvzContainer._load_from_vzlist(line)) - - return results - - @classmethod - def ctid_in_use(cls): - """Get an iterable of all CTIDs currently in use on the system.""" - - return itertools.chain( - xrange(100), # Reserved by OpenVZ. - (int(cont.ovz_id, base=10) - for cont in OvzContainers.list(host=None)), - OvzContainers.list_vz_artifacts(), - ) - - @classmethod - def _artifacts_from_dirs(cls): - """Generate container ids that have artifacts in vz directories. - - Directories in the searched directories are named with the CTID of the - container they represent. Generate a list of all CTIDs in use by - looking in these directories. This accounts for containers that are - deleted but still leave behind certain directories. - """ - - directories_to_check = ( - CONF.ovz_ve_private_dir, - CONF.ovz_ve_root_dir, - CONF.ovz_lock_dir, - ) - for dir_path in directories_to_check: - for item in os.listdir(dir_path): - item_path = os.path.join(dir_path, item) - if os.path.isdir(item_path) and _is_int(item): - yield int(item) - - @classmethod - def _artifacts_from_confs(cls): - """Generate container ids that have artifacts in the vz configs. - - Each container also comes with a series of config files. Each file is - named in the pattern .. Generate a list of CTIDs based on - the config files that are present. This accounts for containers that - were deleted but left behind their config files. - """ - for item in os.listdir(CONF.ovz_ve_conf_dir): - if '.' in item and _is_int(item.split('.')[0]): - yield int(item.split('.')[0]) - - @classmethod - def list_vz_artifacts(cls): - """Lists container ids that have artifacts within vz directories - """ - return itertools.chain( - OvzContainers._artifacts_from_dirs(), - OvzContainers._artifacts_from_confs(), - ) - - @classmethod - def get_memory_mb_used(cls, block_size=4096): - total_used_mb = 0 - lines = cls._list('ctid,privvmpages.l') - for line in lines: - line = line.split() - total_used_mb += ((int(line[1]) * block_size) / 1024 ** 2) - - return total_used_mb diff --git a/ovznovadriver/openvz/driver.py b/ovznovadriver/openvz/driver.py deleted file mode 100644 index 607a4ed..0000000 --- a/ovznovadriver/openvz/driver.py +++ /dev/null @@ -1,1810 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" -import base64 -import fnmatch -import json -from nova.compute import power_state -from nova import context -from nova import exception -from nova.network import linux_net -from nova.openstack.common import importutils -from nova.openstack.common import log as logging -from nova.openstack.common import loopingcall -from nova.virt import driver -from nova.virt import images -from ovznovadriver.localization import _ -from ovznovadriver.openvz import file as ovzfile -from ovznovadriver.openvz.container import OvzContainer -from ovznovadriver.openvz.container import OvzContainers -from ovznovadriver.openvz.file_ext import boot as ovzboot -from ovznovadriver.openvz.file_ext import ext_storage -from ovznovadriver.openvz.file_ext import shutdown as ovzshutdown -from ovznovadriver.openvz import migration as ovz_migration -from ovznovadriver.openvz import network as ovznetwork -from ovznovadriver.openvz.network_drivers import tc as ovztc -from ovznovadriver.openvz import utils as ovz_utils -from ovznovadriver.openvz.volume_drivers import iscsi as ovziscsi -from ovznovadriver.openvz.resources import VZResourceManager -import os -from oslo.config import cfg -import socket -import time - -openvz_conn_opts = [ - cfg.StrOpt('ovz_template_path', - default='/var/lib/vz/template/cache', - help='Path to use for local storage of OVz templates'), - cfg.StrOpt('ovz_ve_private_dir', - default='/var/lib/vz/private', - help='Path where VEs will get placed'), - cfg.StrOpt('ovz_ve_root_dir', - default='/var/lib/vz/root', - help='Path where the VEs root is'), - cfg.StrOpt('ovz_ve_conf_dir', - default='/etc/vz/conf', - help='Path where the VEs confs are'), - cfg.StrOpt('ovz_lock_dir', - default='/tmp/ovz_lock', - help='Path where file locks are placed.'), - cfg.StrOpt('ovz_image_template_dir', - default='/var/lib/vz/template/cache', - help='Path where OpenVZ images are'), - cfg.StrOpt('ovz_config_dir', - default='/etc/vz/conf', - help='Where the OpenVZ configs are stored'), - cfg.StrOpt('ovz_bridge_device', - default='br100', - help='Bridge device to map veth devices to'), - cfg.StrOpt('ovz_vif_driver', - default='ovznovadriver.openvz.network_drivers' - '.network_bridge.OVZNetworkBridgeDriver', - help='The openvz VIF driver to configures the VIFs'), - cfg.StrOpt('ovz_mount_options', - default='defaults', - help='Mount options for external filesystems'), - cfg.StrOpt('ovz_volume_default_fs', - default='ext3', - help='FSType to use for mounted volumes'), - cfg.StrOpt('ovz_tc_host_slave_device', - default='eth0', - help='Device to use as the root device for tc rules'), - cfg.StrOpt('ovz_tc_template_dir', - default='$pybasedir/../openvz-nova-driver/' - 'ovznovadriver/openvz/network_drivers/templates', - help='Where the tc templates are located'), - cfg.StrOpt('ovz_tmp_dir', - default='/var/tmp', - help='Directory to use as temporary storage'), - cfg.StrOpt('ovz_migration_method', - default='python', - help='Method to use for migrations'), - cfg.StrOpt('ovz_migration_user', - default='nova', - help='User to use for running migrations'), - cfg.StrOpt('ovz_migration_transport', - default='rsync', - help='Method to use to transport migrations'), - cfg.StrOpt('ovz_vzmigrate_opts', - default=None, - help='Optional arguments to pass to vzmigrate'), - cfg.BoolOpt('ovz_vzmigrate_online_migration', - default=True, - help='Perform an online migration of a container'), - cfg.BoolOpt('ovz_vzmigrate_destroy_source_container_on_migrate', - default=True, - help='If a migration is successful do we delete the ' - 'container on the old host'), - cfg.BoolOpt('ovz_vzmigrate_verbose_migration_logging', - default=True, - help='Log verbose messages from vzmigrate command'), - cfg.BoolOpt('ovz_disk_space_oversub', - default=True, - help='Allow over subscription of local disk'), - cfg.BoolOpt('ovz_use_veth_devs', - default=True, - help='Use veth devices rather than venet'), - cfg.BoolOpt('ovz_use_dhcp', - default=False, - help='Use dhcp for network configuration'), - cfg.BoolOpt('ovz_use_bind_mount', - default=False, - help='Use bind mounting instead of simfs'), - cfg.IntOpt('ovz_system_num_tries', - default=3, - help='Number of attempts to make when ' - 'running a system command'), - cfg.IntOpt('ovz_tc_id_max', - default=9999, - help='Max TC id to be used in generating a new id'), - cfg.IntOpt('ovz_tc_mbit_per_unit', - default=20, - help='Mbit per unit bandwidth limit'), - cfg.IntOpt('ovz_tc_max_line_speed', - default=1000, - help='Line speed in Mbit'), - cfg.IntOpt('ovz_rsync_iterations', - default=1, - help='Number of times to rsync a container when migrating'), - cfg.IntOpt('ovz_numtcpsock_default', - default=2000, - help='Default number of tcp sockets to give each container'), - cfg.DictOpt('ovz_numtcpsock_map', - default={"8192": 3000, "1024": 2000, "4096": 2000, - "2048": 2000, "16384": 4000, "512": 2000}, - help='Mapped values for flavors based on memory allocation'), - cfg.StrOpt('ovz_layout', - default='simfs', - help='OVZ layout options to use during create.'), -] - -CONF = cfg.CONF -CONF.register_opts(openvz_conn_opts) -CONF.import_opt('host', 'nova.config') - -LOG = logging.getLogger('ovznovadriver.openvz.driver') - - -class OpenVzDriver(driver.ComputeDriver): - - def __init__(self, virtapi, read_only=False): - """ - Create an instance of the openvz connection. - """ - super(OpenVzDriver, self).__init__(virtapi) - self.resource_manager = VZResourceManager(virtapi) - self.host_stats = dict() - self._initiator = None - self.host = None - self.read_only = read_only - self.vif_driver = importutils.import_object(CONF.ovz_vif_driver) - ovz_utils.execute('mkdir', '-p', CONF.ovz_lock_dir, run_as_root=True) - LOG.debug(_('__init__ complete in OpenVzDriver')) - - def init_host(self, host=socket.gethostname()): - """ - Initialize anything that is necessary for the driver to function, - including catching up with currently running VE's on the given host. - """ - LOG.debug(_('Hostname: %s') % host) - - if not self.host: - self.host = host - - LOG.debug(_('Determining the computing power of the host')) - self.resource_manager.get_cpulimit() - self._refresh_host_stats() - - LOG.debug(_('Flushing host TC rules if there are any')) - tc = ovztc.OVZTcRules() - sf = ovzshutdown.OVZShutdownFile(0, 700) - if sf.exists(): - with sf: - sf.read() - sf.run_contents() - - LOG.debug(_('Setting up host TC rules')) - LOG.debug(_('Making TC startup script for the host')) - bf = ovzboot.OVZBootFile(0, 700) - with bf: - # Make sure we're starting with a blank file - bf.set_contents(list()) - bf.make_proper_script() - bf.append(tc.host_start()) - bf.write() - - LOG.debug(_('Making TC shutdown script for the host')) - - # Starting fresh - with sf: - # Make sure we're starting with a blank file - sf.set_contents(list()) - sf.make_proper_script() - sf.append(tc.host_stop()) - sf.write() - - LOG.debug(_('Done setting up TC files, running TC startup')) - bf.run_contents() - - LOG.debug(_('init_host complete in OpenVzDriver')) - - def list_instances(self): - """ - Return the names of all the instances known to the container - layer, as a list. - """ - ctids = list() - containers = OvzContainers.list() - for container in containers: - ctids.append(container.ovz_id) - - return ctids - - def list_instance_uuids(self): - """ - Return the UUIDS of all the instances known to the virtualization - layer, as a list. - """ - uuids = list() - containers = OvzContainers.list() - for container in containers: - if container.uuid is not None: - uuids.append(container.uuid) - - return uuids - - def get_host_stats(self, refresh=False): - """ - Gather host usage stats and return their values for scheduler - accuracy - """ - if refresh: - self._refresh_host_stats() - - return self.host_stats - - def _refresh_host_stats(self): - """ - Abstraction for updating host stats - """ - host_stats = dict() - host_stats['vcpus'] = ovz_utils.get_vcpu_total() - host_stats['vcpus_used'] = ovz_utils.get_vcpu_used() - host_stats['cpu_info'] = json.dumps(ovz_utils.get_cpuinfo()) - host_stats['memory_mb'] = ovz_utils.get_memory_mb_total() - host_stats['memory_mb_used'] = OvzContainers.get_memory_mb_used() - host_stats['host_memory_total'] = host_stats['memory_mb'] - host_stats['host_memory_free'] = (host_stats['memory_mb'] - - host_stats['memory_mb_used']) - host_stats['disk_total'] = ovz_utils.get_local_gb_total() - host_stats['disk_used'] = ovz_utils.get_local_gb_used() - host_stats['disk_available'] = ( - host_stats['disk_total'] - host_stats['disk_used']) - host_stats['local_gb'] = host_stats['disk_total'] - host_stats['local_gb_used'] = host_stats['disk_used'] - host_stats['hypervisor_type'] = ovz_utils.get_hypervisor_type() - host_stats['hypervisor_version'] = ovz_utils.get_hypervisor_version() - host_stats['hypervisor_hostname'] = self.host - self.host_stats = host_stats.copy() - - def spawn(self, context, instance, image_meta, injected_files, - admin_password, network_info=None, block_device_info=None): - """ - Create a new virtual environment on the container platform. - - The given parameter is an instance of nova.compute.service.Instance. - This function should use the data there to guide the creation of - the new instance. - - The work will be done asynchronously. This function returns a - task that allows the caller to detect when it is complete. - - Once this successfully completes, the instance should be - running (power_state.RUNNING). - - If this fails, any partial instance should be completely - cleaned up, and the container platform should be in the state - that it was before this call began. - """ - - # Update state to inform the nova stack that the VE is launching - self.virtapi.instance_update( - context, instance['uuid'], {'power_state': power_state.BUILDING}) - LOG.debug(_('instance %s: is building') % instance['name']) - - # Get current usages and resource availablity. - self.resource_manager.get_cpuunits_usage() - - # Go through the steps of creating a container - # TODO(imsplitbit): Need to add conditionals around this stuff to make - # it more durable during failure. And roll back changes made leading - # up to the error. - self._cache_image(context, instance) - container = OvzContainer.create( - image=instance['image_ref'], - uuid=instance['uuid'], - name=instance['name'], - nova_id=instance['id'], - ) - - # TODO(jcru) change ostemplate='ubuntu' to config - container.set_vz_os_hint(ostemplate='ubuntu') - # A config file may be applied here but it may be - # config parameters may be overwritten afterwards - self.resource_manager.apply_config(context, container, - instance['instance_type_id']) - - # instance.system_metadata will be saved by nova.compute.manager - # after this method returns (driver.spawn) - # ovz_utils.save_instance_metadata does not work because when this - # method returns nova.compute.manager calls instance.save and any - # info that was not updated through instance will be reverted - instance.system_metadata['ovz_id'] = container.ovz_id - - # TODO(imsplitbit): There's probably a better way to do this - has_networking = False - try: - for vif in network_info: - if vif.labeled_ips(): - has_networking = True - except ValueError: - has_networking = False - if has_networking: - self.plug_vifs(instance, network_info) - self._setup_networking(container, network_info) - - # TODO(jimbobhickville) - move this stuff to OvzContainer - self._set_hostname(container, hostname=instance['hostname']) - self.resource_manager.configure_container_resources(context, container, - instance['instance_type_id']) - self._set_onboot(container) - - if block_device_info: - self._attach_volumes( - instance, block_device_info) - - if injected_files: - self._inject_files(instance, injected_files) - - self._start(instance) - self._gratuitous_arp_all_addresses(instance, network_info) - - if admin_password: - self.set_admin_password(context, instance['id'], - admin_password) - - # Begin making our looping async call - timer = loopingcall.FixedIntervalLoopingCall() - - # I stole this from the libvirt driver but it is appropriate to - # have this looping timer call so that if a VE doesn't start right - # away we can defer all of this. - def _wait_for_boot(): - try: - state = self.get_info(instance)['state'] - if state == power_state.RUNNING: - LOG.debug(_('instance %s: booted') % instance['name']) - timer.stop() - - except Exception: - LOG.error(_('instance %s: failed to boot') % instance['name']) - timer.stop() - - timer.stop() - - timer.f = _wait_for_boot - return timer.start(interval=0.5) - - - - def _cache_image(self, context, instance): - """ - Create the disk image for the virtual environment. This uses the - image library to pull the image down the distro image into the openvz - template cache. This is the method that openvz wants to operate - properly. - """ - - image_name = '%s.tar.gz' % instance['image_ref'] - full_image_path = '%s/%s' % (CONF.ovz_image_template_dir, image_name) - - if not os.path.exists(full_image_path): - # Grab image and place it in the image cache - images.fetch(context, instance['image_ref'], full_image_path, - instance['user_id'], instance['project_id']) - return True - else: - return False - - def _set_onboot(self, container): - """ - Method to set the onboot status of the instance. This is done - so that openvz does not handle booting, and instead the compute - manager can handle initialization. - - I run the command: - - vzctl set --onboot no --save - - If I fail to run an exception is raised. - """ - ovz_utils.execute('vzctl', 'set', container.ovz_id, '--onboot', 'no', - '--save', run_as_root=True) - - def _start(self, instance): - """ - Method to start the instance, I don't believe there is a nova-ism - for starting so I am wrapping it under the private namespace and - will call it from expected methods. i.e. resume - - Run the command: - - vzctl start - - If this fails to run an exception is raised. I don't think it needs - to be explained why. - """ - # Attempt to start the VE. - # NOTE: The VE will throw a warning that the hostname is invalid - # if it isn't valid. This is logged in LOG.error and is not - # an indication of failure. - container = OvzContainer.find(uuid=instance['uuid']) - ovz_utils.execute('vzctl', 'start', container.ovz_id, run_as_root=True) - - # Set instance state as RUNNING - self.virtapi.instance_update( - context.get_admin_context(), instance['uuid'], - {'power_state': power_state.RUNNING}) - - bf = ovzboot.OVZBootFile(container.ovz_id, 700) - with bf: - bf.read() - bf.run_contents() - - def _stop(self, instance): - """ - Method to stop the instance. This doesn't seem to be a nova-ism but - it is for openvz so I am wrapping it under the private namespace and - will call it from expected methods. i.e. pause - - Run the command: - - vzctl stop - - If this fails to run an exception is raised for obvious reasons. - """ - container = OvzContainer.find(uuid=instance['uuid']) - sf = ovzshutdown.OVZShutdownFile(container.ovz_id, 700) - with sf: - sf.read() - sf.run_contents() - - ovz_utils.execute('vzctl', 'stop', container.ovz_id, run_as_root=True) - - # Update instance state - self.virtapi.instance_update( - context.get_admin_context(), instance['uuid'], - {'power_state': power_state.SHUTDOWN}) - - def _set_hostname(self, container, hostname): - """ - Set the hostname of a given container. The option to pass - a hostname to the method was added with the intention to allow the - flexibility to override the hostname listed in the instance ref. A - good person wouldn't do this but it was needed for some testing and - therefore remains for future use. - - Run the command: - - vzctl set --save --hostname - - If this fails to execute an exception is raised because the hostname is - used in most cases for connecting to the guest. While having the - hostname not match the dns name is not a complete problem it can lead - name mismatches. One could argue that this should be a softer error - and I might have a hard time arguing with that one. - """ - ovz_utils.execute('vzctl', 'set', container.ovz_id, '--save', - '--hostname', hostname, run_as_root=True) - - def _gratuitous_arp_all_addresses(self, instance, network_info): - """ - Iterate through all addresses assigned to the container and send - a gratuitous arp over it's interface to make sure arp caches have - the proper mac address. - """ - # TODO(imsplitbit): send id, iface, container mac, container ip and - # gateway to _send_garp - iface_counter = -1 - for vif in network_info: - network = vif['network'] - v4_subnets = [] - for subnet in network['subnets']: - if subnet['version'] == 4: - v4_subnets.append(subnet) - iface_counter += 1 - vz_iface = "eth%d" % iface_counter - LOG.debug(_('VZ interface: %s') % vz_iface) - LOG.debug(_('bridge interface: %s') % - network.get_meta('bridge_interface')) - LOG.debug(_('bridge: %s') % network['bridge']) - LOG.debug(_('address block: %s') % v4_subnets[0]['cidr']) - LOG.debug(_('network label: %s') % network['label']) - for v4_subnet in v4_subnets: - for ip in v4_subnet['ips']: - LOG.debug(_('Address: %s') % ip['address']) - LOG.debug( - _('Running _send_garp(%(id)s %(ip)s %(vz_iface)s)') % - {'id': instance['id'], 'ip': ip['address'], - 'vz_iface': vz_iface}) - self._send_garp(instance['id'], ip['address'], vz_iface) - - def _send_garp(self, instance_id, ip_address, interface): - """ - It is possible in nova to have a recently released ip address given - to a new container. We need to send a gratuitous arp on each - interface for the address assigned. - - The command looks like this: - - arping -q -c 5 -A -I eth0 10.0.2.4 - - If this fails to execute no exception is raised because even if the - gratuitous arp fails the container will most likely be available as - soon as the switching/routing infrastructure's arp cache clears. - """ - container = OvzContainer.find(nova_id=instance_id) - ovz_utils.execute('vzctl', 'exec2', container.ovz_id, 'arping', '-q', - '-c', '5', '-A', '-I', interface, ip_address, - run_as_root=True, raise_on_error=False) - - def _access_control(self, instance, host, mask=32, port=None, - protocol='tcp', access_type='allow'): - """ - Does what it says. Use this to interface with the - linux_net.iptables_manager to allow/deny access to a host - or network - """ - - if access_type == 'allow': - access_type = 'ACCEPT' - elif access_type == 'deny': - access_type = 'REJECT' - else: - LOG.error(_('Invalid access_type: %s') % access_type) - raise exception.InvalidInput( - _('Invalid access_type: %s') % access_type) - - if port is None: - port = '' - else: - port = '--dport %s' % port - - # Create our table instance - tables = [ - linux_net.iptables_manager.ipv4['filter'], - linux_net.iptables_manager.ipv6['filter'] - ] - - rule = '-s %s/%s -p %s %s -j %s' %\ - (host, mask, protocol, port, access_type) - - for table in tables: - table.add_rule(str(instance['id']), rule) - - # Apply the rules - linux_net.iptables_manager.apply() - - def _initial_secure_host(self, instance): - """ - Lock down the host in it's default state - """ - - # TODO(tim.simpson) This hangs if the "lock_path" FLAG value refers to - # a directory which can't be locked. It'd be nice - # if we could somehow detect that and raise an error - # instead. - - # Create our table instance and add our chains for the instance - table_ipv4 = linux_net.iptables_manager.ipv4['filter'] - table_ipv6 = linux_net.iptables_manager.ipv6['filter'] - table_ipv4.add_chain(str(instance['id'])) - table_ipv6.add_chain(str(instance['id'])) - - # As of right now there is no API call to manage security - # so there are no rules applied, this really is just a pass. - # The thought here is to allow us to pass a list of ports - # that should be globally open and lock down the rest but - # cannot implement this until the API passes a security - # context object down to us. - - # Apply the rules - linux_net.iptables_manager.apply() - - def resume_state_on_host_boot(self, context, instance, network_info, - block_device_info=None): - """resume guest state when a host is booted.""" - if block_device_info: - self._attach_volumes(instance, block_device_info) - self._start(instance) - - def _setup_networking(self, container, network_info): - """ - Create the vifs for the container's virtual networking. This should - only need to be run on instance spawn. - - :param instance: - :param network_info: - :return: - """ - LOG.debug(_('network_info: %s') % network_info) - interfaces = ovz_utils.generate_network_dict(container, - network_info) - ifaces_fh = ovznetwork.OVZNetworkInterfaces(container, interfaces, - network_info) - ifaces_fh.add() - - def plug_vifs(self, instance, network_info): - """ - Plug vifs into networks and configure network devices in the - container. This is necessary to make multi-nic go. - """ - for vif in network_info: - if vif.labeled_ips(): - self.vif_driver.plug(instance, vif) - - # TODO(pdmars): get_blockdev and rescan_volume are added to expose this - # information to nova-compute for online volume extending. They are - # required because after Cinder extends the volume, it needs nova-compute - # to run rescan on the compute host and then it needs to query the size - # of the block device until it reports the new size. Currently, the - # extensions to Cinder and Nova for online extending are in progress and - # haven't been merged into the public yet. - def get_blockdev(self, instance, connection_info): - volume = ovziscsi.OVZISCSIStorageDriver(instance['id'], - None, - connection_info) - device_name = volume.device_name() - return volume.get_blockdev(device_name) - - def rescan_volume(self, instance, connection_info): - volume = ovziscsi.OVZISCSIStorageDriver(instance['id'], - None, - connection_info) - volume.rescan() - - def reboot(self, context, instance, network_info, reboot_type, - block_device_info=None, bad_volumes_callback=None): - """Reboot the specified instance. - - After this is called successfully, the instance's state - goes back to power_state.RUNNING. The virtualization - platform should ensure that the reboot action has completed - successfully even in cases in which the underlying domain/vm - is paused or halted/stopped. - - :param instance: Instance object as returned by DB layer. - :param network_info: - :py:meth:`~nova.network.manager.NetworkManager.get_instance_nw_info` - :param reboot_type: Either a HARD or SOFT reboot - :param block_device_info: Info pertaining to attached volumes - :param bad_volumes_callback: Function to handle any bad volumes - encountered - - Run the command: - - vzctl restart - - If this fails to run an exception is raised because the container - given to this method will be in an inconsistent state. - """ - # Run the TC rules - container = OvzContainer.find(uuid=instance['uuid']) - sf = ovzshutdown.OVZShutdownFile(container.ovz_id, 700) - with sf: - sf.read() - sf.run_contents() - - # Start by setting the powerstate to paused until we have successfully - # restarted the instance. - self.virtapi.instance_update( - context, instance['uuid'], {'power_state': power_state.PAUSED}) - ovz_utils.execute('vzctl', 'restart', container.ovz_id, - run_as_root=True) - - def _wait_for_reboot(): - try: - state = self.get_info(instance)['state'] - except exception.InstanceNotFound: - self.virtapi.instance_update( - context, instance['uuid'], - {'power_state': power_state.NOSTATE}) - LOG.error(_('During reboot %s disappeared') % instance['name']) - raise loopingcall.LoopingCallDone - - if state == power_state.RUNNING: - self.virtapi.instance_update( - context, instance['uuid'], - {'power_state': power_state.RUNNING}) - LOG.info(_('Instance %s rebooted') % instance['name']) - # Run the TC rules - bf = ovzboot.OVZBootFile(container.ovz_id, 700) - with bf: - bf.read() - bf.run_contents() - raise loopingcall.LoopingCallDone - elif state == power_state.NOSTATE: - LOG.error(_('Error rebooting %s') % instance['name']) - raise loopingcall.LoopingCallDone - - timer = loopingcall.FixedIntervalLoopingCall(_wait_for_reboot) - return timer.start(interval=0.5) - - def _inject_files(self, instance, files_to_inject): - """ - Files to inject into instance. - - :param instance: instance ref of guest to receive injected files - :param files_to_inject: List of files to inject formatted as - [['filename', 'file_contents']] only strings - are accepted. - """ - LOG.debug( - _('Files to inject into %(instance_id)s: %(files_to_inject)s') % - {'instance_id': instance['id'], - 'files_to_inject': files_to_inject}) - for file_to_inject in files_to_inject: - LOG.debug(_('Injecting file: %s') % file_to_inject[0]) - self.inject_file(instance, - base64.b64encode(file_to_inject[0]), - base64.b64encode(file_to_inject[1])) - - def inject_file(self, instance, b64_path, b64_contents): - """ - Writes a file on the specified instance. - - The first parameter is an instance of nova.compute.service.Instance, - and so the instance is being specified as instance.name. The second - parameter is the base64-encoded path to which the file is to be - written on the instance; the third is the contents of the file, also - base64-encoded. - """ - container = OvzContainer.find(uuid=instance['uuid']) - path = base64.b64decode(b64_path) - LOG.debug(_('Injecting file: %s') % path) - file_path = '%s/%s/%s' % ( - CONF.ovz_ve_private_dir, container.ovz_id, path) - LOG.debug(_('New file path: %s') % file_path) - fh = ovzfile.OVZFile(file_path, 644) - with fh: - fh.append(base64.b64decode(b64_contents)) - fh.write() - - def set_admin_password(self, context, instance_id, new_pass=None): - """ - Set the root password on the specified instance. - - The first parameter is an instance of nova.compute.service.Instance, - and so the instance is being specified as instance.name. The second - parameter is the value of the new password. - - The work will be done asynchronously. This function returns a - task that allows the caller to detect when it is complete. - - Run the command: - - vzctl exec2 echo : | chpasswd - - If this fails to run an error is logged. - """ - - user_pass_map = 'root:%s' % new_pass - container = OvzContainer.find(nova_id=instance_id) - ovz_utils.execute('vzctl', 'exec2', container.ovz_id, 'echo', - user_pass_map, '|', 'chpasswd', run_as_root=True) - - def pause(self, instance): - """ - Pause the specified instance. - """ - self._stop(instance) - - def unpause(self, instance): - """ - Unpause the specified instance. - """ - self._start(instance) - - def suspend(self, instance): - """ - suspend the specified instance - """ - # grab an admin context to update the database - admin_context = context.get_admin_context() - - # Suspend the instance - ovz_utils.execute('vzctl', 'chkpnt', instance['uuid'], - '--suspend', run_as_root=True) - - # Set the instance power state to suspended for accurate reporting - try: - self.virtapi.instance_update( - admin_context, instance['uuid'], - {'power_state': power_state.SUSPENDED}) - except exception.InstanceNotFound as err: - LOG.error(_('Instance %s not found in the database') % - instance['uuid']) - LOG.error(err) - - def resume(self, instance, network_info, block_device_info=None): - """ - resume the specified instance - """ - # grab an admin context to update the database - admin_context = context.get_admin_context() - - # Resume the instance - ovz_utils.execute('vzctl', 'chkpnt', instance['uuid'], - '--resume', run_as_root=True) - - # Set the instance power state to running - try: - self.virtapi.instance_update( - admin_context, instance['uuid'], - {'power_state': power_state.RUNNING}) - except exception.InstanceNotFound as err: - LOG.error(_('Instance %s not found in the database') % - instance['uuid']) - LOG.error(err) - - def _clean_orphaned_files(self, instance_id): - """ - When openvz deletes a container it leaves behind orphaned config - files in /etc/vz/conf with the .destroyed extension. We want these - gone when we destroy a container. - - This runs a command that looks like this: - - rm -f /etc/vz/conf/.conf.destroyed - - It this fails to execute no exception is raised but an log error - event is triggered. - """ - # first assemble a list of files that need to be cleaned up, then - # do the deed. - try: - container = OvzContainer.find(nova_id=instance_id) - except exception.InstanceNotFound: - LOG.info("Instance %s cannot be deleted, since it does not exist" - % instance_id) - return - except BaseException: - raise - - for filename in os.listdir(CONF.ovz_config_dir): - if fnmatch.fnmatch(filename, '%s.*' % container.ovz_id): - # minor protection for / - if CONF.ovz_config_dir == '/': - raise exception.InvalidDevicePath( - _('I refuse to operate on /')) - - filename = '%s/%s' % (CONF.ovz_config_dir, filename) - LOG.debug(_('Deleting file: %s') % filename) - ovz_utils.execute( - 'rm', '-f', filename, run_as_root=True, - raise_on_error=False) - - def destroy(self, context, instance, network_info, block_device_info=None, - destroy_disks=True): - """ - Destroy (shutdown and delete) the specified instance. - - Run the command: - - vzctl destroy - - If this does not run successfully then an exception is raised. This is - because a failure to destroy would leave the database and container - in a disparate state. - """ - # If a revert_resize is called in the compute manager we hit a case - # where an in-flight resize on the same host deletes the instance from - # disk. Before any delete operations are allowed first check to be - # sure that there is not currently a resize happening. - # - # NOTE(imsplitbit): There is an edge case here where an in-flight - # resize is taking place and a user issues a destroy via the api - # and this will result in a bad state. We need a better solution to - # allow in place resizes. - meta = ovz_utils.read_instance_metadata(instance['id']) - migration_type = meta.get('migration_type') - - if migration_type == 'resize_in_place': - # This is a resize on the same host. The compute manager calls - # destroy on the source before calling revert_resize on the driver. - # Since there is an in-flight resize we'll exit here. - return - - # cleanup the instance metadata since this is application specific - # it's safe to just delete all of it because if it's there we put - # it there. - if ovz_utils.remove_instance_metadata(instance['id']): - LOG.debug(_('Removed metadata for instance %s') % instance['id']) - else: - LOG.debug(_('Problem removing metadata for instance %s') % - instance['id']) - - # remove all attached volumes - if block_device_info: - self._detach_volumes( - instance, block_device_info) - - timer = loopingcall.FixedIntervalLoopingCall() - - def _wait_for_destroy(): - try: - LOG.debug(_('Beginning _wait_for_destroy')) - state = self.get_info(instance)['state'] - LOG.debug(_('State is %s') % state) - - if state is power_state.RUNNING: - LOG.debug(_('Ve is running, stopping now.')) - self._stop(instance) - LOG.debug(_('Ve stopped')) - - LOG.debug(_('Attempting to destroy container')) - self._destroy(instance['id']) - except exception.InstanceUnacceptable as err: - LOG.error(_('There was an error with the destroy process')) - LOG.error(_('Error from ovz_utils: %s') % err) - timer.stop() - LOG.debug(_('Timer stopped for _wait_for_destroy')) - raise exception.InstanceTerminationFailure( - _('Error running vzctl destroy')) - except exception.InstanceNotFound: - LOG.debug(_('Container not found, destroyed?')) - timer.stop() - LOG.debug(_('Timer stopped for _wait_for_destroy')) - - LOG.debug(_('Making timer')) - timer.f = _wait_for_destroy - LOG.debug(_('Starting timer')) - - running_delete = timer.start(interval=0.5) - LOG.debug(_('Waiting for timer')) - running_delete.wait() - LOG.debug(_('Timer finished')) - - for vif in network_info: - LOG.debug('Unplugging vifs') - self.vif_driver.unplug(instance, vif) - - self._clean_orphaned_files(instance['id']) - - def _destroy(self, instance_id): - """ - Run destroy on the instance - """ - try: - container = OvzContainer.find(nova_id=instance_id) - container.delete() - except exception.InstanceNotFound: - LOG.info("Instance %s cannot be deleted, since it does not exist" - % instance_id) - return - except BaseException: - raise - - def _attach_volumes(self, instance, block_device_mapping): - """ - Iterate through all volumes and attach them all. This is just a helper - method for self.spawn so that all volumes in the db get added to a - container before it gets started. - - This will only attach volumes that have a filesystem uuid. This is - a limitation that is currently imposed by nova not storing the device - name in the volumes table so we have no point of reference for which - device goes where. - """ - for volume in block_device_mapping['block_device_mapping']: - self.attach_volume(volume['connection_info'], - instance, - volume['mount_device']) - - def attach_volume(self, connection_info, instance, mountpoint): - """ - Attach the disk at device_path to the instance at mountpoint. For - volumes being attached to OpenVz we require a filesystem be created - already. - """ - container = OvzContainer.find(uuid=instance['uuid']) - if connection_info['driver_volume_type'] == 'iscsi': - volume = ovziscsi.OVZISCSIStorageDriver( - container.ovz_id, mountpoint, connection_info) - volume.discover_volume() - else: - raise NotImplementedError( - _('There are no suitable storage drivers')) - - volume.attach() - - # Save volume info to the container's storage info store. This is - # just a precaution and stores the volume information necessary - # to manually re-establish communication should nova services - # go away. - ext_str = ext_storage.OVZExtStorage(container.ovz_id) - ext_str.add_volume(mountpoint, connection_info) - ext_str.save() - - def _disconnect_volume(self, connection_info, instance, mountpoint, - container_is_running=True): - """ - Necessary for migrations to disconnect but not permanently remove - volumes. - - :param connection_info: - :param instance: - :param mountpoint: - :return: - """ - container = OvzContainer.find(uuid=instance['uuid']) - if connection_info['driver_volume_type'] == 'iscsi': - volume = ovziscsi.OVZISCSIStorageDriver( - container.ovz_id, mountpoint, connection_info) - else: - raise NotImplementedError( - _('There are no suitable storage drivers')) - - volume.detach(container_is_running) - - def _detach_volumes(self, instance, block_device_mapping, - disconnect_only=False, container_is_running=True): - """ - Move bulk operations of volume connections back into the driver as - they are relevant here and no longer need to be in their own module. - :param instance: - :param block_device_mapping: - :return: None - """ - for volume in block_device_mapping['block_device_mapping']: - if disconnect_only: - self._disconnect_volume(volume['connection_info'], instance, - volume['mount_device'], - container_is_running) - else: - self.detach_volume( - volume['connection_info'], instance, - volume['mount_device']) - - def detach_volume(self, connection_info, instance, mountpoint=None): - """ - Detach the disk attached to the instance at mountpoint - """ - # Create a default mountpoint if none exists - if not mountpoint: - mountpoint = connection_info['mount_device'] - - self._disconnect_volume(connection_info, instance, mountpoint) - - # Remove storage connection info from the storage repo for the - # instance. - container = OvzContainer.find(uuid=instance['uuid']) - ext_str = ext_storage.OVZExtStorage(container.ovz_id) - ext_str.remove_volume(mountpoint) - ext_str.save() - - def get_info(self, instance): - """ - Get a block of information about the given instance. This is returned - as a dictionary containing 'state': The power_state of the instance, - 'max_mem': The maximum memory for the instance, in KiB, 'mem': The - current memory the instance has, in KiB, 'num_cpu': The current number - of virtual CPUs the instance has, 'cpu_time': The total CPU time used - by the instance, in nanoseconds. - - This method should raise exception.InstanceNotFound if the hypervisor - has no knowledge of the instance - """ - container = OvzContainer.find(name=instance['name']) - - # Store the assumed state as the default - # Coerced into an INT because it comes from SQLAlchemy as a string - state = int(instance['power_state']) - - LOG.debug(_('Instance %(uuid)s is in state %(power_state)s') % - {'uuid': container.uuid, 'power_state': state}) - - # NOTE(imsplitbit): This is not ideal but it looks like nova uses - # codes returned from libvirt and xen which don't correlate to - # the status returned from OpenVZ which is either 'running' or - # 'stopped'. There is some contention on how to handle systems - # that were shutdown intentially however I am defaulting to the - # nova expected behavior. - if container.state == 'running': - new_state = power_state.RUNNING - elif container.state is None or container.state == '-': - new_state = power_state.NOSTATE - else: - new_state = power_state.SHUTDOWN - - if state != new_state: - state = new_state - - LOG.debug( - _('OpenVz says instance %(uuid)s is in state %(state)s') % - {'uuid': container.uuid, 'state': state}) - - # TODO(imsplitbit): Need to add all metrics to this dict. - return {'state': state, - 'max_mem': 0, - 'mem': 0, - 'num_cpu': 0, - 'cpu_time': 0} - - def get_available_resource(self, nodename): - """Retrieve resource info. - - This method is called when nova-compute launches, and - as part of a periodic task. - - :returns: dictionary describing resources - - """ - return self.get_host_stats(refresh=True) - - def get_volume_connector(self, instance): - if not self._initiator: - self._initiator = ovz_utils.get_iscsi_initiator() - if not self._initiator: - LOG.warn(_('Could not determine iscsi initiator name'), - instance=instance) - return { - 'ip': CONF.my_ip, - 'initiator': self._initiator, - 'host': CONF.host - } - - def migrate_disk_and_power_off(self, context, instance, dest, - instance_type, network_info, - block_device_info=None): - """ - Transfers the disk of a running instance in multiple phases, turning - off the instance before the end. - """ - LOG.debug(_('Migration context: %s') % context) - LOG.debug(_('Migration instance: %s') % instance) - LOG.debug(_('Migration dest: %s') % dest) - LOG.debug(_('Migration instance_type: %s') % instance_type) - LOG.debug(_('Migration network_info: %s') % network_info) - - if not dest: - LOG.error(_('No destination given to migration')) - raise exception.MigrationError( - _('Migration destination is: %s') % dest) - - if dest == CONF.my_ip: - # if this is an inplace resize we don't need to do any of this - LOG.debug(_('This is an inplace migration')) - instance.system_metadata['migration_type'] = 'resize_in_place' - instance.save() - return - elif instance.system_metadata.get('migration_type'): - # if we failed to clear this metadata on a previous migration - # it will cause everything to blow up, so clear it out now - del instance.system_metadata['migration_type'] - instance.save() - - # Validate the ovz_migration_method flag - if CONF.ovz_migration_method not in ['vzmigrate', 'python']: - raise exception.MigrationError( - _('I do not understand your migration method')) - - # Find out if we have external volumes, this will determine - # if we will freeze the instance and attempt to preserve state of if - # we will stop the instance completely to preserve the integrity - # of the attached filesystems. - if block_device_info: - live_migration = False - self._stop(instance) - self._detach_volumes( - instance, block_device_info, True, live_migration) - else: - live_migration = True - self.suspend(instance) - - LOG.debug(_('ovz_migration_method is: %s') % - CONF.ovz_migration_method) - if CONF.ovz_migration_method == 'vzmigrate': - self._vzmigration_send_to_host(instance, dest) - elif CONF.ovz_migration_method == 'python': - container = OvzContainer.find(uuid=instance['uuid']) - self._pymigration_send_to_host( - instance, ovz_utils.generate_network_dict(container, - network_info), - block_device_info, dest, live_migration) - - def _pymigration_send_to_host(self, instance, network_info, - block_device_info, dest, live_migration): - """ - This performs a more complex but more secure migration using a pure - python implemented vz migration driver. - """ - LOG.debug(_('Beginning pure python based migration')) - container = OvzContainer.find(uuid=instance['uuid']) - mobj = ovz_migration.OVZMigration( - container, network_info, block_device_info, dest, live_migration) - mobj.dump_and_transfer_instance() - mobj.send() - - def _vzmigration_send_to_host(self, instance, dest): - """ - This performs a simple migration using openvz's supplied vzmigrate - script. It requires shared keys for root across all hosts and - does not support containers with externally attached volumes. And - currently TC rules aren't preserved. - """ - LOG.debug(_('Beginning vzmigrate based migration')) - cmd = ['vzmigrate'] - if CONF.ovz_vzmigrate_opts: - if isinstance(CONF.ovz_vzmigrate_opts, str): - cmd += CONF.ovz_vzmigrate_opts.split() - elif isinstance(CONF.ovz_vzmigrate_opts, list): - cmd += CONF.ovz_vzmigrate_opts - if CONF.ovz_vzmigrate_online_migration: - cmd.append('--online') - # default is yes - if not CONF.ovz_vzmigrate_destroy_source_container_on_migrate: - cmd += ['-r', 'no'] - if CONF.ovz_vzmigrate_verbose_migration_logging: - cmd.append('-v') - cmd.append(dest) - cmd.append(instance['uuid']) - LOG.debug( - _('Beginning the migration of %(instance_id)s to %(dest)s') % - {'instance_id': instance['uuid'], 'dest': dest}) - out = ovz_utils.execute(*cmd, run_as_root=True) - LOG.debug(_('Output from migration process: %s') % out) - - def finish_migration(self, context, migration, instance, disk_info, - network_info, image_meta, resize_instance, - block_device_info=None, power_on=True): - """Completes a resize, turning on the migrated instance - - :param network_info: - :py:meth:`~nova.network.manager.NetworkManager.get_instance_nw_info` - :param image_meta: image object returned by nova.image.glance that - defines the image from which this instance - was created - """ - # Get the instance metadata to see what we need to do - meta = ovz_utils.read_instance_metadata(instance['id']) - migration_type = meta.get('migration_type') - - if migration_type == 'resize_in_place': - # This is a resize on the same host so its simple, resize - # in place and then exit the method - LOG.debug(_('Finishing resize-in-place for %s') % instance['uuid']) - container = OvzContainer.find(uuid=instance['uuid']) - self.resource_manager.configure_container_resources(context, - container, instance['instance_type_id']) - self.resource_manager.configure_container_network(container, - network_info, is_migration=False) - - return - - if block_device_info: - # It is assumed that if there are externally attached volumes - # then this is not a live migration. - live_migration = False - else: - live_migration = True - - if CONF.ovz_migration_method == 'vzmigrate': - self._vzmigrate_setup_dest_host(instance, network_info) - elif CONF.ovz_migration_method == 'python': - self._pymigrate_finish_migration(instance, - network_info, - live_migration) - - if block_device_info: - # Once the files have been moved into place we need to attach - # volumes. - self._attach_volumes(instance, block_device_info) - - container = OvzContainer.find(uuid=instance['uuid']) - - if resize_instance: - LOG.debug(_('A resize after migration was requested: %s') % - instance['uuid']) - self.resource_manager.configure_container_resources(context, - container, instance['instance_type_id']) - self.resource_manager.configure_container_network(container, - network_info, is_migration=True) - LOG.debug(_('Resized instance after migration: %s') % - instance['uuid']) - else: - LOG.debug(_('Regenerating TC rules for instance %s') % - instance['uuid']) - self.resource_manager.configure_container_network(container, - network_info, is_migration=True) - LOG.debug(_('Regenerated TC rules for instance %s') % - instance['uuid']) - - if not live_migration: - self._start(instance) - - # Some data gets lost in the migration, make sure ovz has current info - container.save_ovz_metadata() - # instance.system_metadata will be saved by nova.compute.manager - # after this method returns (driver.finish_migration) - # ovz_utils.save_instance_metadata does not work because when this - # method returns nova.compute.manager calls instance.save and any - # info that was not updated through instance will be reverted - instance.system_metadata['ovz_id'] = container.ovz_id - - def _pymigrate_finish_migration(self, instance, network_info, - live_migration): - """ - Take all transferred files and put them back into place to create a - working instance. - """ - LOG.debug(_('Beginning python based finish_migration')) - - # generate a unique local id on the destination - container = OvzContainer( - ovz_id=OvzContainer.get_next_id(), - uuid=instance['uuid'], - nova_id=instance['id'], - host=CONF.host, - name=instance['name'], - ) - - interfaces = ovz_utils.generate_network_dict(container, - network_info) - mobj = ovz_migration.OVZMigration( - container, interfaces, None, live_migration) - mobj.undump_instance() - - # the vif name should have changed during migration, so set it up anew - self.plug_vifs(instance, network_info) - self._setup_networking(container, network_info) - - # Crude but we just need to give things time to settle before cleaning - # up all the dumped stuff - # TODO(imsplitbit): maybe a wait_for_start method with a looping - # timer is better here, will check into it soon - time.sleep(5) - mobj.cleanup_destination() - LOG.debug(_('Finished python based finish_migration')) - - def _vzmigrate_setup_dest_host(self, instance, network_info): - """ - Sequence to run on destination host should the migration be done - by the vzmigrate tools. - """ - LOG.debug(_('Stopping instance: %s') % instance['uuid']) - self._stop(instance) - LOG.debug(_('Stopped instance: %s') % instance['uuid']) - - self.plug_vifs(instance, network_info) - - LOG.debug(_('Starting instance: %s') % instance['uuid']) - self._start(instance) - LOG.debug(_('Started instance: %s') % instance['uuid']) - - def confirm_migration(self, migration, instance, network_info): - """ - Run on the source host to confirm the migration and cleans up the - the files from the source host. - """ - LOG.debug(_('Beginning confirm migration for %s') % instance['uuid']) - - # Get the instance metadata to see what we need to do - meta = ovz_utils.read_instance_metadata(instance['id']) - migration_type = meta.get('migration_type') - - container = OvzContainer.find(uuid=instance['uuid']) - live_migration = True - ext_str = ext_storage.OVZExtStorage(container.ovz_id) - if ext_str._volumes: - live_migration = False - - if migration_type == 'resize_in_place': - # This is a resize on the same host so its simple, resize - # in place and then exit the method - if ovz_utils.remove_instance_metadata_key(instance['id'], - 'migration_type'): - LOG.debug(_('Removed migration_type metadata')) - else: - LOG.debug(_('Failed to remove migration_type metadata')) - return - - try: - status = self.get_info(instance)['state'] - LOG.debug(_('State in confirm_migration: %s') % status) - if status == power_state.RUNNING: - LOG.warn( - _('Instance %s is running on source after migration') % - instance['uuid']) - self._stop(instance) - status = self.get_info(instance)['state'] - - if status == power_state.SHUTDOWN: - LOG.debug(_('Cleaning up migration on source host')) - mobj = ovz_migration.OVZMigration( - container, ovz_utils.generate_network_dict( - container, network_info), None, live_migration) - mobj.cleanup_source() - self._destroy(instance['id']) - self._clean_orphaned_files(instance['id']) - else: - LOG.warn( - _('Check instance: %(instance_id)s, it may be broken. ' - 'power_state: %(ps)s') % - {'instance_id': instance['uuid'], - 'ps': status}) - except exception.InstanceNotFound: - LOG.warn( - _('Instance %s not found, migration cleaned itself up?') % - instance['uuid']) - except exception.InstanceUnacceptable: - LOG.error(_('Failed to stop and destroy the instance')) - LOG.debug(_('Finished confirm migration for %s') % instance['uuid']) - - def finish_revert_migration(self, context, instance, network_info, - block_device_info=None, power_on=True): - """Finish reverting a resize, powering back on the instance.""" - # Get the instance metadata to see what we need to do - LOG.debug(_('Beginning finish_revert_migration')) - meta = ovz_utils.read_instance_metadata(instance['id']) - migration_type = meta.get('migration_type') - container = OvzContainer.find(uuid=instance['uuid']) - - if migration_type == 'resize_in_place': - # This is a resize on the same host so its simple, resize - # in place and then exit the method - LOG.debug(_('Reverting in-place migration for %s') % - instance['id']) - self.resource_manager.configure_container_resources(context, - container, instance['instance_type_id']) - self.resource_manager.configure_container_network(container, - network_info) - if ovz_utils.remove_instance_metadata_key(instance['id'], - 'migration_type'): - LOG.debug(_('Removed migration_type metadata')) - LOG.debug(_('Done reverting in-place migration for %s') % - instance['uuid']) - else: - LOG.debug(_('Failed to remove migration_type metadata')) - return - - container.save_ovz_metadata() - if block_device_info: - LOG.debug(_('Instance %s has volumes') % instance['id']) - # the instance has external volumes and was not a live migration - # so we need to reattach external volumes - live_migration = False - LOG.debug(_('Starting instance %s, after revert') % - instance['uuid']) - ext_str = ext_storage.OVZExtStorage(container.ovz_id) - - for mountpoint, connection_info in ext_str.volumes(): - self.attach_volume(connection_info, instance, mountpoint) - - self._start(instance) - else: - LOG.debug(_('Instance %s has no volumes') % instance['uuid']) - live_migration = True - LOG.debug(_('Resuming live migration for %s') % instance['uuid']) - self.resume(instance, network_info) - - mobj = ovz_migration.OVZMigration( - container, ovz_utils.generate_network_dict( - container, network_info), None, live_migration) - mobj.cleanup_files() - - # instance.system_metadata will be saved by nova.compute.manager - # after this method returns (driver.finish_revert_migration) - # ovz_utils.save_instance_metadata does not work because when this - # method returns nova.compute.manager calls instance.save and any - # info that was not updated through instance will be reverted - instance.system_metadata['ovz_id'] = container.ovz_id - - def get_host_ip_addr(self): - """ - Retrieves the IP address of the host - """ - return CONF.my_ip - - # TODO(imsplitbit): finish the outstanding software contract with nova - # All methods in the driver below this need to be worked out. - def snapshot(self, context, instance, image_id, update_task_state): - """ - Snapshots the specified instance. - - The given parameter is an instance of nova.compute.service.Instance, - and so the instance is being specified as instance.name. - - The second parameter is the name of the snapshot. - - The work will be done asynchronously. This function returns a - task that allows the caller to detect when it is complete. - """ - # TODO(imsplitbit): Need to implement vzdump - pass - - def rescue(self, context, instance, network_info, image_meta, - rescue_password): - """ - Rescue the specified instance. - """ - pass - - def unrescue(self, instance, network_info): - """ - Unrescue the specified instance. - """ - pass - - def get_diagnostics(self, instance_name): - pass - - def list_disks(self, instance_name): - """ - Return the IDs of all the virtual disks attached to the specified - instance, as a list. These IDs are opaque to the caller (they are - only useful for giving back to this layer as a parameter to - disk_stats). These IDs only need to be unique for a given instance. - - Note that this function takes an instance ID, not a - compute.service.Instance, so that it can be called by compute.monitor. - """ - return ['A_DISK'] - - def list_interfaces(self, instance_name): - """ - Return the IDs of all the virtual network interfaces attached to the - specified instance, as a list. These IDs are opaque to the caller - (they are only useful for giving back to this layer as a parameter to - interface_stats). These IDs only need to be unique for a given - instance. - - Note that this function takes an instance ID, not a - compute.service.Instance, so that it can be called by compute.monitor. - """ - return ['A_VIF'] - - def block_stats(self, instance_name, disk_id): - """ - Return performance counters associated with the given disk_id on the - given instance_name. These are returned as [rd_req, rd_bytes, wr_req, - wr_bytes, errs], where rd indicates read, wr indicates write, req is - the total number of I/O requests made, bytes is the total number of - bytes transferred, and errs is the number of requests held up due to a - full pipeline. - - All counters are long integers. - - This method is optional. On some platforms (e.g. XenAPI) performance - statistics can be retrieved directly in aggregate form, without Nova - having to do the aggregation. On those platforms, this method is - unused. - - Note that this function takes an instance ID, not a - compute.service.Instance, so that it can be called by compute.monitor. - """ - return [0L, 0L, 0L, 0L, None] - - def interface_stats(self, instance_name, iface_id): - """ - Return performance counters associated with the given iface_id on the - given instance_id. These are returned as [rx_bytes, rx_packets, - rx_errs, rx_drop, tx_bytes, tx_packets, tx_errs, tx_drop], where rx - indicates receive, tx indicates transmit, bytes and packets indicate - the total number of bytes or packets transferred, and errs and dropped - is the total number of packets failed / dropped. - - All counters are long integers. - - This method is optional. On some platforms (e.g. XenAPI) performance - statistics can be retrieved directly in aggregate form, without Nova - having to do the aggregation. On those platforms, this method is - unused. - - Note that this function takes an instance ID, not a - compute.service.Instance, so that it can be called by compute.monitor. - """ - return [0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L] - - def get_console_output(self, instance): - return 'FAKE CONSOLE OUTPUT' - - def get_ajax_console(self, instance): - return 'http://fakeajaxconsole.com/?token=FAKETOKEN' - - def get_console_pool_info(self, console_type): - return {'address': '127.0.0.1', 'username': 'fakeuser', - 'password': 'fakepassword'} - - def refresh_security_group_rules(self, security_group_id): - """This method is called after a change to security groups. - - All security groups and their associated rules live in the datastore, - and calling this method should apply the updated rules to instances - running the specified security group. - - An error should be raised if the operation cannot complete. - - """ - return True - - def refresh_security_group_members(self, security_group_id): - """This method is called when a security group is added to an instance. - - This message is sent to the virtualization drivers on hosts that are - running an instance that belongs to a security group that has a rule - that references the security group identified by `security_group_id`. - It is the responsiblity of this method to make sure any rules - that authorize traffic flow with members of the security group are - updated and any new members can communicate, and any removed members - cannot. - - Scenario: - * we are running on host 'H0' and we have an instance 'i-0'. - * instance 'i-0' is a member of security group 'speaks-b' - * group 'speaks-b' has an ingress rule that authorizes group 'b' - * another host 'H1' runs an instance 'i-1' - * instance 'i-1' is a member of security group 'b' - - When 'i-1' launches or terminates we will recieve the message - to update members of group 'b', at which time we will make - any changes needed to the rules for instance 'i-0' to allow - or deny traffic coming from 'i-1', depending on if it is being - added or removed from the group. - - In this scenario, 'i-1' could just as easily have been running on our - host 'H0' and this method would still have been called. The point was - that this method isn't called on the host where instances of that - group are running (as is the case with - :method:`refresh_security_group_rules`) but is called where references - are made to authorizing those instances. - - An error should be raised if the operation cannot complete. - - """ - return True - - def poll_rebooting_instances(self, timeout, instances): - """Poll for rebooting instances.""" - # TODO(Vek): Need to pass context in for access to auth_token - return - - def poll_rescued_instances(self, timeout): - """Poll for rescued instances.""" - # TODO(Vek): Need to pass context in for access to auth_token - return - - def power_off(self, instance): - """Power off the specified instance.""" - return - - def power_on(self, context, instance, network_info, block_device_info): - """Power on the specified instance.""" - return - - def compare_cpu(self, cpu_info): - """Compares given cpu info against host - - Before attempting to migrate a VM to this host, - compare_cpu is called to ensure that the VM will - actually run here. - - :param cpu_info: (str) JSON structure describing the source CPU. - :returns: None if migration is acceptable - :raises: :py:class:`~nova.exception.InvalidCPUInfo` if migration - is not acceptable. - """ - return - - def poll_unconfirmed_resizes(self, resize_confirm_window): - """Poll for unconfirmed resizes.""" - # TODO(Vek): Need to pass context in for access to auth_token - return - - def host_power_action(self, host, action): - """Reboots, shuts down or powers up the host.""" - return - - def set_host_enabled(self, host, enabled): - """Sets the specified host's ability to accept new instances.""" - # TODO(Vek): Need to pass context in for access to auth_token - return - - def ensure_filtering_rules_for_instance(self, instance_ref, network_info): - """Setting up filtering rules and waiting for its completion. - - To migrate an instance, filtering rules to hypervisors - and firewalls are inevitable on destination host. - ( Waiting only for filtering rules to hypervisor, - since filtering rules to firewall rules can be set faster). - - Concretely, the below method must be called. - - setup_basic_filtering (for nova-basic, etc.) - - prepare_instance_filter(for nova-instance-instance-xxx, etc.) - - to_xml may have to be called since it defines PROJNET, PROJMASK. - but libvirt migrates those value through migrateToURI(), - so , no need to be called. - - Don't use thread for this method since migration should - not be started when setting-up filtering rules operations - are not completed. - - :params instance_ref: nova.db.sqlalchemy.models.Instance object - - """ - # TODO(Vek): Need to pass context in for access to auth_token - return - - def unfilter_instance(self, instance, network_info): - """Stop filtering instance.""" - # TODO(Vek): Need to pass context in for access to auth_token - return - - def refresh_provider_fw_rules(self): - """This triggers a firewall update based on database changes. - - When this is called, rules have either been added or removed from the - datastore. You can retrieve rules with - :method:`nova.db.provider_fw_rule_get_all`. - - Provider rules take precedence over security group rules. If an IP - would be allowed by a security group ingress rule, but blocked by - a provider rule, then packets from the IP are dropped. This includes - intra-project traffic in the case of the allow_project_net_traffic - flag for the libvirt-derived classes. - - """ - # TODO(Vek): Need to pass context in for access to auth_token - return - - def agent_update(self, instance, url, md5hash): - """ - Update agent on the specified instance. - - The first parameter is an instance of nova.compute.service.Instance, - and so the instance is being specified as instance.name. The second - parameter is the URL of the agent to be fetched and updated on the - instance; the third is the md5 hash of the file for verification - purposes. - """ - # TODO(Vek): Need to pass context in for access to auth_token - return - - def update_host_status(self): - """Refresh host stats.""" - return - - def get_all_bw_usage(self, instances, start_time, stop_time=None): - """Return bandwidth usage info for each interface on each - running VM""" - return [] - - def snapshot_instance(self, context, instance_id, image_id): - return - - # The method to add to aggregates is not yet implemented, - # but the API needs to support it for the scheduler. We are - # adding this return in here so the driver does not complain - # when adding the aggregates to the API. The functionality of this - # is to only set the operational_state back to active - def add_to_aggregate(self, context, aggregate, host, **kwargs): - #NOTE(imsplitbit): only used for Xen Pools - return - - def resize(self, instance, flavor): - """ - Resizes/Migrates the specified instance. - - The flavor parameter determines whether or not the instance RAM and - disk space are modified, and if so, to what size. - """ - return diff --git a/ovznovadriver/openvz/file.py b/ovznovadriver/openvz/file.py deleted file mode 100644 index b790726..0000000 --- a/ovznovadriver/openvz/file.py +++ /dev/null @@ -1,224 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -from nova import exception -from ovznovadriver.localization import _ -from nova.openstack.common import log as logging -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg - -CONF = cfg.CONF - -LOG = logging.getLogger('ovznovadriver.openvz.file') - - -class OVZFile(object): - """ - This is a generic file class for wrapping up standard file operations that - may need to run on files associated with OpenVz - """ - def __init__(self, filename, permissions): - self.filename = os.path.abspath(filename) - self.contents = [] - self.permissions = permissions - - def __enter__(self): - """ - This may feel dirty but we need to be able to read and write files - as a non priviledged user so we need to change the permissions to - be more open for our file operations and then secure them once we - are done. - """ - if not self.exists(): - self.make_path() - self.touch() - - self.set_permissions(666) - - def __exit__(self, _type, value, tb): - if self.exists(): - self.set_permissions(self.permissions) - - def read(self): - """ - Open the file for reading only and read it's contents into the instance - attribute self.contents - """ - try: - with open(self.filename, 'r') as fh: - self.contents = fh.read().split('\n') - except Exception as err: - LOG.error(_('Output from open: %s') % err) - raise exception.FileNotFound( - _('Failed to read %s') % self.filename) - - def write(self): - """ - Because self.contents may or may not get manipulated throughout the - process, this is a method used to dump the contents of self.contents - back into the file that this object represents. - """ - LOG.debug(_('File contents before write: %s') % - '\n'.join(self.contents)) - try: - with open(self.filename, 'w') as fh: - fh.writelines('\n'.join(self.contents) + '\n') - except Exception as err: - LOG.error(_('Output from open: %s') % err) - raise exception.FileNotFound( - _('Failed to write %s') % self.filename) - - def touch(self): - """ - There are certain conditions where we create an OVZFile object but that - file may or may not exist and this provides us with a way to create - that file if it doesn't exist. - - Run the command: - - touch - - If this does not run an exception is raised as a failure to touch a - file when you intend to do so would cause a serious failure of - procedure. - """ - self.make_path() - ovz_utils.execute('touch', self.filename, run_as_root=True) - - def make_proper_script(self): - """ - OpenVz mount and umount files must be properly formatted scripts. - Prepend the proper shell script header to the files - """ - if not self.contents[:1] == ['#!/bin/sh']: - self.prepend('#!/bin/sh') - - def append(self, contents): - """ - Add the argument contents to the end of self.contents - """ - if not isinstance(contents, list): - contents = [str(contents)] - self.contents += contents - LOG.debug(_('File contents: %s') % self.contents) - - def prepend(self, contents): - """ - Add the argument contents to the beginning of self.contents - """ - if not isinstance(contents, list): - contents = [str(contents)] - self.contents = contents + self.contents - LOG.debug(_('File contents: %s') % self.contents) - - def delete(self, contents): - """ - Delete the argument contents from self.contents if they exist. - """ - if isinstance(contents, list): - LOG.debug(_('A list was passed to delete: %s') % contents) - for line in contents: - LOG.debug(_('Line: %(line)s \tFound in: %(contents)s') % - locals()) - self.remove_line(line) - else: - LOG.debug(_('A string was passed to delete: %s') % contents) - self.remove_line(contents) - - def remove_line(self, line): - """ - Simple helper method to actually do the removal of a line from an array - """ - LOG.debug(_('Removing line if present: %s') % line) - if line in self.contents: - LOG.debug(_('Line found: %s') % line) - self.contents.remove(line) - LOG.debug(_('Line removed: %(line)s \t%(contents)s') % - {'line': line, 'contents': self.contents}) - - def set_permissions(self, permissions): - """ - Because nova runs as an unprivileged user we need a way to mangle - permissions on files that may be owned by root for manipulation - - Run the command: - - chmod - - If this doesn't run an exception is raised because the permissions not - being set to what the application believes they are set to can cause - a failure of epic proportions. - """ - ovz_utils.execute('chmod', permissions, self.filename, - run_as_root=True) - - def make_path(self, path=None): - """ - Helper method for an OVZFile object to be able to create the path for - self.filename if it doesn't exist before running touch() - """ - if not path: - path = self.filename - basedir = os.path.dirname(path) - ovz_utils.make_dir(basedir) - - def set_contents(self, new_contents): - """ - We need the ability to overwrite all contents and this is the cleanest - way while allowing some validation. - """ - if isinstance(new_contents, str): - LOG.debug(_('Type of new_contents is: str')) - self.contents = new_contents.split('\n') - LOG.debug(_('Contents of file: %s') % self.contents) - elif isinstance(new_contents, list): - LOG.debug(_('Type of new_contents is: list')) - self.contents = new_contents - else: - raise TypeError(_("I don't know what to do with this type: %s") % - type(new_contents)) - - def run_contents(self, raise_on_error=True): - # Because only approved commands in rootwrap can be executed we - # don't need to worry about unwanted command injection - for line in self.contents: - if len(line) > 0: - if line[0] != '#' and line != '\n': - line = line.strip() - try: - LOG.debug( - _('Running line from %(filename)s: %(line)s') % - {'filename': self.filename, 'line': line}) - line = line.split() - ovz_utils.execute( - *line, run_as_root=True, - raise_on_error=raise_on_error) - except exception.InstanceUnacceptable as err: - LOG.error(_('Cannot execute: %s') % line) - LOG.error(err) - - def exists(self): - """ - Simple wrapper for os.path.exists - """ - return os.path.exists(self.filename) diff --git a/ovznovadriver/openvz/file_ext/__init__.py b/ovznovadriver/openvz/file_ext/__init__.py deleted file mode 100644 index 3e1c627..0000000 --- a/ovznovadriver/openvz/file_ext/__init__.py +++ /dev/null @@ -1,16 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. diff --git a/ovznovadriver/openvz/file_ext/boot.py b/ovznovadriver/openvz/file_ext/boot.py deleted file mode 100644 index d8f45ad..0000000 --- a/ovznovadriver/openvz/file_ext/boot.py +++ /dev/null @@ -1,43 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -OpenVZ doesn't allow for a script to be run after a container has started up -using the host node's context so we are implementing one here -""" - -from nova.openstack.common import log as logging -from ovznovadriver.openvz import file as ovzfile -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.file_ext.boot') - - -class OVZBootFile(ovzfile.OVZFile): - def __init__(self, instance_id, permissions): - """ - Child class of OVZFile used to manage the CTID.boot file. This file - will be executed line by line after the container has started but - using the host's context. - - :param instance_id: Instance used for the file - """ - filename = "%s/%s.boot" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - super(OVZBootFile, self).__init__(filename, permissions) diff --git a/ovznovadriver/openvz/file_ext/ext_storage.py b/ovznovadriver/openvz/file_ext/ext_storage.py deleted file mode 100644 index 200ebf0..0000000 --- a/ovznovadriver/openvz/file_ext/ext_storage.py +++ /dev/null @@ -1,118 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -import json -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -from ovznovadriver.openvz import file as ovzfile -import os -from oslo.config import cfg - - -CONF = cfg.CONF - -LOG = logging.getLogger('ovznovadriver.openvz.file_ext.ext_storage') - - -class OVZExtStorage(object): - """ - Local store for volume information needing to be persisted to the local - host. - """ - def __init__(self, instance_id): - """ - :param instance_id: CTID of the container - :return: None - """ - filename = '%s/%s.ext_storage' % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - self.instance_id = instance_id - self.local_store = ovzfile.OVZFile(filename, 600) - - # read the local store for the CTID or create it if it doesn't already - # exist. - with self.local_store: - self.local_store.read() - - # preload volume info - self.load_volumes() - - def load_volumes(self): - """ - return the contents of self.contents *after* converting it from json - to python objects. - - :return: list - """ - try: - self._volumes = json.loads(self.local_store.contents[0]) - except (ValueError, IndexError): - self._volumes = dict() - - def add_volume(self, device, volume_info): - """ - Add a volume to local storage so volumes can be reconnected to in - emergencies without nova services if need be. - - :param device: Device name - :param volume_info: Nova volume information from block_device_map - :return: None - """ - self._volumes[device] = volume_info - - def remove_volume(self, device): - """ - removes a volume from the volume store. - - :param device: - :return: None - """ - try: - self._volumes.pop(device) - LOG.debug( - _('Removed volume %(device)s from instance %(instance_id)s') % - {'device': device, 'instance_id': self.instance_id}) - except KeyError: - LOG.error( - _('Volume %(device)s was not in local store for ' - 'instance %(instance_id)s') % - {'device': device, 'instance_id': self.instance_id}) - - def save(self): - """ - Flushes contents of self._volumes to disk for persistance - - :return: None - """ - self.local_store.set_contents(json.dumps(self._volumes)) - with self.local_store: - self.local_store.write() - - def volumes(self): - """ - Simple generator to give back the volumes in an iterable and - adventurous way. - - :return: device name, connection info - """ - for key in self._volumes.keys(): - yield key, self._volumes[key] diff --git a/ovznovadriver/openvz/file_ext/shutdown.py b/ovznovadriver/openvz/file_ext/shutdown.py deleted file mode 100644 index e174f58..0000000 --- a/ovznovadriver/openvz/file_ext/shutdown.py +++ /dev/null @@ -1,45 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -OpenVz doesn't have provision for a script to be run before a container -is stopped but with the host node's context so we are implementing one here. -""" -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -from ovznovadriver.openvz import file as ovzfile -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.file_ext.shutdown') - - -class OVZShutdownFile(ovzfile.OVZFile): - def __init__(self, instance_id, permissions): - """ - Child class of OVZFile used to manage the CTID.boot file. This file - will be executed line by line after the container has started but - using the host's context. - - :param instance_id: Instance used for the file - """ - LOG.debug(_('Beginning OVZShutdownFile')) - filename = "%s/%s.shutdown" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - LOG.debug(_('OVZShutdownFile: %s') % filename) - super(OVZShutdownFile, self).__init__(filename, permissions) diff --git a/ovznovadriver/openvz/file_ext/start.py b/ovznovadriver/openvz/file_ext/start.py deleted file mode 100644 index 15abea5..0000000 --- a/ovznovadriver/openvz/file_ext/start.py +++ /dev/null @@ -1,33 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" -from ovznovadriver.openvz import file as ovzfile -import os -from oslo.config import cfg - -CONF = cfg.CONF - - -class OVZContainerStartScript(ovzfile.OVZFile): - def __init__(self, instance_id): - filename = "%s/%s.start" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - super(OVZContainerStartScript, self).__init__(filename) diff --git a/ovznovadriver/openvz/file_ext/stop.py b/ovznovadriver/openvz/file_ext/stop.py deleted file mode 100644 index 306cbfd..0000000 --- a/ovznovadriver/openvz/file_ext/stop.py +++ /dev/null @@ -1,33 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" -from ovznovadriver.openvz import file as ovzfile -import os -from oslo.config import cfg - -CONF = cfg.CONF - - -class OVZContainerStopScript(ovzfile.OVZFile): - def __init__(self, instance_id): - filename = "%s/%s.stop" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - super(OVZContainerStopScript, self).__init__(filename) diff --git a/ovznovadriver/openvz/migration.py b/ovznovadriver/openvz/migration.py deleted file mode 100644 index 2fc0746..0000000 --- a/ovznovadriver/openvz/migration.py +++ /dev/null @@ -1,386 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" -from nova import exception -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -from ovznovadriver.openvz.container import OvzContainer -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.volume') - - -class OVZMigration(object): - def __init__(self, container, interfaces, block_device_info=None, - dest=None, live=False): - self.container = container - - # TODO(pdmars): does interfaces need to be in the legacy - # network_info format? because it's not anymore - self.interfaces = interfaces - self.block_device_info = block_device_info - self.destination_host = dest - self.live_migration = live - - self.instance_tarfile = os.path.abspath('%s/%s.tar' % - (CONF.ovz_tmp_dir, - self.container.uuid)) - - self.instance_parent = CONF.ovz_ve_private_dir - self.instance_source = os.path.abspath( - '%s/%s' % (self.instance_parent, self.container.ovz_id)) - self.dumpdir_name = '%s-dumpdir' % self.container.uuid - self.dumpdir_parent = CONF.ovz_tmp_dir - self.dumpdir = os.path.abspath('%s/%s' % (self.dumpdir_parent, - self.dumpdir_name)) - self.i_dumpdir = os.path.abspath('%s/instance' % self.dumpdir) - self.dumpfile = os.path.abspath( - '%s/dump.%s' % (self.i_dumpdir, self.container.uuid)) - self.q_dumpdir = os.path.abspath('%s/quotas' % self.dumpdir) - self.qdumpfile = os.path.abspath( - '%s/qdump.%s' % (self.q_dumpdir, self.container.uuid)) - self.as_dumpdir = os.path.abspath('%s/ascripts' % self.dumpdir) - self.actionscripts = ['start', 'stop', 'mount', 'umount', 'premount', - 'postumount', 'boot', 'shutdown', 'conf', - 'ext_storage'] - self.dumpdir_tarfile = '%s.tar' % self.dumpdir - - def dump_and_transfer_instance(self): - """ - Put all the pieces together to dump the instance and make the dump - ready for transfer to the destination host. - """ - - self.container.prep_for_migration() - self.make_dump_dir() - - # Begin the dumping process - if self.live_migration: - # this is a live migration so dump current memory and network - # state. - LOG.debug(_('Making container backup for %s') % - self.container.ovz_id) - self.dump() - else: - LOG.debug(_('Archiving container to tar: %s') % - self.container.ovz_id) - self.tar_instance() - - # Take all instance scripts from /etc/vz/conf and put them in a - # tarball for transfer. - LOG.debug(_('Making action script backups for %s') % - self.container.ovz_id) - self.backup_action_scripts() - LOG.debug(_('Archiving misc files: %s') % self.container.ovz_id) - self.tar_dumpdir() - LOG.debug(_('Migration image created')) - - def undump_instance(self): - """ - Take the pieces of a dump archive and put them back in place. - """ - # If a non-root user was used to transfer the files then we - # need to move everything to where it is expected to be. - LOG.debug(_('Restoring action scripts from archive: %s') % - self.dumpdir_tarfile) - self.untar_dumpdir() - LOG.debug(_('Restoring action scripts for %s') % self.container.ovz_id) - self.restore_action_scripts() - - if self.live_migration: - LOG.debug(_('Restoring container state from dump for %s') % - self.container.ovz_id) - self.undump() - - LOG.debug(_('Resuming container: %s') % self.container.ovz_id) - self.resume() - else: - LOG.debug(_('Restoring container from tar: %s') % - self.container.ovz_id) - self.untar_instance() - - root_dir = os.path.join(CONF.ovz_ve_root_dir, self.container.ovz_id) - if os.path.exists(root_dir) is False: - ovz_utils.execute('mkdir', '-p', root_dir, run_as_root=True) - # ensure we can interact with the new instance via its uuid - self.container.save_ovz_metadata() - - LOG.debug(_('Done restoring instance %s') % self.container.ovz_id) - - def make_dump_dir(self): - """ - Make our dump locations - """ - LOG.debug(_('Making dump location for %s') % self.container.ovz_id) - ovz_utils.make_dir(self.dumpdir) - ovz_utils.make_dir(self.i_dumpdir) - ovz_utils.make_dir(self.q_dumpdir) - ovz_utils.make_dir(self.as_dumpdir) - LOG.debug(_('Done making location for %s') % self.container.ovz_id) - - def cleanup_source(self): - """ - Helper method to wrap up all methods required to clean up a - migration. - """ - if self.live_migration: - self.kill() - - self.cleanup_files() - - def cleanup_destination(self): - """ - Do anything you need to do on the destination host to clean it up - """ - self.cleanup_files() - - def dump(self): - """ - Create a vz dump file from a container. This is the file that we - transfer to do a full migration - """ - LOG.debug(_('Dumping instance %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'chkpnt', self.container.ovz_id, - '--dump', '--dumpfile', self.dumpfile, - run_as_root=True) - LOG.debug(_('Dumped instance %(instance_id)s to %(dumpfile)s') % - {'instance_id': self.container.ovz_id, - 'dumpfile': self.dumpfile}) - - def undump(self): - """ - Restore a VZ from a dump file - """ - LOG.debug(_('Undumping instance %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'restore', self.container.ovz_id, '--undump', - '--dumpfile', self.dumpfile, '--skip_arpdetect', - run_as_root=True) - LOG.debug(_('Undumped instance %(instance_id)s from %(dumpfile)s') % - {'instance_id': self.container.ovz_id, - 'dumpfile': self.dumpfile}) - - def resume(self): - """ - Resume a container from an undumped migration - """ - LOG.debug(_('Resuming instance %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'restore', self.container.ovz_id, - '--resume', run_as_root=True) - LOG.debug(_('Resumed instance %s') % self.container.ovz_id) - - def kill(self): - """ - This is used to stop a container once it's suspended without having to - resume it to properly destroy it - """ - LOG.debug(_('Killing instance %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'chkpnt', self.container.ovz_id, - '--kill', run_as_root=True) - LOG.debug(_('Killed instance %s') % self.container.ovz_id) - - def quotadump(self): - """ - Dump the quotas for containers - """ - LOG.debug(_('Dumping quotas for %s') % self.container.ovz_id) - ovz_utils.execute('vzdqdump', self.container.ovz_id, '-U', '-G', - '-T', '>', self.qdumpfile, run_as_root=True) - LOG.debug(_('Dumped quotas for %s') % self.container.ovz_id) - - def quotaload(self): - """ - Load quotas from quota file - """ - LOG.debug(_('Loading quotas for %s') % self.container.ovz_id) - ovz_utils.execute('vzdqload', self.container.ovz_id, '-U', '-G', '-T', - '<', self.qdumpfile, run_as_root=True) - LOG.debug(_('Loaded quotas for %s') % self.container.ovz_id) - - def quotaenable(self): - """ - enable quotas for a given container - """ - LOG.debug(_('Enabling quotas for %s') % self.container.ovz_id) - ovz_utils.execute('vzquota', 'reload2', - self.container.ovz_id, run_as_root=True) - LOG.debug(_('Enabled quotas for %s') % self.container.ovz_id) - - def quota_init(self): - """ - Initialize quotas for instance - """ - LOG.debug(_('Initializing quotas for %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'quotainit', self.container.ovz_id) - LOG.debug(_('Initialized quotas for %s') % self.container.ovz_id) - - def quota_on(self): - """ - Turn on quotas for instance - """ - LOG.debug(_('Turning on quotas for %s') % self.container.ovz_id) - ovz_utils.execute('vzctl', 'quotaon', self.container.ovz_id, - run_as_root=True) - LOG.debug(_('Turned on quotas for %s') % self.container.ovz_id) - - def backup_action_scripts(self): - """ - Take the action scripts with us in the backup/migration - """ - LOG.debug(_('Copying actionscripts into place')) - for a_script in self.actionscripts: - a_script_src = os.path.abspath( - '%s/%s.%s' % (CONF.ovz_config_dir, self.container.ovz_id, - a_script)) - if os.path.exists(a_script_src): - LOG.debug(_('Copying actionscript: %s') % a_script_src) - a_script_dest = os.path.abspath( - '%s/%s.%s' % (self.as_dumpdir, self.container.uuid, - a_script)) - ovz_utils.copy(a_script_src, a_script_dest) - LOG.debug(_('Copied actionscript: %(src)s as %(dest)s') - % { 'src': a_script_src, 'dest': a_script_dest }) - LOG.debug(_('Copied actionscripts into place')) - - def restore_action_scripts(self): - """ - Put the action scripts back into place - """ - LOG.debug(_('Restoring actionscripts into place')) - for a_script in self.actionscripts: - a_script_src = os.path.abspath('%s/%s.%s' % (self.as_dumpdir, - self.container.uuid, - a_script)) - if os.path.exists(a_script_src): - LOG.debug(_('Restoring actionscript: %s') % a_script_src) - a_script_dest = os.path.abspath( - '%s/%s.%s' % (CONF.ovz_config_dir, self.container.ovz_id, - a_script)) - ovz_utils.copy(a_script_src, a_script_dest) - LOG.debug(_('Restored actionscript: %(src)s as %(dest)s') - % { 'src': a_script_src, 'dest': a_script_dest }) - LOG.debug(_('Restored actionscripts into place')) - - def send(self): - """ - Use the configured transport to transfer the image from the src to - the dest host. This will run on the source host. - """ - # Set the destination and source for the instance transfer - src_path = self.instance_tarfile - dest_path = CONF.ovz_tmp_dir - - transport_instance = self._setup_transport(src_path, dest_path) - transport_instance.send() - - # Set the destination and source for the dumpdir transfer - src_path = self.dumpdir_tarfile - dest_path = self.dumpdir_parent - - transport_instance_scripts = self._setup_transport(src_path, dest_path) - transport_instance_scripts.send() - - def receive(self): - """ - Use the configured transport to transfer the image form the src to - dest host. This will run on the destination host - """ - # Right now we don't have a transport that needs this. - raise NotImplementedError() - - def cleanup_files(self): - """ - Remove the files in the OpenVz temp dir - """ - LOG.debug(_('Cleaning migration files for %s') % self.container.ovz_id) - ovz_utils.execute('rm', '-rf', self.dumpdir, run_as_root=True) - ovz_utils.execute('rm', '-f', self.dumpdir_tarfile, run_as_root=True) - if self.instance_tarfile: - ovz_utils.execute('rm', '-f', self.instance_tarfile, - run_as_root=True) - LOG.debug( - _('Cleaned up migration files for %s') % self.container.ovz_id) - - def tar_instance(self): - """ - Not an optimal way to do this but if you aren't using the root user - to rsync the files from host to host you need to preserve the - permissions and ownerships thus tar is your only hope. - """ - # Create our batch volume operations object - LOG.debug(_('Tarring up instance: %s') % self.container.ovz_id) - sed_regex = 's/%(ctid)s/%(uuid)s/' % { - 'ctid': self.container.ovz_id, - 'uuid': self.container.uuid, - } - ovz_utils.tar(self.container.ovz_id, self.instance_tarfile, - working_dir=self.instance_parent, - extra=['--transform', sed_regex]) - LOG.debug(_('Tarred up instance: %s') % self.container.ovz_id) - - def tar_dumpdir(self): - """ - Archive the instance action scripts - """ - LOG.debug(_('Tarring up instance dumpdir: %s') % self.dumpdir) - ovz_utils.tar(self.dumpdir_name, self.dumpdir_tarfile, - self.dumpdir_parent) - LOG.debug(_('Tarred up instance dumpdir: %s') % self.dumpdir) - - def untar_instance(self): - """ - Expand the tarball from the instance and expand it into place - """ - LOG.debug(_('Untarring instance: %s') % self.instance_tarfile) - LOG.debug(_('Make sure directory exists: %s') % self.instance_source) - ovz_utils.make_dir(self.instance_source) - - sed_regex = 's/%(uuid)s/%(ctid)s/' % { - 'ctid': self.container.ovz_id, - 'uuid': self.container.uuid, - } - ovz_utils.untar(self.instance_tarfile, self.instance_parent, - extra=['--transform', sed_regex]) - LOG.debug(_('Untarred instance: %s') % self.instance_source) - - def untar_dumpdir(self): - """ - Expand the dumpdir into place on the destination machine - """ - LOG.debug(_('Untarring instance dumpdir: %s') % self.dumpdir) - ovz_utils.untar(self.dumpdir_tarfile, self.dumpdir_parent) - LOG.debug(_('Untarred instance dumpdir: %s') % self.dumpdir) - - def _setup_transport(self, src_path, dest_path, skip_list=None): - if CONF.ovz_migration_transport == 'rsync': - from ovznovadriver.openvz.migration_drivers import rsync - return rsync.OVZMigrationRsyncTransport( - src_path, dest_path, self.container.ovz_id, - self.destination_host, skip_list) - else: - LOG.error( - _('I do not understand your migration transport: %s') % - CONF.ovz_migration_transport) - raise exception.MigrationError( - _('No valid migration transport: %s') % - CONF.ovz_migration_transport) diff --git a/ovznovadriver/openvz/migration_drivers/__init__.py b/ovznovadriver/openvz/migration_drivers/__init__.py deleted file mode 100644 index 3e1c627..0000000 --- a/ovznovadriver/openvz/migration_drivers/__init__.py +++ /dev/null @@ -1,16 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. diff --git a/ovznovadriver/openvz/migration_drivers/rsync.py b/ovznovadriver/openvz/migration_drivers/rsync.py deleted file mode 100644 index 445aefe..0000000 --- a/ovznovadriver/openvz/migration_drivers/rsync.py +++ /dev/null @@ -1,66 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -Driver for OVZ Migrations. Uses rsync as a backend. -""" -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -from ovznovadriver.openvz.migration_drivers import transport -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.migration_drivers.rsync') - - -class OVZMigrationRsyncTransport(transport.OVZMigrationTransport): - def __init__(self, src_path, dest_path, instance_id, - dest_host, skip_list=None): - super(OVZMigrationRsyncTransport, self).__init__(src_path, - dest_path, - instance_id, - dest_host, - skip_list) - - def send(self): - """ - Send image/files to a destination. This should be run on the source - host. - """ - LOG.debug(_('Running _rsync()')) - self._rsync(self.src_path, self.dest_path) - LOG.debug(_('Ran _rsync()')) - super(OVZMigrationRsyncTransport, self).send() - - def _rsync(self, src_path, dest_path): - """ - Copy a path from one place to another using rsync - """ - dest = '%s@%s:%s' % (self.user, self.dest_host, - os.path.abspath(dest_path)) - counter = 1 - while counter <= CONF.ovz_rsync_iterations: - LOG.debug(_('RSyncing %(src_path)s, attempt: %(counter)s') % - locals()) - ovz_utils.execute('rsync', - '-qavz', - src_path, - dest, - run_as_root=True) - counter += 1 diff --git a/ovznovadriver/openvz/migration_drivers/transport.py b/ovznovadriver/openvz/migration_drivers/transport.py deleted file mode 100644 index f7d09ae..0000000 --- a/ovznovadriver/openvz/migration_drivers/transport.py +++ /dev/null @@ -1,73 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -Generic transport class for OVZ Migrations. Common methods will be placed -in this file for reuse. -""" -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.migration_drivers.transport') - - -class OVZMigrationTransport(object): - def __init__(self, src_path, dest_path, instance_id, - dest_host, skip_list=None): - self.src_path = src_path - self.dest_path = dest_path - self.instance_id = instance_id - self.dest_host = dest_host - self.skip_list = skip_list - self.user = CONF.ovz_migration_user - self.container_path = os.path.abspath('%s/%s' % - (CONF.ovz_ve_private_dir, - self.instance_id)) - - def send(self): - """ - Code should go here to support what needs to be done upon sending a - container to another host. This should be called from all transport - drivers after their work is done on the source host. - """ - LOG.debug(_('Beginning send() for %s') % self.instance_id) - # Generic use case transport code goes here, this code is run - # after any code in a custom transport - LOG.debug(_('Finished send() for %s') % self.instance_id) - - def receive(self): - """ - Code should go here to support what needs to be done upon receiving a - container from another host. This should be called from all transport - drivers after their work is done on the destination host. - """ - LOG.debug(_('Beginning receive() for %s') % self.instance_id) - # Generic use case transport code goes here, this code is run - # after any code in a custom transport - LOG.debug(_('Finished receive() for %s') % self.instance_id) - - def verify(self): - """ - Check things on the destination host to make sure that the migration - went well. - """ - LOG.debug(_('Beginning verify() for %s') % self.instance_id) - # Generic use case transport code goes here - LOG.debug(_('Finished verify() for %s') % self.instance_id) diff --git a/ovznovadriver/openvz/network.py b/ovznovadriver/openvz/network.py deleted file mode 100644 index 676613d..0000000 --- a/ovznovadriver/openvz/network.py +++ /dev/null @@ -1,201 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -from nova import exception -from nova.openstack.common import log as logging -from nova.virt import netutils -from ovznovadriver.localization import _ -from ovznovadriver.openvz import file as ovzfile -from ovznovadriver.openvz.container import OvzContainer -from ovznovadriver.openvz.file_ext import boot as ovzboot -from ovznovadriver.openvz.file_ext import shutdown as ovzshutdown -from ovznovadriver.openvz.network_drivers import tc as ovztc -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.network') - - -class OVZNetworkInterfaces(object): - """ - Helper class for managing interfaces in OpenVz - """ - #TODO(imsplitbit): fix this to work with redhat based distros - def __init__(self, container, interface_info, network_info=None): - """ - Manage the network interfaces for your OpenVz containers. - """ - self.interface_info = interface_info - self.network_info = network_info - LOG.debug(_('Interface info: %s') % self.interface_info) - self.container = container - self.boot_file = ovzboot.OVZBootFile(container.ovz_id, 755) - with self.boot_file: - self.boot_file.set_contents(list()) - self.shutdown_file = ovzshutdown.OVZShutdownFile(container.ovz_id, 755) - with self.shutdown_file: - self.shutdown_file.set_contents(list()) - - def add(self): - """ - Add all interfaces and addresses to the container. - """ - if CONF.ovz_use_veth_devs: - for net_dev in self.interface_info: - self._add_netif(net_dev['name'], net_dev['bridge'], - net_dev['mac']) - tc_rules = ovztc.OVZTcRules() - tc_rules.instance_info(self.container.nova_id, - net_dev['address'], - net_dev['vz_host_if']) - with self.boot_file: - self.boot_file.append(tc_rules.container_start()) - - with self.shutdown_file: - self.shutdown_file.append(tc_rules.container_stop()) - - self._fill_templates() - else: - for net_dev in self.interface_info: - self._add_ip(net_dev['address']) - - with self.boot_file: - self.boot_file.write() - - with self.shutdown_file: - self.shutdown_file.write() - - self._set_nameserver(self.interface_info[0]['dns']) - - def _fill_templates(self): - """ - Iterate through each file necessary for creating interfaces on a - given platform, open the file and write the contents of the template - to the file. - """ - iface_file = netutils.get_injected_network_template(self.network_info, - use_ipv6=CONF.use_ipv6, - template=CONF.injected_network_template) - for filename in self._filename_factory(): - network_file = OVZNetworkFile(filename) - with network_file: - network_file.append(iface_file) - network_file.write() - - def _filename_factory(self, variant='debian'): - """ - Generate a path for the file needed to implement an interface - """ - #TODO(imsplitbit): Figure out how to introduce OS hints into nova - # so we can generate support for redhat based distros. This will - # require an os hint to be placed in glance to use for making - # decisions. Then we can create a generator that will generate - # redhat style interface paths like: - # - # /etc/sysconfig/network-scripts/ifcfg-eth0 - # - # for now, we just return the debian path. - - redhat_path = '/etc/sysconfig/network-scripts/' - debian_path = '/etc/network/interfaces' - prefix = '%(private_dir)s/%(instance_id)s' %\ - {'private_dir': CONF.ovz_ve_private_dir, - 'instance_id': self.container.ovz_id} - prefix = os.path.abspath(prefix) - - #TODO(imsplitbit): fix this placeholder for RedHat compatibility. - if variant == 'redhat': - for net_dev in self.interface_info: - path = prefix + redhat_path + ('ifcfg-%s' % net_dev['name']) - path = os.path.abspath(path) - LOG.debug(_('Generated filename %(path)s') % locals()) - yield path - elif variant == 'debian': - path = prefix + debian_path - path = os.path.abspath(path) - LOG.debug(_('Generated filename %(path)s') % locals()) - yield path - else: - raise exception.InvalidMetadata( - _('Variant %(variant)s is not known') % locals()) - - def _add_netif(self, netif, bridge, host_mac): - """ - This is a work around to add the eth devices the way OpenVZ - wants them. - - When this works, it runs a command similar to this: - - vzctl set 1 --save --netif_add \ - eth0,,veth1.eth0,11:11:11:11:11:11,br100 - """ - host_if = 'veth%s.%s' % (self.container.ovz_id, netif) - ovz_utils.execute('vzctl', 'set', self.container.ovz_id, '--save', - '--netif_add', - '%s,,%s,%s,%s' % (netif, host_if, host_mac, bridge), - run_as_root=True) - - def _add_ip(self, ip): - """ - Add an IP address to a container if you are not using veth devices. - - Run the command: - - vzctl set --save --ipadd - - If this fails to run an exception is raised as this indicates a failure - to create a network available connection within the container thus - making it unusable to all but local users and therefore unusable to - nova. - """ - ovz_utils.execute('vzctl', 'set', self.container.ovz_id, '--save', - '--ipadd', ip, run_as_root=True) - - def _set_nameserver(self, dns): - """ - Get the nameserver for the assigned network and set it using - OpenVz's tools. - - Run the command: - - vzctl set --save --nameserver - - If this fails to run an exception is raised as this will indicate - the container's inability to do name resolution. - """ - ovz_utils.execute('vzctl', 'set', self.container.ovz_id, '--save', - '--nameserver', dns, run_as_root=True) - - -class OVZNetworkFile(ovzfile.OVZFile): - """ - An abstraction for network files. This is necessary for multi-platform - support. OpenVz runs on all linux distros and can host all linux distros - but they don't all create interfaces the same way. This should make it - easy to add interface files to all flavors of linux. - """ - - def __init__(self, filename): - super(OVZNetworkFile, self).__init__(filename, 644) - diff --git a/ovznovadriver/openvz/network_drivers/__init__.py b/ovznovadriver/openvz/network_drivers/__init__.py deleted file mode 100644 index 3e1c627..0000000 --- a/ovznovadriver/openvz/network_drivers/__init__.py +++ /dev/null @@ -1,16 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. diff --git a/ovznovadriver/openvz/network_drivers/network_bridge.py b/ovznovadriver/openvz/network_drivers/network_bridge.py deleted file mode 100644 index 70e6787..0000000 --- a/ovznovadriver/openvz/network_drivers/network_bridge.py +++ /dev/null @@ -1,59 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -from nova.network import linux_net -from ovznovadriver.localization import _ -from nova.openstack.common import log as logging - -LOG = logging.getLogger('ovznovadriver.openvz.network_drivers.network_bridge') - - -class OVZNetworkBridgeDriver(object): - """ - VIF driver for a Linux Bridge - """ - - def plug(self, instance, vif): - """ - Ensure that the bridge exists and add a vif to it. - """ - if (not vif['network'].get_meta('should_create_bridge', False) and - vif['network'].get_meta('should_create_vlan', False)): - if vif['network'].get_meta('should_create_vlan', False): - LOG.debug(_('Ensuring bridge %(bridge)s and vlan %(vlan)s') % - {'bridge': vif['network']['bridge'], - 'vlan': vif['network'].get_meta('vlan')}) - linux_net.LinuxBridgeInterfaceDriver.ensure_vlan_bridge( - vif['network'].get_meta('vlan'), - vif['network']['bridge'], - vif['network'].get_meta('bridge_interface')) - else: - LOG.debug(_('Ensuring bridge %s') % vif['network']['bridge']) - linux_net.LinuxBridgeInterfaceDriver.ensure_bridge( - vif['network']['bridge'], - vif['network'].get_meta('bridge_interface')) - - def unplug(self, instance, vif): - """ - No manual unplugging required - """ - pass diff --git a/ovznovadriver/openvz/network_drivers/tc.py b/ovznovadriver/openvz/network_drivers/tc.py deleted file mode 100644 index 0cb8a32..0000000 --- a/ovznovadriver/openvz/network_drivers/tc.py +++ /dev/null @@ -1,284 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. -from Cheetah import Template -from nova.conductor import api -from nova import context -from nova import exception -from nova.openstack.common import lockutils -from nova.openstack.common import log as logging -from ovznovadriver.localization import _ -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg -import random - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.network_drivers.tc') - -global _ovz_tc_available_ids -global _ovz_tc_inflight_ids -_ovz_tc_available_ids = None -_ovz_tc_inflight_ids = None - - -class OVZTcRules(object): - # Set our class variables if they don't exist - # TODO(imsplitbit): figure out if there is a more pythonic way to do this - if not _ovz_tc_available_ids: - _ovz_tc_available_ids = list() - - if not _ovz_tc_inflight_ids: - _ovz_tc_inflight_ids = list() - - def __init__(self): - """ - This class is used to return TC rulesets for both a host and guest for - use with host and guest startup and shutdown. - """ - self.conductor = api.API() - - if not len(OVZTcRules._ovz_tc_available_ids): - LOG.debug(_('Available_ids is empty, filling it with numbers')) - OVZTcRules._ovz_tc_available_ids = [ - i for i in range(1, CONF.ovz_tc_id_max) - ] - - # do an initial clean of the available ids - self._remove_used_ids() - LOG.debug( - _('OVZTcRules thinks ovz_tc_host_slave_device is set to %s') - % CONF.ovz_tc_host_slave_device) - - def instance_info(self, instance_id, address, vz_iface): - """ - Use this method when creating or resizing an instance. It will - generate a new tc ruleset - - :param instance_id: Instance to generate the rules for - :param address: IP address for the instance - :param vz_iface: interface on the hosts bridge that is associated with - the instance - """ - # TODO(jcru) figure out if there is a case for no instance_id else - # take it out - if not instance_id: - self.instance_type = dict() - self.instance_type['memory_mb'] = 2048 - else: - admin_context = context.get_admin_context() - self.instance = self.conductor.instance_get( - admin_context, instance_id) - self.instance_type = self.conductor.instance_type_get( - admin_context, self.instance['instance_type_id']) - LOG.debug(_('CT TC address: %s') % address) - - self.address = address - self.vz_iface = vz_iface - - # TODO(jcru) Ideally wish to move this to resources.py - # check under instance_type/flavor extra_specs to see if bandwidth has - # been predefined for flavor - extra_specs = self.instance_type.get("extra_specs", {}) - self.bandwidth = extra_specs.get("vz_bandwidth", None) - if not self.bandwidth: - LOG.debug(_('No (vz_bandwidth) extra_specs key/value defined for ' - 'flavor id (%s)') % self.instance_type['flavorid']) - # Calculate the bandwidth total by figuring out how many units we - # have - self.bandwidth = int(round(self.instance_type['memory_mb'] / - CONF.ovz_memory_unit_size)) * CONF.ovz_tc_mbit_per_unit - else: - int(self.bandwidth) - - LOG.debug(_('Allotted bandwidth: %s') % self.bandwidth) - - self.tc_id = self._get_instance_tc_id() - if not self.tc_id: - LOG.debug(_('No preassigned tc_id for %s, getting a new one') % - instance_id) - self.tc_id = self.get_id() - - self._save_instance_tc_id() - LOG.debug(_('Saved the tc_id in the database for the instance')) - - @lockutils.synchronized('get_id_lock', 'openvz-') - def get_id(self): - """ - Uses nova utils decorator @lockutils.synchronized to make sure that we - do not return duplicate available ids. This will return a random id - number between 1 and 9999 which are the limits of TC. - """ - self._remove_used_ids() - LOG.debug(_('Pulling new TC id')) - tc_id = self._pull_id() - LOG.debug(_('TC id %s pulled, testing for dupe') % tc_id) - while tc_id in OVZTcRules._ovz_tc_inflight_ids: - LOG.debug(_('TC id %s inflight already, pulling another') % tc_id) - tc_id = self._pull_id() - LOG.debug(_('TC id %s pulled, testing for dupe') % tc_id) - LOG.debug(_('TC id %s pulled, verified unique') % tc_id) - self._reserve_id(tc_id) - return tc_id - - def container_start(self): - template = self._load_template('tc_container_start.template') - search_list = { - 'prio': self.tc_id, - 'host_iface': CONF.ovz_tc_host_slave_device, - 'vz_iface': self.vz_iface, - 'bandwidth': self.bandwidth, - 'vz_address': self.address, - 'line_speed': CONF.ovz_tc_max_line_speed - } - ovz_utils.save_instance_metadata(self.instance['id'], - 'tc_id', self.tc_id, - fail_on_dupe_key=False) - return self._fill_template(template, search_list).splitlines() - - def container_stop(self): - template = self._load_template('tc_container_stop.template') - search_list = { - 'prio': self.tc_id, - 'host_iface': CONF.ovz_tc_host_slave_device, - 'vz_iface': self.vz_iface, - 'bandwidth': self.bandwidth, - 'vz_address': self.address - } - ovz_utils.save_instance_metadata(self.instance['id'], - 'tc_id', self.tc_id, - fail_on_dupe_key=False) - return self._fill_template(template, search_list).splitlines() - - def host_start(self): - template = self._load_template('tc_host_start.template') - search_list = { - 'host_iface': CONF.ovz_tc_host_slave_device, - 'line_speed': CONF.ovz_tc_max_line_speed - } - return self._fill_template(template, search_list).splitlines() - - def host_stop(self): - template = self._load_template('tc_host_stop.template') - search_list = { - 'host_iface': CONF.ovz_tc_host_slave_device - } - return self._fill_template(template, search_list).splitlines() - - def _load_template(self, template_name): - """ - read and return the template file - """ - full_template_path = '%s/%s' % ( - CONF.ovz_tc_template_dir, template_name) - full_template_path = os.path.abspath(full_template_path) - try: - LOG.debug(_('Opening template file: %s') % full_template_path) - template_file = open(full_template_path).read() - LOG.debug(_('Template file opened successfully')) - return template_file - except Exception as err: - LOG.error(_('Unable to open template: %s') % full_template_path) - raise exception.FileNotFound(err) - - def _fill_template(self, template, search_list): - """ - Take the vars in search_list and fill out template - """ - return str(Template.Template(template, searchList=[search_list])) - - def _pull_id(self): - """ - Pop a random id from the list of available ids for tc rules - """ - return OVZTcRules._ovz_tc_available_ids[random.randint( - 0, len(OVZTcRules._ovz_tc_available_ids) - 1)] - - def _list_existing_ids(self): - LOG.debug(_('Attempting to list existing IDs')) - out = ovz_utils.execute('tc', 'filter', 'show', 'dev', - CONF.ovz_tc_host_slave_device, - run_as_root=True) - ids = list() - for line in out.splitlines(): - line = line.split() - if line[0] == 'filter': - tc_id = int(line[6]) - if tc_id not in ids: - ids.append(int(tc_id)) - - # get the metadata for instances from the database - # this will provide us with any ids of instances that aren't - # currently running so that we can remove active and provisioned - # but inactive ids from the available list - instances_metadata = ovz_utils.read_all_instance_metadata() - LOG.debug(_('Instances metadata: %s') % instances_metadata) - if instances_metadata: - for instance_id, meta in instances_metadata.iteritems(): - tc_id = meta.get('tc_id') - if tc_id: - if tc_id not in ids: - LOG.debug( - _('TC id "%(tc_id)s" for instance ' - '"%(instance_id)s" found') % locals()) - ids.append(int(tc_id)) - return ids - - def _reserve_id(self, tc_id): - """ - This removes the id from the _ovz_tc_available_ids and adds it to the - _ovz_tc_inflight_ids - """ - LOG.debug(_('Beginning reservation process')) - OVZTcRules._ovz_tc_inflight_ids.append(tc_id) - LOG.debug(_('Added id "%s" to _ovz_tc_inflight_ids') % tc_id) - OVZTcRules._ovz_tc_available_ids.remove(tc_id) - LOG.debug(_('Removed id "%s" from _ovz_tc_available_ids') % tc_id) - - def _remove_used_ids(self): - """ - Clean ids that are currently provisioned on the host from the - list of _ovz_tc_available_ids - """ - LOG.debug(_('Beginning cleanup of used ids')) - used_ids = self._list_existing_ids() - LOG.debug(_('Used ids found, removing from _ovz_tc_available_ids')) - for tc_id in used_ids: - if tc_id in OVZTcRules._ovz_tc_available_ids: - OVZTcRules._ovz_tc_available_ids.remove(tc_id) - LOG.debug(_('Removed all ids in use')) - - def _save_instance_tc_id(self): - """ - Save the tc id in the instance metadata in the database - """ - ovz_utils.save_instance_metadata(self.instance['id'], 'tc_id', - self.tc_id, fail_on_dupe_key=False) - - def _get_instance_tc_id(self): - """ - Look up instance metadata in the db and see if there is already - a tc_id for the instance - """ - instance_metadata = ovz_utils.read_instance_metadata( - self.instance['id']) - LOG.debug(_('Instances metadata: %s') % instance_metadata) - if instance_metadata: - tc_id = instance_metadata.get('tc_id') - LOG.debug( - _('TC id for instance %(instance_id)s is %(tc_id)s') % - {'instance_id': self.instance['id'], 'tc_id': tc_id}) - return tc_id diff --git a/ovznovadriver/openvz/network_drivers/templates/tc_container_start.template b/ovznovadriver/openvz/network_drivers/templates/tc_container_start.template deleted file mode 100644 index 1233560..0000000 --- a/ovznovadriver/openvz/network_drivers/templates/tc_container_start.template +++ /dev/null @@ -1,8 +0,0 @@ -tc qdisc add dev ${vz_iface} root handle 1: htb default 10 -tc class add dev ${vz_iface} parent 1: classid 1:1 htb rate ${line_speed}mbit ceil ${line_speed}mbit burst 15k -tc class add dev ${vz_iface} parent 1:1 classid 1:${prio} htb rate ${bandwidth}mbit ceil ${bandwidth}mbit burst 15k -tc qdisc add dev ${vz_iface} parent 1:${prio} handle ${prio}: sfq perturb 10 -tc filter replace dev ${vz_iface} protocol ip parent 1: prio ${prio} u32 match ip dst ${vz_address} flowid 1:${prio} -tc class add dev ${host_iface} parent 1:1 classid 1:${prio} htb rate ${bandwidth}mbit ceil ${bandwidth}mbit burst 15k -tc qdisc add dev ${host_iface} parent 1:${prio} handle ${prio}: sfq perturb 10 -tc filter replace dev ${host_iface} protocol ip parent 1: prio ${prio} u32 match ip src ${vz_address} flowid 1:${prio} \ No newline at end of file diff --git a/ovznovadriver/openvz/network_drivers/templates/tc_container_stop.template b/ovznovadriver/openvz/network_drivers/templates/tc_container_stop.template deleted file mode 100644 index a59143c..0000000 --- a/ovznovadriver/openvz/network_drivers/templates/tc_container_stop.template +++ /dev/null @@ -1,6 +0,0 @@ -tc filter del dev ${host_iface} protocol ip parent 1:0 prio ${prio} -tc class del dev ${host_iface} parent 1:1 classid 1:${prio} htb rate ${bandwidth}mbit -tc qdisc delete dev ${host_iface} parent 1:${prio} handle ${prio} -tc filter del dev ${vz_iface} protocol ip parent 1:0 prio ${prio} -tc class del dev ${vz_iface} parent 1:1 classid 1:${prio} htb rate ${bandwidth}mbit -tc qdisc delete dev ${vz_iface} parent 1:${prio} handle ${prio} \ No newline at end of file diff --git a/ovznovadriver/openvz/network_drivers/templates/tc_host_start.template b/ovznovadriver/openvz/network_drivers/templates/tc_host_start.template deleted file mode 100644 index f20d25b..0000000 --- a/ovznovadriver/openvz/network_drivers/templates/tc_host_start.template +++ /dev/null @@ -1,5 +0,0 @@ -# Outgoing traffic control -# Should only be run once at setup or all rules are wiped -tc qdisc del dev ${host_iface} root -tc qdisc add dev ${host_iface} root handle 1: htb default 10 -tc class add dev ${host_iface} parent 1: classid 1:1 htb rate ${line_speed}mbit ceil ${line_speed}mbit burst 15k \ No newline at end of file diff --git a/ovznovadriver/openvz/network_drivers/templates/tc_host_stop.template b/ovznovadriver/openvz/network_drivers/templates/tc_host_stop.template deleted file mode 100644 index c1c24f2..0000000 --- a/ovznovadriver/openvz/network_drivers/templates/tc_host_stop.template +++ /dev/null @@ -1 +0,0 @@ -tc qdisc del dev ${host_iface} root \ No newline at end of file diff --git a/ovznovadriver/openvz/resources.py b/ovznovadriver/openvz/resources.py deleted file mode 100644 index 91cb9c6..0000000 --- a/ovznovadriver/openvz/resources.py +++ /dev/null @@ -1,405 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2014 Rackspace -# All Rights Reserved. -# -# 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. - -import math - -from ovznovadriver.openvz import utils as ovz_utils -from ovznovadriver.openvz.file_ext import boot as ovzboot -from ovznovadriver.openvz.file_ext import shutdown as ovzshutdown -from ovznovadriver.openvz.network_drivers import tc as ovztc -from ovznovadriver.localization import _ - -from oslo.config import cfg - -from nova.openstack.common import log as logging - -__openvz_resource_opts = [ - cfg.BoolOpt('ovz_use_cpuunit', - default=True, - help='Use OpenVz cpuunits for guaranteed minimums'), - cfg.BoolOpt('ovz_use_cpulimit', - default=True, - help='Use OpenVz cpulimit for maximum cpu limits'), - cfg.FloatOpt('ovz_cpulimit_overcommit_multiplier', - default=1.0, - help='Multiplier for cpulimit to facilitate over ' - 'committing cpu resources'), - cfg.BoolOpt('ovz_use_cpus', - default=True, - help='Use OpenVz cpus for max cpus ' - 'available to the container'), - cfg.BoolOpt('ovz_use_ioprio', - default=True, - help='Use IO fair scheduling'), - cfg.BoolOpt('ovz_use_ubc', - default=False, - help='Use OpenVz User BeanCounters memory management model ' - 'instead of vswap'), - cfg.IntOpt('ovz_file_descriptors_per_unit', - default=4096, - help='Max open file descriptors per memory unit'), - cfg.IntOpt('ovz_memory_unit_size', - default=512, - help='Unit size in MB'), - cfg.BoolOpt('ovz_use_disk_quotas', - default=True, - help='Use disk quotas to contain disk usage'), - cfg.StrOpt('ovz_disk_space_increment', - default='G', - help='Disk subscription increment'), - cfg.FloatOpt('ovz_disk_space_oversub_percent', - default=1.10, - help='Local disk over subscription percentage'), - cfg.IntOpt('ovz_kmemsize_percent_of_memory', - default=20, - help='Percent of memory of the container to allow to be used ' - 'by the kernel'), - cfg.IntOpt('ovz_kmemsize_barrier_differential', - default=10, - help='Difference of kmemsize barrier vs limit'), - cfg.StrOpt('ovz_default_config', - default='basic', - help='Default config file to apply if no config is set for ' - 'flavor extra_specs'), - ] - -CONF = cfg.CONF -CONF.register_opts(__openvz_resource_opts) - -LOG = logging.getLogger(__name__) - - -class VZResourceManager(object): - """Manage OpenVz container resources - - The purpose of this class is meant to decide/calculate vz resource configs - and apply them through the Container class""" - - # TODO (jcru) make this a config? - # OpenVz sets the upper limit of cpuunits to 500000 - MAX_CPUUNITS = 500000 - - def __init__(self, virtapi): - """Requires virtapi (api to conductor) to get flavor info""" - self.virtapi = virtapi - # TODO (jcru) replace dict (self.utility) with self.cpulimit? - self.utility = dict() - - def _get_flavor_info(self, context, flavor_id): - """Get the latest flavor info which contains extra_specs""" - # instnace_type refers to the flavor (what you see in flavor list) - return self.virtapi.flavor_get(context, flavor_id) - - def _calc_pages(self, instance_memory, block_size=4096): - """ - Returns the number of pages for a given size of storage/memory - """ - return ((int(instance_memory) * 1024) * 1024) / block_size - - def _percent_of_resource(self, instance_memory): - """ - In order to evenly distribute resources this method will calculate a - multiplier based on memory consumption for the allocated container and - the overall host memory. This can then be applied to the cpuunits in - self.utility to be passed as an argument to the self._set_cpuunits - method to limit cpu usage of the container to an accurate percentage of - the host. This is only done on self.spawn so that later, should - someone choose to do so, they can adjust the container's cpu usage - up or down. - """ - cont_mem_mb = ( - float(instance_memory) / float(ovz_utils.get_memory_mb_total())) - - # We shouldn't ever have more than 100% but if for some unforseen - # reason we do, lets limit it to 1 to make all of the other - # calculations come out clean. - if cont_mem_mb > 1: - LOG.error(_('_percent_of_resource came up with more than 100%')) - return 1.0 - else: - return cont_mem_mb - - def get_cpulimit(self): - """ - Fetch the total possible cpu processing limit in percentage to be - divided up across all containers. This is expressed in percentage - being added up by logical processor. If there are 24 logical - processors then the total cpulimit for the host node will be - 2400. - """ - self.utility['CPULIMIT'] = ovz_utils.get_vcpu_total() * 100 - LOG.debug(_('Updated cpulimit in utility')) - LOG.debug( - _('Current cpulimit in utility: %s') % self.utility['CPULIMIT']) - - def get_cpuunits_usage(self): - """ - Use openvz tools to discover the total used processing power. This is - done using the vzcpucheck -v command. - - Run the command: - - vzcpucheck -v - - If this fails to run an exception should not be raised as this is a - soft error and results only in the lack of knowledge of what the - current cpuunit usage of each container. - """ - out = ovz_utils.execute( - 'vzcpucheck', '-v', run_as_root=True, raise_on_error=False) - if out: - for line in out.splitlines(): - line = line.split() - if len(line) > 0: - if line[0].isdigit(): - LOG.debug(_('Usage for CTID %(id)s: %(usage)s') % - {'id': line[0], 'usage': line[1]}) - if int(line[0]) not in self.utility.keys(): - self.utility[int(line[0])] = dict() - self.utility[int(line[0])] = int(line[1]) - - def configure_container_resources(self, context, container, - requested_flavor_id): - instance_type = self._get_flavor_info(context, requested_flavor_id) - - self._setup_memory(container, instance_type) - self._setup_file_limits(container, instance_type) - self._setup_cpu(container, instance_type) - self._setup_io(container, instance_type) - self._setup_disk_quota(container, instance_type) - - # TODO(jcru) normally we would pass a context and requested flavor as - # configure_container_resources but we look up instance_type within tc - # code. Ideally all of the networking setup would happen here - def configure_container_network(self, container, network_info, - is_migration=False): - self._generate_tc_rules(container, network_info, is_migration) - - def apply_config(self, context, container, requested_flavor_id): - """In order to succesfully apply a config file the file must exist - within /etc/vz/config if just the file name is passed (e.g. samples) - or the full file path must be specified - - It is possible to not define a config file which in that case nothing - is applied. - """ - instance_type = self._get_flavor_info(context, requested_flavor_id) - instance_type_extra_specs = instance_type.get('extra_specs', {}) - # TODO(jcru) handle default config for both UBC and Vswap - config_file = instance_type_extra_specs.get("vz_config_file", - CONF.ovz_default_config) - if config_file: - container.apply_config(config_file) - - def _setup_memory(self, container, instance_type): - """Decides on what VZ memory model to use. - By default we use Vswap. If User Beancounters (UBC) is desired, enable - through config. - """ - if CONF.ovz_use_ubc: - self._setup_memory_with_ubc(instance_type, container) - return - - self._setup_memory_with_vswap(container, instance_type) - - def _setup_memory_with_ubc(self, container, instance_type): - instance_memory_mb = int(instance_type.get('memory_mb')) - - instance_memory_bytes = ((instance_memory_mb * 1024) * 1024) - instance_memory_pages = self._calc_pages(instance_memory_mb) - - # Now use the configuration CONF to calculate the appropriate - # values for both barrier and limit. - kmem_limit = int(instance_memory_mb * ( - float(CONF.ovz_kmemsize_percent_of_memory) / 100.0)) - kmem_barrier = int(kmem_limit * ( - float(CONF.ovz_kmemsize_barrier_differential) / 100.0)) - - container.set_vmguarpages(instance_memory_pages) - container.set_privvmpages(instance_memory_pages) - container.set_kmemsize(kmem_barrier, kmem_limit) - - def _setup_memory_with_vswap(self, container, instance_type): - memory = int(instance_type.get('memory_mb')) - swap = instance_type.get('swap', 0) - - # Memory should be in MB - memory = "%sM" % memory - # Swap should be in GB - swap = "%sG" % swap - container.set_vswap(memory, swap) - - def _setup_file_limits(self, container, instance_type): - instance_memory_mb = int(instance_type.get('memory_mb')) - memory_unit_size = int(CONF.ovz_memory_unit_size) - max_fd_per_unit = int(CONF.ovz_file_descriptors_per_unit) - max_fd = int(instance_memory_mb / memory_unit_size) * max_fd_per_unit - - container.set_numfiles(max_fd) - container.set_numflock(max_fd) - - # TODO(jcru) overide caclulated values? - def _setup_cpu(self, container, instance_type): - """ - """ - instance_memory_mb = instance_type.get('memory_mb') - instance_type_extra_specs = instance_type.get('extra_specs', {}) - percent_of_resource = self._percent_of_resource(instance_memory_mb) - - if CONF.ovz_use_cpuunit: - LOG.debug(_('Reported cpuunits %s') % self.MAX_CPUUNITS) - LOG.debug(_('Reported percent of resource: %s') % percent_of_resource) - - units = int(round(self.MAX_CPUUNITS * percent_of_resource)) - - if units > self.MAX_CPUUNITS: - units = self.MAX_CPUUNITS - - container.set_cpuunits(units) - - if CONF.ovz_use_cpulimit: - # Check if cpulimit for flavor is predefined in flavors extra_specs - cpulimit = instance_type_extra_specs.get('vz_cpulimit', None) - - if not cpulimit: - cpulimit = int(round( - (self.utility['CPULIMIT'] * percent_of_resource) * - CONF.ovz_cpulimit_overcommit_multiplier)) - else: - cpulimit = int(cpulimit) - - if cpulimit > self.utility['CPULIMIT']: - LOG.warning(_("The cpulimit that was calculated or predefined " - "(%s) is to high based on the CPULIMIT (%s)") % - (cpulimit, self.utility['CPULIMIT'])) - LOG.warning(_("Using CPULIMIT instead.")) - cpulimit = self.utility['CPULIMIT'] - - container.set_cpulimit(cpulimit) - - if CONF.ovz_use_cpus: - vcpus = int(instance_type.get('vcpus')) - LOG.debug(_('VCPUs: %s') % vcpus) - utility_cpus = self.utility['CPULIMIT'] / 100 - - if vcpus > utility_cpus: - LOG.debug( - _('OpenVZ thinks vcpus "%(vcpus)s" ' - 'is greater than "%(utility_cpus)s"') % locals()) - # We can't set cpus higher than the number of actual logical cores - # on the system so set a cap here - vcpus = self.utility['CPULIMIT'] / 100 - - LOG.debug(_('VCPUs: %s') % vcpus) - container.set_cpus(vcpus) - - def _setup_io(self, container, instance_type): - # The old algorithm made it impossible to distinguish between a - # 512MB container and a 2048MB container for IO priority. We will - # for now follow a simple map to create a more non-linear - # relationship between the flavor sizes and their IO priority groups - - # The IO priority of a container is grouped in 1 of 8 groups ranging - # from 0 to 7. We can calculate an appropriate value by finding out - # how many ovz_memory_unit_size chunks are in the container's memory - # allocation and then using python's math library to solve for that - # number's logarithm. - if CONF.ovz_use_ioprio: - instance_memory_mb = instance_type.get('memory_mb') - num_chunks = int(int(instance_memory_mb) / CONF.ovz_memory_unit_size) - - try: - ioprio = int(round(math.log(num_chunks, 2))) - except ValueError: - ioprio = 0 - - if ioprio > 7: - # ioprio can't be higher than 7 so set a ceiling - ioprio = 7 - - container.set_ioprio(ioprio) - - def _setup_disk_quota(self, container, instance_type): - if CONF.ovz_use_disk_quotas: - instance_root_gb = instance_type.get('root_gb') - - soft_limit = int(instance_root_gb) - hard_limit = int(soft_limit * CONF.ovz_disk_space_oversub_percent) - - # Now set the increment of the limit. I do this here so that I don't - # have to do this in every line above. - soft_limit = '%s%s' % (soft_limit, CONF.ovz_disk_space_increment) - hard_limit = '%s%s' % (hard_limit, CONF.ovz_disk_space_increment) - - container.set_diskspace(soft_limit, hard_limit) - - # TODO(jcru) move more of tc logic into here ? - def _generate_tc_rules(self, container, network_info, is_migration=False): - """ - Utility method to generate tc info for instances that have been - resized and/or migrated - """ - LOG.debug(_('Setting network sizing')) - boot_file = ovzboot.OVZBootFile(container.ovz_id, 755) - shutdown_file = ovzshutdown.OVZShutdownFile(container.ovz_id, 755) - - if not is_migration: - with shutdown_file: - LOG.debug(_('Cleaning TC rules for %s') % container.nova_id) - shutdown_file.read() - shutdown_file.run_contents(raise_on_error=False) - - # On resize we throw away existing tc_id and make a new one - # because the resize *could* have taken place on a different host - # where the tc_id is already in use. - meta = ovz_utils.read_instance_metadata(container.nova_id) - tc_id = meta.get('tc_id', None) - if tc_id: - ovz_utils.remove_instance_metadata_key(container.nova_id, 'tc_id') - - with shutdown_file: - shutdown_file.set_contents(list()) - - with boot_file: - boot_file.set_contents(list()) - - LOG.debug(_('Getting network dict for: %s') % container.uuid) - interfaces = ovz_utils.generate_network_dict(container, - network_info) - for net_dev in interfaces: - LOG.debug(_('Adding tc rules for: %s') % - net_dev['vz_host_if']) - tc = ovztc.OVZTcRules() - tc.instance_info(container.nova_id, net_dev['address'], - net_dev['vz_host_if']) - with boot_file: - boot_file.append(tc.container_start()) - - with shutdown_file: - shutdown_file.append(tc.container_stop()) - - with boot_file: - if not is_migration: - # during migration, the instance isn't yet running, so it'll - # just spew errors to attempt to apply these rules before then - LOG.debug(_('Running TC rules for: %s') % container.ovz_id) - boot_file.run_contents() - LOG.debug(_('Saving TC rules for: %s') % container.ovz_id) - boot_file.write() - - with shutdown_file: - shutdown_file.write() diff --git a/ovznovadriver/openvz/utils.py b/ovznovadriver/openvz/utils.py deleted file mode 100644 index 8f9af40..0000000 --- a/ovznovadriver/openvz/utils.py +++ /dev/null @@ -1,610 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -import multiprocessing -from nova.conductor import api -from nova import context -from nova import exception -from nova.openstack.common import log as logging -from nova.openstack.common import processutils -from ovznovadriver.localization import _ -from nova import utils -import os -from oslo.config import cfg -import platform -import re -import sys -import uuid - -CONF = cfg.CONF -LOG = logging.getLogger('ovznovadriver.openvz.utils') -conductor = api.API() - - -def execute(*cmd, **kwargs): - """ - This is a wrapper for utils.execute so as to reduce the amount of - duplicated code in the driver. - """ - if 'raise_on_error' in kwargs: - raise_on_error = kwargs.pop('raise_on_error') - else: - raise_on_error = True - - try: - out, err = utils.execute(*cmd, **kwargs) - if out: - LOG.debug(_('Stdout from %(command)s: %(out)s') % - {'command': cmd[0], 'out': out}) - if err: - LOG.debug(_('Stderr from %(command)s: %(out)s') % - {'command': cmd[0], 'out': err}) - return out - except processutils.ProcessExecutionError as err: - msg = (_('Stderr from %(command)s: %(out)s') % - {'command': cmd[0], 'out': err}) - if raise_on_error: - LOG.error(msg) - raise exception.InstanceUnacceptable( - _('Error running %(command)s: %(out)s') % - {'command': cmd[0], 'out': err}) - else: - LOG.warn(msg) - return None - - -def mkfs(path, fs, fs_uuid=None, fs_label=None): - """Format a file or block device - - :param fs: Filesystem type (examples include 'ext3', 'ext4' - 'btrfs', etc.) - :param path: Path to file or block device to format - :param fs_uuid: Volume uuid to use - :param fs_label: Volume label to use - """ - if not fs_uuid: - fs_uuid = str(uuid.uuid4()) - - args = ['mkfs', '-F', '-t', fs] - if fs_uuid: - args.extend(['-U', fs_uuid]) - if fs_label: - args.extend(['-L', fs_label]) - args.append(path) - LOG.debug(_('Mkfs command: %s') % args) - execute(*args, run_as_root=True) - - -def get_fs_uuid(device): - """ - Because we may need to operate on a volume by it's uuid - we need a way to see if a filesystem has a uuid on it - """ - LOG.debug(_('Getting FS UUID for: %s') % device) - out = execute('blkid', '-o', 'value', '-s', 'UUID', device, - run_as_root=True, raise_on_error=False) - if out: - LOG.debug(_('Found something in get_fs_uuid')) - for line in out.split('\n'): - line = line.strip() - LOG.debug(_('Examining line: %s') % line) - result = re.search( - '[a-f0-9]{8}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{12}', - line) - if result: - LOG.debug( - _('Found the FS UUID for: %(device)s It is: %(uuid)s') % - {'device': device, 'uuid': result.group(0)}) - return result.group(0) - return None - - -def get_vcpu_total(): - """Get vcpu number of physical computer. - - :returns: the number of cpu core. - - """ - LOG.debug(_('Getting cpu count')) - # On certain platforms, this will raise a NotImplementedError. - try: - cpu_count = multiprocessing.cpu_count() - LOG.debug(_('Got cpu count: %s') % cpu_count) - return cpu_count - - except NotImplementedError: - LOG.warn(_("Cannot get the number of cpu, because this " - "function is not implemented for this platform. " - "This error can be safely ignored for now.")) - return 0 - - -def get_cpuinfo(): - """ - Gather detailed statistics on the host's cpus - """ - - if sys.platform.upper() not in ['LINUX2', 'LINUX3']: - return 0 - - cpuinfo = dict() - cpuinfo['features'] = list() - - # Gather the per core/hyperthread info for accumulation - for line in open('/proc/cpuinfo').readlines(): - # Do some cleaning up to make searching for keys easier - line = line.split(':') - line[0] = line[0].strip().replace(' ', '_') - if len(line) > 1: - line[1] = line[1].strip() - - if line[0] == 'vendor_id': - cpuinfo['vendor'] = line[1] - - if line[0] == 'model_name': - cpuinfo['model'] = line[1] - - if line[0] == 'flags': - cpuinfo['features'] += line[1].split() - - cpuinfo['arch'] = platform.uname()[4] - - # dedupe the features - cpuinfo['features'] = list(set(cpuinfo['features'])) - - return cpuinfo - - -def get_iscsi_initiator(): - """ - This is a basic implementation of the iscsi stuff needed for external - volumes. This should live in a utility module when the openvz driver is - broken up. - """ - # code borrowed from libvirt utils - contents = utils.read_file_as_root('/etc/iscsi/initiatorname.iscsi') - for l in contents.split('\n'): - if l.startswith('InitiatorName='): - return l[l.index('=') + 1:].strip() - - -def get_cpuunits_capability(): - """ - Use openvz tools to discover the total processing capability of the - host node. This is done using the vzcpucheck utility. - - Run the command: - - vzcpucheck - - If this fails to run an exception is raised because the output of this - method is required to calculate the overall bean count available on the - host to be carved up for guests to use. - """ - result = {} - out = execute('vzcpucheck', run_as_root=True) - for line in out.splitlines(): - line = line.split() - if len(line) > 0: - if line[0] == 'Power': - LOG.debug(_('Power of host: %s') % line[4]) - result['total'] = int(line[4]) - elif line[0] == 'Current': - LOG.debug(_('Current cpuunits subscribed: %s') % line[3]) - result['subscribed'] = int(line[3]) - - if len(result.keys()) == 2: - return result - else: - raise exception.InvalidCPUInfo( - _("Cannot determine the CPUUNITS for host")) - - -def get_vcpu_used(): - """ - OpenVz doesn't have the concept of VCPUs but we can approximate - what they would be by looking at the percentage of subscribed - cpuunits. - - :returns: The total number of vcpu that currently used. - - """ - - cpuunits = get_cpuunits_capability() - cpus = get_vcpu_total() - pct_cpuunits_used = float(cpuunits['subscribed']) / cpuunits['total'] - return int(cpus * pct_cpuunits_used) - - -def get_memory_mb_total(): - """Get the total memory size(MB) of physical computer. - - :returns: the total amount of memory(MB). - - """ - - if sys.platform.upper() not in ['LINUX2', 'LINUX3']: - return 1 - - meminfo = open('/proc/meminfo').read().split() - idx = meminfo.index(u'MemTotal:') - # transforming kb to mb. - return int(meminfo[idx + 1]) / 1024 - - -def get_local_gb(path): - """ - Get the total hard drive space at - """ - - hddinfo = os.statvfs(path) - total = hddinfo.f_frsize * hddinfo.f_blocks - free = hddinfo.f_frsize * hddinfo.f_bavail - used = hddinfo.f_frsize * (hddinfo.f_blocks - hddinfo.f_bfree) - return {'total': total, 'free': free, 'used': used} - - -def get_local_gb_total(): - """ - Get the total hdd size(GB) of physical computer. - - :returns: - The total amount of HDD(GB). - Note that this value shows a partition where - OVZ_VE_PRIVATE_DIR is. - - """ - - return get_local_gb(CONF.ovz_ve_private_dir)['total'] / (1024 ** 3) - - -def get_local_gb_used(): - """ - Get the total used disk space on the host computer. - - :returns: - The total amount of HDD(GB) - Note that this value show a partition where - OVZ_VE_PRIVATE_DIR is. - """ - - return get_local_gb(CONF.ovz_ve_private_dir)['used'] / (1024 ** 3) - - -def get_hypervisor_type(): - """ - Just return the type of hypervisor we are using. This will always - be 'openvz' - """ - - return 'openvz' - - -def get_hypervisor_version(): - """ - Since the version of the hypervisor is really determined by the kernel - it is running lets just return that for version. I don't think it - matters at this point and this is the most accurate representation of - what *version* we are running. - """ - - return platform.uname()[2] - - -def make_dir(path): - """ - This is the method that actually creates directories. This is used by - make_path and can be called directly as a utility to create - directories. - - Run the command: - - mkdir -p - - If this doesn't run an exception is raised as this path creation is - required to ensure that other file operations are successful. Such - as creating the path for a file yet to be created. - """ - if not os.path.exists(path): - execute('mkdir', '-p', path, run_as_root=True) - - -def delete_path(path): - """ - After a volume has been detached and the mount statements have been - removed from the mount configuration for a container we want to remove - the paths created on the host system so as not to leave orphaned files - and directories on the system. - - This runs a command like: - sudo rmdir /mnt/100/var/lib/mysql - """ - try: - execute('rmdir', path, run_as_root=True) - return True - except exception.InstanceUnacceptable: - return False - - -def set_permissions(filename, permissions): - """ - Because nova runs as an unprivileged user we need a way to mangle - permissions on files that may be owned by root for manipulation - - Run the command: - - chmod - - If this doesn't run an exception is raised because the permissions not - being set to what the application believes they are set to can cause - a failure of epic proportions. - """ - execute('chmod', permissions, filename, run_as_root=True) - - -def format_system_metadata(metadata): - """ - System metadata returned by conductor contains data that is irrelevant to - OpenVz and the nova driver. This method sanitizes this information down - to key / value pairs in a list - - :param metadata: instance['system_metadata'] - :return: dict - """ - if isinstance(metadata, dict): - return metadata - fmt_meta = dict() - if isinstance(metadata, list): - for item in metadata: - meta_item = dict() - for key, value in item.iteritems(): - if key in ['key', 'value']: - meta_item[key] = value - fmt_meta[meta_item['key']] = meta_item['value'] - return fmt_meta - - -def save_instance_metadata(instance_id, key, value, fail_on_dupe_key=False): - """ - Simple wrapper for saving data to the db as metadata for an instance - - :param instance_id: Instance id to add metadata to - :param key: Key to save to db - :param value: Value of key to save to db - """ - LOG.debug( - _('Beginning saving instance metadata for ' - '%(instance_id)s: {%(key)s: %(value)s}') % locals()) - admin_context = context.get_admin_context() - LOG.debug(_('Got admin context')) - try: - instance = conductor.instance_get(admin_context, instance_id) - LOG.debug(_('Fetched instance: %s') % instance) - LOG.debug(_('Fixing system_metadata')) - sysmeta = format_system_metadata(instance['system_metadata']) - if key in sysmeta: - if fail_on_dupe_key: - raise KeyError(_('Key %(key)s is set already') % locals()) - sysmeta[key] = value - conductor.instance_update( - admin_context, instance['uuid'], system_metadata=sysmeta) - LOG.debug(_('Updated instance metadata')) - except exception.InstanceNotFound as err: - LOG.error(_('Instance not in the database: %s') % instance_id) - LOG.error(_('Consistency check is needed, orphaned instance: %s') % - instance_id) - - -def read_instance_metadata(instance_id): - """ - Read the metadata in the database for a given instance - - :param instance_id: Instance to read all metadata for from the db - :returns: dict() - """ - LOG.debug(_('Beginning read_instance_metadata: %s') % instance_id) - admin_context = context.get_admin_context() - LOG.debug(_('Got admin context for db access')) - try: - instance = conductor.instance_get(admin_context, instance_id) - LOG.debug(_('Fetched instance')) - LOG.debug( - _('Results from read_instance_metadata: %s') % - instance['system_metadata']) - return format_system_metadata(instance['system_metadata']) - except exception.InstanceNotFound: - LOG.error(_('Instance not in the database: %s') % instance_id) - LOG.error(_('Consistency check is needed, orphaned instance: %s') % - instance_id) - return dict() - - -def read_all_instance_metadata(): - """ - Fetch a list of all instance ids on the local host and for each get - the associated metadata and return it in a dictionary - - :returns dict(): - """ - from ovznovadriver.openvz.container import OvzContainers - instances_metadata = {} - containers = OvzContainers.list() - for container in containers: - instances_metadata[container.nova_id] = read_instance_metadata( - container.nova_id) - - return instances_metadata - - -def remove_instance_metadata_key(instance_id, key): - """ - Remove a specific key from an instance's metadata - """ - LOG.debug(_('Getting an admin context for remove_instance_metadata_key')) - admin_context = context.get_admin_context() - LOG.debug(_('Got admin context, fetching instance ref')) - instance = conductor.instance_get(admin_context, instance_id) - LOG.debug(_('Got instance ref, beginning deletion of metadata')) - sysmeta = format_system_metadata(instance['system_metadata']) - if key in sysmeta: - LOG.debug(_('Key %s exists in system_metadata') % key) - sysmeta.pop(key) - conductor.instance_update( - admin_context, instance['uuid'], system_metadata=sysmeta) - return True - else: - LOG.debug(_('Key %s does not exist in system_metadata') % key) - return False - - -def remove_instance_metadata(instance_id): - """ - Clean up instance metadata for an instance - """ - openvz_metadata_keys = ('tc_id','migration_type') - try: - for key in openvz_metadata_keys: - LOG.debug(_('Removing metadata key: %s') % key) - remove_instance_metadata_key(instance_id, key) - - LOG.debug(_('Deleted metadata for %(instance_id)s') % locals()) - return True - except exception.InstanceNotFound as err: - LOG.error(_('Instance not in the database: %s') % instance_id) - LOG.error(_('Consistency check is needed, orphaned instance: %s') % - instance_id) - return False - - -def generate_network_dict(container, network_info): - interfaces = list() - interface_num = -1 - for vif in network_info: - if vif.labeled_ips(): - interface_num += 1 - v6_subnets = [] - v4_subnets = [] - for subnet in vif['network']['subnets']: - if subnet['version'] == 4: - v4_subnets.append(subnet) - elif subnet['version'] == 6: - v6_subnets.append(subnet) - #TODO(imsplitbit): make this work for ipv6 - address_v6 = None - gateway_v6 = None - netmask_v6 = None - if CONF.use_ipv6: - if v6_subnets: - address_v6 = v6_subnets[0]['ips'][0]['address'] - netmask_v6 = v6_subnets[0].as_netaddr()._prefixlen - gateway_v6 = v6_subnets[0]['gateway'] - - interface_info = { - 'id': container.ovz_id, - 'interface_number': interface_num, - 'bridge': vif['network']['bridge'], - 'name': 'eth%d' % interface_num, - 'mac': vif['address'], - 'address': v4_subnets[0]['ips'][0]['address'], - 'netmask': v4_subnets[0].as_netaddr().netmask, - 'gateway': v4_subnets[0]['gateway'], - 'broadcast': v4_subnets[0].as_netaddr().broadcast, - 'dns': ' '.join([ip['address'] for ip in v4_subnets[0]['dns']]), - 'address_v6': address_v6, - 'gateway_v6': gateway_v6, - 'netmask_v6': netmask_v6 - } - interface_info['vz_host_if'] = ('veth%s.%s' % - (interface_info['id'], - interface_info['name'])) - interfaces.append(interface_info) - return interfaces - - -def move(src, dest): - """ - utility method to wrap up moving a file or directory from one place to - another. - """ - try: - execute('mv', src, dest, run_as_root=True) - return True - except exception.InstanceUnacceptable as err: - LOG.error(_('Error moving file %s') % src) - LOG.error(err) - return False - - -def copy(src, dest): - """ - utility method wrap up copying files from one directory to another - """ - try: - execute('cp', src, dest, run_as_root=True) - return True - except exception.InstanceUnacceptable as err: - LOG.error(_('Error copying file %s') % src) - LOG.error(err) - return False - - -def tar(source, target_file, working_dir=None, skip_list=None, extra=None): - """ - wrapper for tar for making backup archives - """ - cmd = ['tar', '-cf', target_file] - if working_dir: - cmd += ['-C', working_dir] - - if skip_list: - for exclude_path in skip_list: - cmd += ['--exclude', '%s/*' % exclude_path] - - if extra: - cmd.extend(extra) - - cmd.append(source) - try: - execute(*cmd, run_as_root=True) - return True - except exception.InstanceUnacceptable as err: - LOG.error(_('Error tarring: %s') % source) - LOG.error(err) - return False - - -def untar(target_file, destination, extra=None): - """ - wrapper for untarring files into a destination directory - """ - - cmd = ['tar', '-xf', target_file, '-C', destination] - if extra: - cmd.extend(extra) - - try: - execute(*cmd, run_as_root=True) - return True - except exception.InstanceUnacceptable as err: - LOG.error(_('Error untarring: %s') % target_file) - LOG.error(err) - return False diff --git a/ovznovadriver/openvz/volume.py b/ovznovadriver/openvz/volume.py deleted file mode 100644 index da4c45d..0000000 --- a/ovznovadriver/openvz/volume.py +++ /dev/null @@ -1,497 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" - -import glob -from nova import block_device -from nova import exception -from nova.openstack.common import log as logging -from nova.openstack.common import processutils -from ovznovadriver.localization import _ -from ovznovadriver.openvz import file as ovzfile -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg -import re -import time - -CONF = cfg.CONF -CONF.register_opts([ - cfg.IntOpt('ovz_volume_settle_num_tries', - default=10, - help='Number of attempts before we determine that a device ' - 'has had time to settle and we are beyond a reasonable ' - 'wait time'), - cfg.BoolOpt('ovz_create_disk_partition', - default=False, - help='Create a partition on the volume (if it does not exist) ' - 'when it is attached to the container'), -]) -LOG = logging.getLogger('ovznovadriver.openvz.volume') - - -class OVZVolume(object): - """ - This Class is a helper class to manage the mount and umount files - for a given container. - """ - def __init__(self, instance_id, mountpoint, dev): - """ - Setup critical information for attaching/detaching volumes from - instance_id. - - :param instance_id: - :param mountpoint: connection_info['data']['mount_device'] - :param dev: - """ - #TODO(imsplitbit): Need to make this happen while supporting block - # devices and externally mounted filesystems at the same time. - # Currently it does not. - self.instance_id = instance_id - self.mountpoint = block_device.prepend_dev(mountpoint) - self.device = dev - - def attach(self): - """ - Public method for attaching volumes either by creating bind mounts or - attaching a raw device to the instance. - """ - self._attach_raw_devices() - - def detach(self, container_is_running=True): - """ - Public method for detaching volumes from an instance. - """ - self._detach_raw_devices(container_is_running) - - def device_name(self): - """ - Generates an device name. If no volume driver is used this will - assist in generating an error should things get this far. - """ - return - - def _check_device_exists(self, device_path): - """Check that the device path exists. - - Verify that the device path has actually been created and can report - it's size, only then can it be available for formatting, retry - num_tries to account for the time lag. - """ - try: - ovz_utils.execute('blockdev', '--getsize64', device_path, - attempts=CONF.ovz_system_num_tries, - run_as_root=True) - except processutils.ProcessExecutionError: - raise exception.InvalidDevicePath(path=device_path) - - def _find_device(self): - try: - return os.path.realpath(self.device_name()) - - except (OSError, AttributeError) as err: - raise exception.VolumeNotFound( - _('Device cannot be found %s') % err) - - def _list_host_devices(self): - dev = self._find_device() - LOG.debug(_('Device name: %(dev)s') % locals()) - devs = list() - listing = glob.glob('/dev/sd*') - - for device in listing: - LOG.debug(_('Trying to match against %(device)s') % locals()) - m = re.match('^(?P%s)(?P\\d*)$' % dev, device) - if m: - LOG.debug(_('Matched device %(device)s') % locals()) - devs.append(m.string) - - LOG.debug(_('Devices: %(devs)s') % locals()) - return devs - - def _get_major_minor(self, device): - try: - dev = os.stat(device) - maj_min = dict() - maj_min['major'] = os.major(dev.st_rdev) - maj_min['minor'] = os.minor(dev.st_rdev) - LOG.debug( - _('Major Minor numbers for %(dev)s: %(maj_min)s') % locals()) - return maj_min - - except OSError as err: - LOG.error(_('Device error in OpenVz volumes: %(err)s') % locals()) - raise exception.VolumeNotFound( - _('Unable to find device: %(device)s') % locals()) - - def _let_disk_settle(self): - """ - Check to see if the device_name is available in /dev/disk/by-path. If - it isn't then we'll wait a bit and retry. Disks don't just instantly - show up in /dev so this gives a little bit of wait time for things - to show up. - - :return: - """ - ovz_utils.execute( - 'ls', self.device_name(), run_as_root=True, - attempts=CONF.ovz_volume_settle_num_tries, delay_on_retry=True) - - def _list_partition_table(self): - """ - There is a bit of work done here to make a nice partition table - structure for later use. Currently the only thing we care about is - if there is already a partition table but we may need this info soon - so the legwork is done. - - :return: dict - """ - # Now we should be able to move on to goodness. - dev = self._find_device() - LOG.debug(_('Device name: %(dev)s') % locals()) - part_table = dict() - try: - out = ovz_utils.execute('sfdisk', '-d', dev, run_as_root=True) - - for line in out.splitlines(): - line = line.split(':') - dev = line[0].strip() - LOG.debug(_('Device from part table: %(dev)s') % locals()) - - if dev.startswith('/dev'): - line = line[1].split(',') - - LOG.debug(_('Line from part table: %(line)s') % locals()) - part_table[dev] = {} - part_table[dev]['start'] = line[0].split('=')[1] - part_table[dev]['size'] = line[1].split('=')[1] - part_table[dev]['id'] = line[2].split('=')[1] - - LOG.debug( - _('Device info from part table: %s') % part_table[dev]) - - if len(line) > 3: - part_table[dev]['flags'] = line[3] - LOG.debug(_('Disk flags exist for %(dev)s') % locals()) - - LOG.debug(_('Partition Table: %(part_table)s') % locals()) - return part_table - - except exception.InstanceUnacceptable as err: - LOG.warn(_('No partition table on %(dev)s') % locals()) - return part_table - - def _partition_disk(self): - """ - Openvz requires that we pass in not only the root device but if the - user is to access partitions on that disk we need also to pass in - the major/minor numbers for each partition. Given that requirement - we're making the assumption for now that volumes are going to be - presented as one partition. This will partition the root device so - we can later get the information on both the major and minor numbers. - - If the disk contains a valid partition table then we just return - - :return: - """ - # We need potentially need to give the device time to settle - self._let_disk_settle() - - dev = self._find_device() - part_table = self._list_partition_table() - LOG.debug(_('Partition table for %(dev)s: %(part_table)s') % locals()) - - # If the volume is partitioned we're assuming this is a reconnect of - # a volume and we won't partition anything. - if not part_table: - commands = ['o,w', 'n,p,1,,,t,1,83,w'] - - for command in commands: - command = command.replace(',', '\n') - ovz_utils.execute( - 'fdisk', dev, process_input=command, run_as_root=True) - time.sleep(3) - - def _get_vz_device_list(self): - """ - Grab existing device information from vz config and create new - device string for device connections. - - :return: - """ - devices = list() - config = os.path.normpath( - '%s/%s.conf' % (CONF.ovz_config_dir, self.instance_id)) - config = ovzfile.OVZFile(config, 644) - config.read() - - for line in config.contents: - if '=' in line: - line = line.split('=') - if line[0] == 'DEVICES': - devices = line[1].replace('\"', '').strip().split() - - return devices - - def _ovz_block_dev_name_generator(self, major, minor, privs): - """ - OpenVz requires a specific format for granting or revoking block - device privileges. This tool will create those names. - - :param major: - :param minor: - :param privs: - :return: - """ - return 'b:%(major)s:%(minor)s:%(privs)s' % locals() - - def _attach_raw_devices(self): - """ - If there are no partitions on the disk already, partition it with 1 - partition. Then use openvz tools and mknod to attach these devices - to the container. - - :return: - """ - if CONF.ovz_create_disk_partition: - LOG.debug(_('Partitioning disk in _attach_raw_devices')) - self._partition_disk() - - # storage for block device major/minor pairs for setting in - # the container config file. - bdevs = [] - for dev in self._list_host_devices(): - maj_min = self._get_major_minor(dev) - bdevs.append( - self._ovz_block_dev_name_generator( - maj_min['major'], maj_min['minor'], 'rw')) - - m = re.match('^(?P/[a-z]+/[a-z]+)(?P\\d*)$', dev) - device_name = self.mountpoint - - if m and m.group('part'): - device_name = '%s%s' % (self.mountpoint, m.group('part')) - - # Remove the device if it happens to exist. This prevents stale - # devices with old major/minor numbers existing. - self._delete_container_device(device_name) - self._mknod(maj_min['major'], maj_min['minor'], device_name) - - if bdevs: - self._add_block_devices(bdevs) - - def _attach_raw_device(self, major, minor): - ovz_utils.execute( - 'vzctl', 'set', self.instance_id, - '--devices', 'b:%s:%s:rw' % (major, minor), - run_as_root=True) - - def _add_block_devices(self, new_devices): - """ - New devices should be a list that looks like this: - - ['b:8:32:rw', 'b:8:33:rw'] - - :param new_devices: - :return: - """ - devices = self._get_vz_device_list() - - for dev in new_devices: - if dev not in devices: - devices.append(dev) - - self._set_block_devices(devices) - - def _del_block_devices(self, new_devices, container_is_running=True): - """ - New devices should be a list that looks like this: - - ['b:8:32:rw', 'b:8:33:rw'] - - :param new_devices: - :return: - """ - devices = self._get_vz_device_list() - - for dev in new_devices: - if dev in devices: - devices.remove(dev) - - self._set_block_devices(devices, container_is_running) - - def _detach_remaining_block_devices(self): - """ - If the final ephemeral volume is detached from the container we issue - a privs :none for the remaining devices in the conf file for the - container before we remove those entries from the conf file. This is - necessary to ensure the removal of the devices from the in memory - device list for openvz. - - :return: - """ - devices = self._get_vz_device_list() - cmd = ['vzctl', 'set', self.instance_id] - - for dev in devices: - dev = dev.replace(':rw', ':none') - cmd.append('--devices') - cmd.append(dev) - - ovz_utils.execute(*cmd, run_as_root=True) - - def _set_block_devices(self, devices, container_is_running=True): - """ - Run the command necessary to save the block device permissions to - the container config file so that they persist on reboot. - - :param devices: - :return: - """ - cmd = ['vzctl', 'set', self.instance_id, '--save'] - if devices: - for dev in devices: - cmd.append('--devices') - cmd.append(dev) - - ovz_utils.execute(*cmd, run_as_root=True) - else: - # if the device list is empty this means that it's the last device - # attached to the container and we need to run some special case - # code to remove that device. - if container_is_running: - self._detach_remaining_block_devices() - - self._remove_all_device_entries() - - def _remove_all_device_entries(self): - """ - When there are no devices left to remove we need to remove the - DEVICES line from the CTID.conf file. This cannot be achieved by - a vzctl command so the file has to be manipulated and saved. - - :return: None - """ - filename = '%s/%s.conf' % (CONF.ovz_config_dir, self.instance_id) - filename = os.path.normpath(filename) - ct_conf = ovzfile.OVZFile(filename, 644) - ct_conf.read() - with ct_conf: - for line in ct_conf.contents: - if "DEVICES" in line: - ct_conf.contents.remove(line) - ct_conf.write() - - def _detach_raw_devices(self, container_is_running=True): - """ - Remove the associated devices from the container. - - :return: - """ - LOG.debug(_('Detaching raw devices')) - - # storage for block device major/minor pairs for setting in - # the container config file. - bdevs_conf = list() - for dev in self._list_host_devices(): - maj_min = self._get_major_minor(dev) - bdevs_conf.append( - self._ovz_block_dev_name_generator( - maj_min['major'], maj_min['minor'], 'rw')) - - # TODO(imsplitbit): research to see if running this remove command - # adhoc is necessary or if just removing the device from the config - # file is adequate. - if container_is_running: - # If the container isn't running this command makes things - # unhappy. Very very unhappy. - self._detach_raw_device(maj_min['major'], maj_min['minor']) - - m = re.match('^(?P/[a-z]+/[a-z]+)(?P\\d*)$', dev) - device_name = self.mountpoint - - if m and m.group('part'): - device_name = '%s%s' % (self.mountpoint, m.group('part')) - - self._delete_container_device(device_name) - self._delete_device(dev) - - if bdevs_conf: - self._del_block_devices(bdevs_conf, container_is_running) - - def _detach_raw_device(self, major, minor): - """ - Remove perms from the container for a device based on major and minor - numbers. - - :param major: - :param minor: - :return: - """ - ovz_utils.execute( - 'vzctl', 'set', self.instance_id, '--devices', - 'b:%s:%s:none' % (major, minor), run_as_root=True) - - def _mknod(self, major, minor, device_name, dev_type='b'): - """ - Because openvz doesn't support device aliases we manually create - a block device sharing the same major and minor numbers as the device - on the host. This device should be created in the openvz chrooted - /dev directory so as to allow it to be cleaned up upon deletion. - - :param major: - :param minor: - :param dev_type: - :return: None - """ - good_types = ['b'] - if dev_type not in good_types: - raise TypeError( - _('Cannot make device of type "%(dev_type)s"') % locals()) - - device_path = '%s/%s/%s' % ( - CONF.ovz_ve_private_dir, self.instance_id, device_name) - device_path = os.path.normpath(device_path) - ovz_utils.execute( - 'mknod', device_path, dev_type, major, minor, run_as_root=True) - - def _delete_device(self, device): - """ - Utility method for deleting/removing device file - - :param device - """ - ovz_utils.execute('rm', '-f', device, run_as_root=True) - - def _delete_container_device(self, device): - """ - Utility method for removing a device from inside the container. This - is to happen before you create a device because the existing device - may or may not have the proper major/minor numbers. This is obviously - done on volume detach as well. - - :param device: - :return: - """ - device = '%s/%s/%s' % ( - CONF.ovz_ve_private_dir, self.instance_id, device) - device = os.path.normpath(device) - self._delete_device(device) diff --git a/ovznovadriver/openvz/volume_drivers/__init__.py b/ovznovadriver/openvz/volume_drivers/__init__.py deleted file mode 100644 index 3e1c627..0000000 --- a/ovznovadriver/openvz/volume_drivers/__init__.py +++ /dev/null @@ -1,16 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. diff --git a/ovznovadriver/openvz/volume_drivers/iscsi.py b/ovznovadriver/openvz/volume_drivers/iscsi.py deleted file mode 100644 index 34925ce..0000000 --- a/ovznovadriver/openvz/volume_drivers/iscsi.py +++ /dev/null @@ -1,194 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -""" -A driver specific to OpenVz as the support for Ovz in libvirt -is sketchy at best. -""" -from nova import exception -from nova.openstack.common import lockutils -from nova.openstack.common import log as logging -from nova.openstack.common import processutils -from ovznovadriver.localization import _ -from ovznovadriver.openvz import utils as ovz_utils -from ovznovadriver.openvz import volume as ovzvolume -from oslo.config import cfg -import time - - -CONF = cfg.CONF -CONF.register_opt( - cfg.IntOpt('ovz_iscsiadm_num_tries', - default=1, - help='Number of attempts to make an iscsi connection')) - -CONF.register_opt( - cfg.IntOpt('ovz_max_symlink_wait_time', - default=5, - help='Max seconds to wait for symlink resolution.')) - -LOG = logging.getLogger('ovznovadriver.openvz.volume_drivers.iscsi') - - -class OVZISCSIStorageDriver(ovzvolume.OVZVolume): - def __init__(self, instance_id, mountpoint, connection_data): - """ - Driver for openvz to connect iscsi volumes to instances - - :param connection_data: Data from the connection_info given to the - ovz driver - :param instance_id: Instance ID for the volume to be attached to - :param mountpoint: place to mount the volume within the container - """ - self.iscsi_properties = connection_data['data'] - super(OVZISCSIStorageDriver, self).__init__( - instance_id, mountpoint, self.device_name()) - self.init_iscsi_device() - - def device_name(self): - """ - Generates an device name based on the iSCSI parameters in the - block device mapping - """ - return "/dev/disk/by-path/ip-%s-iscsi-%s-lun-%s" % \ - (self.iscsi_properties['target_portal'], - self.iscsi_properties['target_iqn'], - self.iscsi_properties['target_lun']) - - def _find_device(self): - idle_time = .1 - total_wait_time = 0 - while total_wait_time < CONF.ovz_max_symlink_wait_time: - path = super(OVZISCSIStorageDriver, self)._find_device() - if 'disk/by-path' not in path: - return path - time.sleep(idle_time) - total_wait_time += idle_time - idle_time *= 2 - LOG.debug('Having trouble resolving %s. Trying Again.' % path) - raise IOError("Could not resolve symlink: %s" % path) - - def init_iscsi_device(self): - """ - Log into the device and setup files - """ - self.discover_volume() - - def _run_iscsiadm(self, iscsi_command, raise_on_error=True): - out = ovz_utils.execute('iscsiadm', '-m', 'node', '-T', - self.iscsi_properties['target_iqn'], - '-p', self.iscsi_properties['target_portal'], - *iscsi_command, run_as_root=True, - attempts=CONF.ovz_iscsiadm_num_tries, - raise_on_error=raise_on_error) - LOG.debug("iscsiadm %s: stdout=%s" % - (iscsi_command, out)) - return out - - def _iscsiadm_update(self, property_key, property_value, - raise_on_error=True): - iscsi_command = ('--op', 'update', '-n', property_key, - '-v', property_value) - return self._run_iscsiadm(iscsi_command, raise_on_error=raise_on_error) - - def get_iscsi_properties_for_volume(self): - if not self.iscsi_properties['target_discovered']: - self._run_iscsiadm(('--op', 'new')) - - def session_currently_connected(self, **kwargs): - check_exit_code = kwargs.pop('check_exit_code', [0]) - out = ovz_utils.execute( - 'iscsiadm', '-m', 'session', run_as_root=True, - raise_on_error=False, - check_exit_code=check_exit_code) - if out: - for line in out.splitlines(): - if self.iscsi_properties['target_iqn'] in line: - return True - else: - return False - - def set_iscsi_auth(self): - if self.iscsi_properties.get('auth_method', None): - self._iscsiadm_update("node.session.auth.authmethod", - self.iscsi_properties['auth_method']) - self._iscsiadm_update("node.session.auth.username", - self.iscsi_properties['auth_username']) - self._iscsiadm_update("node.session.auth.password", - self.iscsi_properties['auth_password']) - - @lockutils.synchronized('iscsiadm_lock', 'openvz-') - def discover_volume(self): - """Discover volume on a remote host.""" - self.get_iscsi_properties_for_volume() - self.set_iscsi_auth() - - try: - if not self.session_currently_connected(check_exit_code=[0, 21]): - LOG.debug(_('iSCSI session for %s not connected, ' - 'connecting now') % - self.iscsi_properties['target_iqn']) - self._run_iscsiadm(("--login",)) - LOG.debug(_('iSCSI session for %s connected') % - self.iscsi_properties['target_iqn']) - except processutils.ProcessExecutionError as err: - if "15 - already exists" in err.message: - raise exception.VolumeUnattached() - LOG.error(err) - raise exception.VolumeNotFound(_("iSCSI device %s not found") % - self.iscsi_properties['target_iqn']) - - def detach(self, container_is_running=True): - """Detach the volume from instance_name.""" - super(OVZISCSIStorageDriver, self).detach(container_is_running) - self._detach_iscsi() - - @lockutils.synchronized('iscsiadm_lock', 'openvz-') - def _detach_iscsi(self): - """ - Detach all iscsi sessions for this volume - - :return: - """ - self._iscsiadm_update("node.startup", "manual") - self._run_iscsiadm(("--logout",), raise_on_error=False) - self._run_iscsiadm(('--op', 'delete'), raise_on_error=False) - - def get_blockdev(self, device_name): - return ovz_utils.execute('blockdev', - '--getsize64', - device_name, - attempts=CONF.ovz_system_num_tries, - run_as_root=True) - - @lockutils.synchronized('iscsiadm_lock', 'openvz-') - def rescan(self): - """Rescan the client storage connection.""" - - self.get_iscsi_properties_for_volume() - try: - LOG.debug("ISCSI Properties: %s" % self.iscsi_properties) - self._run_iscsiadm(("--rescan",)) - return ("/dev/disk/by-path/ip-%s-iscsi-%s-lun-%s" % - (self.iscsi_properties['target_portal'], - self.iscsi_properties['target_iqn'], - self.iscsi_properties['target_lun'])) - except processutils.ProcessExecutionError as err: - LOG.error(err) - raise exception.ISCSITargetNotFoundForVolume( - _("Error rescanning iscsi device: %s") % - self.iscsi_properties['target_iqn']) diff --git a/ovznovadriver/tests/openvz/__init__.py b/ovznovadriver/tests/openvz/__init__.py deleted file mode 100644 index 3e1c627..0000000 --- a/ovznovadriver/tests/openvz/__init__.py +++ /dev/null @@ -1,16 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. diff --git a/ovznovadriver/tests/openvz/fakes.py b/ovznovadriver/tests/openvz/fakes.py deleted file mode 100644 index 73a4945..0000000 --- a/ovznovadriver/tests/openvz/fakes.py +++ /dev/null @@ -1,826 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -from Cheetah import Template -import json -from nova.compute import power_state -from nova import exception -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg -import random -import socket - -CONF = cfg.CONF - -global _ovz_tc_available_ids -global _ovz_tc_inflight_ids -_ovz_tc_available_ids = None -_ovz_tc_inflight_ids = None - - -class FakeOVZExtStorage(object): - def __init__(self, instance_id): - self.instance_id = instance_id - self._volumes = {} - - def add_volume(self, mount_point, connection_info): - self._volumes[mount_point] = connection_info - - def remove_volume(self, mount_point): - self._volumes.pop(mount_point) - - -class FakeOVZTcRules(object): - if not _ovz_tc_available_ids: - _ovz_tc_available_ids = list() - - if not _ovz_tc_inflight_ids: - _ovz_tc_inflight_ids = list() - - def __init__(self): - if not len(FakeOVZTcRules._ovz_tc_available_ids): - FakeOVZTcRules._ovz_tc_available_ids = [ - i for i in range(1, CONF.ovz_tc_id_max) - ] - self.instance_type = {'memory_mb': 512} - self._remove_used_ids() - - def instance_info(self, instance_id, address, vz_iface): - if not instance_id: - self.instance_type = dict() - self.instance_type['memory_mb'] = 2048 - - self.address = address - self.vz_iface = vz_iface - self.bandwidth = int( - round(self.instance_type['memory_mb'] / - CONF.ovz_memory_unit_size)) * CONF.ovz_tc_mbit_per_unit - self.tc_id = self._get_instance_tc_id() - if not self.tc_id: - self.tc_id = self.get_id() - - self._save_instance_tc_id() - - def get_id(self): - self._remove_used_ids() - tc_id = self._pull_id() - while tc_id in FakeOVZTcRules._ovz_tc_inflight_ids: - tc_id = self._pull_id() - self._reserve_id(tc_id) - return id - - def container_start(self): - template = self._load_template('tc_container_start.template') - search_list = { - 'prio': self.tc_id, - 'host_iface': CONF.ovz_tc_host_slave_device, - 'vz_iface': self.vz_iface, - 'bandwidth': self.bandwidth, - 'vz_address': self.address, - 'line_speed': CONF.ovz_tc_max_line_speed - } - return self._fill_template(template, search_list).splitlines() - - def container_stop(self): - template = self._load_template('tc_container_stop.template') - search_list = { - 'prio': self.tc_id, - 'host_iface': CONF.ovz_tc_host_slave_device, - 'vz_iface': self.vz_iface, - 'bandwidth': self.bandwidth, - 'vz_address': self.address - } - return self._fill_template(template, search_list).splitlines() - - def host_start(self): - template = self._load_template('tc_host_start.template') - search_list = { - 'host_iface': CONF.ovz_tc_host_slave_device, - 'line_speed': CONF.ovz_tc_max_line_speed - } - return self._fill_template(template, search_list).splitlines() - - def host_stop(self): - template = self._load_template('tc_host_stop.template') - search_list = { - 'host_iface': CONF.ovz_tc_host_slave_device - } - return self._fill_template(template, search_list).splitlines() - - def _load_template(self, template_name): - full_template_path = '%s/%s' % ( - CONF.ovz_tc_template_dir, template_name) - full_template_path = os.path.abspath(full_template_path) - try: - template_file = open(full_template_path).read() - return template_file - except Exception as err: - raise exception.FileNotFound(err) - - def _fill_template(self, template, search_list): - return str(Template.Template(template, searchList=[search_list])) - - def _pull_id(self): - return _ovz_tc_available_ids[random.randint( - 0, len(_ovz_tc_available_ids) - 1)] - - def _list_existing_ids(self): - return [1, 3, 6] - - def _reserve_id(self, tc_id): - FakeOVZTcRules._ovz_tc_inflight_ids.append(tc_id) - FakeOVZTcRules._ovz_tc_available_ids.remove(tc_id) - - def _remove_used_ids(self): - used_ids = self._list_existing_ids() - for tc_id in used_ids: - if tc_id in FakeOVZTcRules._ovz_tc_available_ids: - FakeOVZTcRules._ovz_tc_available_ids.remove(tc_id) - - def _save_instance_tc_id(self): - return - - def _get_instance_tc_id(self): - return 1 - - -class Context(object): - def __init__(self): - self.is_admin = False - self.read_deleted = "yes" - - -class AdminContext(Context): - def __init__(self): - super(AdminContext, self).__init__() - self.is_admin = True - - -# Stubs for faked file operations to allow unittests to test code paths -# without actually leaving file turds around the test box. -class FakeOvzFile(object): - def __init__(self, filename, perms): - self.filename = filename - self.permissions = perms - self.contents = [] - - def __enter__(self): - """ - This may feel dirty but we need to be able to read and write files - as a non priviledged user so we need to change the permissions to - be more open for our file operations and then secure them once we - are done. - """ - if not self.exists(): - self.make_path() - self.touch() - - self.set_permissions(666) - - def __exit__(self, _type, value, tb): - if self.exists(): - self.set_permissions(self.permissions) - - def exists(self): - return True - - def make_path(self, path=None): - return - - def touch(self): - return - - def set_permissions(self, perms): - return - - def read(self): - return - - def run_contents(self, raise_on_error=True): - return - - def set_contents(self, contents): - self.contents = contents - - def make_proper_script(self): - return - - def append(self, contents): - if not isinstance(contents, list): - contents = [str(contents)] - self.contents = self.contents + contents - - def prepend(self, contents): - if not isinstance(contents, list): - contents = [str(contents)] - self.contents = contents + self.contents - - def write(self): - return - - -class FakeOVZShutdownFile(FakeOvzFile): - def __init__(self, instance_id, permissions): - filename = "%s/%s.shutdown" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - super(FakeOVZShutdownFile, self).__init__(filename, permissions) - - -class FakeOVZBootFile(FakeOvzFile): - def __init__(self, instance_id, permissions): - filename = "%s/%s.shutdown" % (CONF.ovz_config_dir, instance_id) - filename = os.path.abspath(filename) - super(FakeOVZBootFile, self).__init__(filename, permissions) - - -class FakeOVZNetworkFile(FakeOvzFile): - def __init__(self, filename): - self.filename = filename - super(FakeOVZNetworkFile, self).__init__(filename, 644) - - -class FakeOVZInstanceVolumeOps(object): - def __init__(self, instance): - self.instance = instance - - def attach_all_volumes(self): - return - - def detach_all_volumes(self): - return - - -class FakeOVZISCSIStorageDriver(object): - def init_iscsi_device(self): - return - - def disconnect_iscsi_volume(self): - return - - def discover_volume(self): - return - - def setup(self): - return - - def prepare_filesystem(self): - return - - def attach(self): - return - - def detach(self, container_is_running=True): - return - - def write_and_close(self): - return - - -class FakeAggregate(object): - def __init__(self): - self.id = 1 - - -class FakePosixStatVFSResult(object): - def __init__(self): - self.f_frsize = 4096 - self.f_blocks = 61005206 - self.f_bavail = 58342965 - self.f_bfree = 58342965 - - -METAKEY = 'tc_id' -METAVALUE = '1002' -METADATA = {METAKEY: METAVALUE} - -STATVFSRESULT = FakePosixStatVFSResult() - -AGGREGATE = FakeAggregate() - -ROOTPASS = '2s3cUr3' - -USER = {'user': 'admin', 'role': 'admin', 'id': 1} - -PROJECT = {'name': 'test', 'id': 2} - -ADMINCONTEXT = AdminContext() - -CONTEXT = Context() - -DESTINATION = '127.0.7.1' - -BDM = { - 'block_device_mapping': [ - { - 'connection_info': { - 'data': { - 'volume_id': 'c49a7247-731e-4135-8420-7a3c67002582' - }, - 'driver_volume_type': 'iscsi', - 'mount_device': '/dev/sdgg' - }, - 'mount_device': '/dev/sdgg' - } - ] -} - -INSTANCETYPE = { - 'id': 1, - 'vcpus': 1, - 'name': 'm1.small', - 'memory_mb': 2048, - 'swap': 0, - 'root_gb': 20 -} - -INSTANCE = { - "image_ref": 1, - "name": "instance-00001002", - "instance_type_id": 1, - "id": 1002, - "uuid": "07fd1fc9-eb75-4375-88d5-6247ce2fb7e4", - "hostname": "test.foo.com", - "power_state": power_state.RUNNING, - "admin_pass": ROOTPASS, - "user_id": USER['id'], - "project_id": PROJECT['id'], - "memory_mb": INSTANCETYPE['memory_mb'], - "block_device_mapping": BDM, - "system_metadata": [ - {'key': METAKEY, 'value': METAVALUE}, - {'key': 'instance_type_name', 'value': INSTANCETYPE['name']}, - {'key': 'instance_type_root_gb', 'value': INSTANCETYPE['root_gb']}, - {'key': 'instance_type_memory_mb', 'value': INSTANCETYPE['memory_mb']}, - {'key': 'instance_type_vcpus', 'value': INSTANCETYPE['vcpus']} - ] -} - -BLKID = '0670a412-bba5-4ef4-a954-7fec8f2a06aa\n' - -IMAGEPATH = '%s/%s.tar.gz' % \ - (CONF.ovz_image_template_dir, INSTANCE['image_ref']) - -INSTANCES = [INSTANCE, INSTANCE] - -RES_PERCENT = .50 - -RES_OVER_PERCENT = 1.50 - -VZLIST = "\t1001\n\t%d\n\t1003\n\t1004\n" % (INSTANCE['id'],) - -VZLISTDETAIL = " %d running %s" \ - % (INSTANCE['id'], INSTANCE['hostname']) - -FINDBYNAME = VZLISTDETAIL.split() -FINDBYNAME = {'name': FINDBYNAME[2], 'id': int(FINDBYNAME[0]), - 'state': FINDBYNAME[1]} -FINDBYNAMENOSTATE = VZLISTDETAIL.split() -FINDBYNAMENOSTATE = { - 'name': FINDBYNAMENOSTATE[2], 'id': int(FINDBYNAMENOSTATE[0]), - 'state': '-'} -FINDBYNAMESHUTDOWN = VZLISTDETAIL.split() -FINDBYNAMESHUTDOWN = { - 'name': FINDBYNAMESHUTDOWN[2], 'id': int(FINDBYNAMESHUTDOWN[0]), - 'state': 'stopped'} - -VZNAME = """\tinstance-00001001\n""" - -VZNAMES = """\tinstance-00001001\n\t%s - \tinstance-00001003\n\tinstance-00001004\n""" % ( - INSTANCE['name'],) - -GOODSTATUS = { - 'state': power_state.RUNNING, - 'max_mem': 0, - 'mem': 0, - 'num_cpu': 0, - 'cpu_time': 0 -} - -NOSTATUS = { - 'state': power_state.NOSTATE, - 'max_mem': 0, - 'mem': 0, - 'num_cpu': 0, - 'cpu_time': 0 -} - -SHUTDOWNSTATUS = { - 'state': power_state.SHUTDOWN, - 'max_mem': 0, - 'mem': 0, - 'num_cpu': 0, - 'cpu_time': 0 -} - -ERRORMSG = "vz command ran but output something to stderr" - -MEMINFO = """MemTotal: 506128 kB -MemFree: 291992 kB -Buffers: 44512 kB -Cached: 64708 kB -SwapCached: 0 kB -Active: 106496 kB -Inactive: 62948 kB -Active(anon): 62108 kB -Inactive(anon): 496 kB -Active(file): 44388 kB -Inactive(file): 62452 kB -Unevictable: 2648 kB -Mlocked: 2648 kB -SwapTotal: 1477624 kB -SwapFree: 1477624 kB -Dirty: 0 kB -Writeback: 0 kB -AnonPages: 62908 kB -Mapped: 14832 kB -Shmem: 552 kB -Slab: 27988 kB -SReclaimable: 17280 kB -SUnreclaim: 10708 kB -KernelStack: 1448 kB -PageTables: 3092 kB -NFS_Unstable: 0 kB -Bounce: 0 kB -WritebackTmp: 0 kB -CommitLimit: 1730688 kB -Committed_AS: 654760 kB -VmallocTotal: 34359738367 kB -VmallocUsed: 24124 kB -VmallocChunk: 34359711220 kB -HardwareCorrupted: 0 kB -HugePages_Total: 0 -HugePages_Free: 0 -HugePages_Rsvd: 0 -HugePages_Surp: 0 -Hugepagesize: 2048 kB -DirectMap4k: 8128 kB -DirectMap2M: 516096 kB -""" - -PROCINFO = """ -processor : 0 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 0 -cpu cores : 4 -apicid : 0 -initial apicid : 0 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.55 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 1 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 0 -cpu cores : 4 -apicid : 1 -initial apicid : 1 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.36 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 2 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 1 -cpu cores : 4 -apicid : 2 -initial apicid : 2 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.36 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 3 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 1 -cpu cores : 4 -apicid : 3 -initial apicid : 3 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.36 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 4 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 2 -cpu cores : 4 -apicid : 4 -initial apicid : 4 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.37 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 5 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 2 -cpu cores : 4 -apicid : 5 -initial apicid : 5 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.36 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 6 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 3 -cpu cores : 4 -apicid : 6 -initial apicid : 6 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.37 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: - -processor : 7 -vendor_id : GenuineIntel -cpu family : 6 -model : 58 -model name : Intel(R) Core(TM) i7-3610QM CPU @ 2.30GHz -stepping : 9 -microcode : 0x13 -cpu MHz : 1200.000 -cache size : 6144 KB -physical id : 0 -siblings : 8 -core id : 3 -cpu cores : 4 -apicid : 7 -initial apicid : 7 -fpu : yes -fpu_exception : yes -cpuid level : 13 -wp : yes -flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca -bogomips : 4589.37 -clflush size : 64 -cache_alignment : 64 -address sizes : 36 bits physical, 48 bits virtual -power management: -""" - -UTILITY = { - 'CTIDS': { - 1: { - - } - }, - 'UTILITY': 10000, - 'TOTAL': 1000, - 'UNITS': 100000, - 'MEMORY_MB': 512000, - 'CPULIMIT': 2400 -} - -CPUUNITSCAPA = { - 'total': 500000, - 'subscribed': 1000 -} - -CPUCHECKCONT = """VEID CPUUNITS -------------------------- -0 1000 -26 25000 -27 25000 -Current CPU utilization: 51000 -Power of the node: 758432 -""" - -CPUCHECKNOCONT = """Current CPU utilization: 51000 -Power of the node: 758432 -""" - -FILECONTENTS = """mount UUID=FEE52433-F693-448E-B6F6-AA6D0124118B /mnt/foo - mount --bind /mnt/foo /vz/private/1/mnt/foo - """ - - -INTERFACEINFO = [ - { - 'id': 1002, - 'interface_number': 0, - 'bridge': 'br100', - 'name': 'eth0', - 'vz_host_if': 'veth1002.eth0', - 'mac': '02:16:3e:0c:2c:08', - 'address': '10.0.2.16', - 'netmask': '255.255.255.0', - 'gateway': '10.0.2.2', - 'broadcast': '10.0.2.255', - 'dns': '192.168.2.1', - 'address_v6': None, - 'gateway_v6': None, - 'netmask_v6': None - }, - { - 'id': 1002, - 'interface_number': 1, - 'bridge': 'br200', - 'name': 'eth1', - 'vz_host_if': 'veth1002.eth1', - 'mac': '02:16:3e:40:5e:1b', - 'address': '10.0.4.16', - 'netmask': '255.255.255.0', - 'gateway': '10.0.2.2', - 'broadcast': '10.0.4.255', - 'dns': '192.168.2.1', - 'address_v6': None, - 'gateway_v6': None, - 'netmask_v6': None - } -] - -TEMPFILE = '/tmp/foo/file' - -NETTEMPLATE = """ - # This file describes the network interfaces available on your system - # and how to activate them. For more information, see interfaces(5). - - # The loopback network interface - auto lo - iface lo inet loopback - - #for $ifc in $interfaces - auto ${ifc.name} - iface ${ifc.name} inet static - address ${ifc.address} - netmask ${ifc.netmask} - broadcast ${ifc.broadcast} - gateway ${ifc.gateway} - dns-nameservers ${ifc.dns} - - #if $use_ipv6 - iface ${ifc.name} inet6 static - address ${ifc.address_v6} - netmask ${ifc.netmask_v6} - gateway ${ifc.gateway_v6} - #end if - - #end for - """ - -HOSTSTATS = { - 'vcpus': 12, - 'vcpus_used': 2, - 'cpu_info': json.dumps(PROCINFO), - 'memory_mb': 36864, - 'memory_mb_used': 2048, - 'host_memory_total': 36864, - 'host_memory_free': 34816, - 'disk_total': 232, - 'disk_used': 10, - 'disk_available': 222, - 'local_gb': 232, - 'local_gb_used': 10, - 'hypervisor_type': ovz_utils.get_hypervisor_type(), - 'hypervisor_version': '3.2.0-31-generic', - 'hypervisor_hostname': socket.gethostname() -} - -FILESTOINJECT = [ - ['/tmp/testfile1', FILECONTENTS], - ['/tmp/testfile2', FILECONTENTS] -] - -OSLISTDIR = ['1002.start', '1002.stop'] - -INITIATORNAME = 'iqn.1993-08.org.debian:01:f424a54e43' - -ISCSIINITIATOR = """## DO NOT EDIT OR REMOVE THIS FILE! -## If you remove this file, the iSCSI daemon will not start. -## If you change the InitiatorName, existing access control lists -## may reject this initiator. The InitiatorName must be unique -## for each iSCSI initiator. Do NOT duplicate iSCSI InitiatorNames. -InitiatorName=%s -""" % INITIATORNAME - -PRIVVMPAGES_2048 = "%s 524288\n" % INSTANCE['id'] -PRIVVMPAGES_1024 = "1003 262144\n" -PRIVVMPAGES = PRIVVMPAGES_2048 + PRIVVMPAGES_1024 - -UNAME = ('Linux', 'imsplitbit-M17xR4', '3.2.0-31-generic', - '#50-Ubuntu SMP Fri Sep 7 16:16:45 UTC 2012', 'x86_64', 'x86_64') diff --git a/ovznovadriver/tests/openvz/test_driver.py b/ovznovadriver/tests/openvz/test_driver.py deleted file mode 100644 index 1edf421..0000000 --- a/ovznovadriver/tests/openvz/test_driver.py +++ /dev/null @@ -1,2024 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -import base64 -import json -import mox -from nova.compute import manager -from nova.compute import power_state -from nova import exception -from nova.openstack.common import processutils -from nova import test -from nova.tests import fake_network -from ovznovadriver.tests.openvz import fakes -from ovznovadriver.openvz import driver as openvz_conn -from ovznovadriver.openvz.file_ext import ext_storage -from ovznovadriver.openvz import migration -from ovznovadriver.openvz import utils as ovz_utils -import os -from oslo.config import cfg - -CONF = cfg.CONF -_fake_network_info = fake_network.fake_get_instance_nw_info - - -class OpenVzDriverTestCase(test.TestCase): - def setUp(self): - super(OpenVzDriverTestCase, self).setUp() - try: - CONF.injected_network_template - except AttributeError: - CONF.register_opt( - cfg.StrOpt('injected_network_template', - default='ovznovadriver/interfaces.template', - help='Stub for network template ' - 'for testing purposes')) - CONF.use_ipv6 = False - self.ext_str_filename = '%s/%s.ext_storage' % (CONF.ovz_config_dir, - fakes.INSTANCE['id']) - self.ext_str_filename = os.path.abspath(self.ext_str_filename) - self.ext_str_permissions = 600 - self.network_info = _fake_network_info(self.stubs, 1) - - - def test_start_success(self): - # Testing happy path :-D - # Mock the objects needed for this test to succeed. - self.mox.StubOutWithMock(openvz_conn.ovzboot, 'OVZBootFile') - openvz_conn.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'start', fakes.INSTANCE['id'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.RUNNING}) - # Start the tests - self.mox.ReplayAll() - # Create our connection object. For all intents and purposes this is - # a real OpenVzDriver object. - conn._start(fakes.INSTANCE) - - def test_start_fail(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'start', fakes.INSTANCE['id'], - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._start, fakes.INSTANCE) - - def test_list_instances_success(self): - # Testing happy path of OpenVzDriver.list_instances() - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzlist', '--all', '--no-header', '--output', 'ctid', - run_as_root=True).AndReturn( - (fakes.VZLIST, fakes.ERRORMSG)) - # Start test - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - vzs = conn.list_instances() - self.assertEqual(vzs.__class__, list) - - def test_list_instances_fail(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzlist', '--all', '--no-header', '--output', 'ctid', - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - # Start test - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises(exception.InstanceUnacceptable, conn.list_instances) - - def test_create_vz_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'create', fakes.INSTANCE['id'], '--ostemplate', - fakes.INSTANCE['image_ref'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._create_vz(fakes.INSTANCE) - - def test_create_vz_fail(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'create', fakes.INSTANCE['id'], '--ostemplate', - fakes.INSTANCE['image_ref'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._create_vz, fakes.INSTANCE) - - def test_set_vz_os_hint_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--ostemplate', - 'ubuntu', run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_vz_os_hint(fakes.INSTANCE) - - def test_set_vz_os_hint_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--ostemplate', - 'ubuntu', run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_vz_os_hint, - fakes.INSTANCE) - - def test_configure_vz_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--applyconfig', - 'basic', run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._configure_vz(fakes.INSTANCE) - - def test_configure_vz_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--applyconfig', - 'basic', run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._configure_vz, fakes.INSTANCE) - - def test_stop_success(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'stop', fakes.INSTANCE['id'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.SHUTDOWN}) - self.mox.ReplayAll() - conn._stop(fakes.INSTANCE) - - def test_stop_failure_on_exec(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'stop', fakes.INSTANCE['id'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._stop, fakes.INSTANCE) - - def test_stop_failure_on_db_access(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'stop', fakes.INSTANCE['id'], - run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.SHUTDOWN}).AndRaise( - exception.InstanceNotFound('FAIL')) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceNotFound, conn._stop, fakes.INSTANCE) - - def test_set_vmguarpages_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--vmguarpages', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_vmguarpages( - fakes.INSTANCE, conn._calc_pages(fakes.INSTANCE['memory_mb'])) - - def test_set_vmguarpages_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--vmguarpages', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_vmguarpages, - fakes.INSTANCE, conn._calc_pages(fakes.INSTANCE['memory_mb'])) - - def test_set_privvmpages_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--privvmpages', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_privvmpages( - fakes.INSTANCE, conn._calc_pages(fakes.INSTANCE['memory_mb'])) - - def test_set_privvmpages_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--privvmpages', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_privvmpages, - fakes.INSTANCE, conn._calc_pages(fakes.INSTANCE['memory_mb'])) - - def test_set_kmemsize_success(self): - kmemsize = ((fakes.INSTANCE['memory_mb'] * 1024) * 1024) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--kmemsize', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_kmemsize(fakes.INSTANCE, kmemsize) - - def test_set_kmemsize_failure(self): - kmemsize = ((fakes.INSTANCE['memory_mb'] * 1024) * 1024) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--kmemsize', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_kmemsize, fakes.INSTANCE, - kmemsize) - - def test_cache_image_path_doesnt_exist(self): - self.mox.StubOutWithMock(openvz_conn.os.path, 'exists') - openvz_conn.os.path.exists(mox.IgnoreArg()).AndReturn(False) - self.mox.StubOutWithMock(openvz_conn.images, 'fetch') - openvz_conn.images.fetch( - fakes.ADMINCONTEXT, fakes.INSTANCE['image_ref'], fakes.IMAGEPATH, - fakes.INSTANCE['user_id'], fakes.INSTANCE['project_id']) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertTrue( - ovz_conn._cache_image(fakes.ADMINCONTEXT, fakes.INSTANCE)) - - def test_cache_image_path_exists(self): - self.mox.StubOutWithMock(openvz_conn.os.path, 'exists') - openvz_conn.os.path.exists(mox.IgnoreArg()).AndReturn(True) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertFalse( - ovz_conn._cache_image(fakes.ADMINCONTEXT, fakes.INSTANCE)) - - def test_access_control_allow(self): - self.mox.StubOutWithMock( - openvz_conn.linux_net.iptables_manager, 'apply') - openvz_conn.linux_net.iptables_manager.apply().MultipleTimes() - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._initial_secure_host(fakes.INSTANCE) - ovz_conn._access_control(fakes.INSTANCE, '1.1.1.1') - - def test_access_control_deny_and_port(self): - self.mox.StubOutWithMock( - openvz_conn.linux_net.iptables_manager, 'apply') - openvz_conn.linux_net.iptables_manager.apply().MultipleTimes() - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._initial_secure_host(fakes.INSTANCE) - ovz_conn._access_control( - fakes.INSTANCE, '1.1.1.1', port=22, access_type='deny') - - def test_access_control_invalid_access_type(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InvalidInput, ovz_conn._access_control, fakes.INSTANCE, - '1.1.1.1', port=22, access_type='invalid') - - def test_reset_instance_size_success(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, 'reboot') - ovz_conn.reboot(fakes.INSTANCE, None, None, None, None) - self.mox.ReplayAll() - self.assertTrue(ovz_conn.reset_instance_size(fakes.INSTANCE, True)) - - def test_reset_instance_size_failure(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn.reset_instance_size, - fakes.INSTANCE, True) - - def test_set_numflock(self): - instance_memory_mb = int(fakes.INSTANCETYPE['memory_mb']) - memory_unit_size = int(CONF.ovz_memory_unit_size) - max_fd_per_unit = int(CONF.ovz_file_descriptors_per_unit) - max_fd = int(instance_memory_mb / memory_unit_size) * max_fd_per_unit - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--numflock', - max_fd, run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_numflock(fakes.INSTANCE, max_fd) - - def test_sum_numfiles(self): - instance_memory_mb = int(fakes.INSTANCETYPE['memory_mb']) - memory_unit_size = int(CONF.ovz_memory_unit_size) - max_fd_per_unit = int(CONF.ovz_file_descriptors_per_unit) - max_fd = int(instance_memory_mb / memory_unit_size) * max_fd_per_unit - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--numfile', - max_fd, run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_numfiles(fakes.INSTANCE, max_fd) - - def test_set_numtcpsock(self): - instance_meta = ovz_utils.format_system_metadata( - fakes.INSTANCE['system_metadata']) - numtcpsock_map = CONF.ovz_numtcpsock_map - flavor_memory = str(instance_meta['instance_type_memory_mb']) - numtcpsock = numtcpsock_map[flavor_memory] - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--numtcpsock', - numtcpsock, run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_numtcpsock( - fakes.INSTANCE, instance_meta['instance_type_memory_mb']) - - def test_set_numtcpsock_no_flag(self): - instance_meta = ovz_utils.format_system_metadata( - fakes.INSTANCE['system_metadata']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--numtcpsock', - CONF.ovz_numtcpsock_default, run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_numtcpsock( - fakes.INSTANCE, - (instance_meta['instance_type_memory_mb'] + 1)) - - def test_set_instance_size_with_instance_type_id(self): - instance_memory_bytes = ((int(fakes.INSTANCETYPE['memory_mb']) - * 1024) * 1024) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - pages = ovz_conn._calc_pages(fakes.INSTANCE['memory_mb']) - memory_unit_size = int(CONF.ovz_memory_unit_size) - max_fd_per_unit = int(CONF.ovz_file_descriptors_per_unit) - max_fd = int( - fakes.INSTANCE['memory_mb'] / memory_unit_size) * max_fd_per_unit - self.mox.StubOutWithMock(ovz_conn, '_percent_of_resource') - ovz_conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']).AndReturn( - float(fakes.INSTANCE['memory_mb']) / - float(fakes.HOSTSTATS['memory_mb'])) - self.mox.StubOutWithMock(ovz_conn, '_set_vmguarpages') - ovz_conn._set_vmguarpages( - fakes.INSTANCE, pages) - self.mox.StubOutWithMock(ovz_conn, '_set_privvmpages') - ovz_conn._set_privvmpages(fakes.INSTANCE, pages) - self.mox.StubOutWithMock(ovz_conn, '_set_kmemsize') - ovz_conn._set_kmemsize(fakes.INSTANCE, instance_memory_bytes) - self.mox.StubOutWithMock(ovz_conn, '_set_numfiles') - ovz_conn._set_numfiles(fakes.INSTANCE, max_fd) - self.mox.StubOutWithMock(ovz_conn, '_set_numflock') - ovz_conn._set_numflock(fakes.INSTANCE, max_fd) - self.mox.StubOutWithMock(ovz_conn, '_set_cpuunits') - ovz_conn._set_cpuunits(fakes.INSTANCE, mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_set_cpulimit') - ovz_conn._set_cpulimit(fakes.INSTANCE, mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_set_cpus') - ovz_conn._set_cpus(fakes.INSTANCE, fakes.INSTANCETYPE['vcpus']) - self.mox.StubOutWithMock(ovz_conn, '_set_ioprio') - ovz_conn._set_ioprio( - fakes.INSTANCE, int(fakes.INSTANCETYPE['memory_mb'])) - self.mox.StubOutWithMock(ovz_conn, '_set_diskspace') - ovz_conn._set_diskspace(fakes.INSTANCE, fakes.INSTANCETYPE['root_gb']) - self.mox.StubOutWithMock(ovz_conn, '_generate_tc_rules') - ovz_conn._generate_tc_rules(fakes.INSTANCE, self.network_info, False) - self.mox.ReplayAll() - ovz_conn._set_instance_size( - fakes.INSTANCE, self.network_info) - - def test_set_instance_size_without_instance_type_id(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - instance_memory_bytes = ((int(fakes.INSTANCETYPE['memory_mb']) - * 1024) * 1024) - pages = ovz_conn._calc_pages(fakes.INSTANCE['memory_mb']) - memory_unit_size = int(CONF.ovz_memory_unit_size) - max_fd_per_unit = int(CONF.ovz_file_descriptors_per_unit) - max_fd = int( - fakes.INSTANCE['memory_mb'] / memory_unit_size) * max_fd_per_unit - self.mox.StubOutWithMock(ovz_conn, '_percent_of_resource') - ovz_conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']).AndReturn( - float(fakes.INSTANCE['memory_mb']) / - float(fakes.HOSTSTATS['memory_mb'])) - self.mox.StubOutWithMock(ovz_conn, '_set_vmguarpages') - ovz_conn._set_vmguarpages( - fakes.INSTANCE, pages) - self.mox.StubOutWithMock(ovz_conn, '_set_privvmpages') - ovz_conn._set_privvmpages(fakes.INSTANCE, pages) - self.mox.StubOutWithMock(ovz_conn, '_set_kmemsize') - ovz_conn._set_kmemsize(fakes.INSTANCE, instance_memory_bytes) - self.mox.StubOutWithMock(ovz_conn, '_set_numfiles') - ovz_conn._set_numfiles(fakes.INSTANCE, max_fd) - self.mox.StubOutWithMock(ovz_conn, '_set_numflock') - ovz_conn._set_numflock(fakes.INSTANCE, max_fd) - self.mox.StubOutWithMock(ovz_conn, '_set_cpuunits') - ovz_conn._set_cpuunits(fakes.INSTANCE, mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_set_cpulimit') - ovz_conn._set_cpulimit(fakes.INSTANCE, mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_set_cpus') - ovz_conn._set_cpus(fakes.INSTANCE, fakes.INSTANCETYPE['vcpus']) - self.mox.StubOutWithMock(ovz_conn, '_set_ioprio') - ovz_conn._set_ioprio( - fakes.INSTANCE, int(fakes.INSTANCETYPE['memory_mb'])) - self.mox.StubOutWithMock(ovz_conn, '_set_diskspace') - ovz_conn._set_diskspace( - fakes.INSTANCE, - ovz_utils.format_system_metadata( - fakes.INSTANCE['system_metadata'])['instance_type_root_gb']) - self.mox.StubOutWithMock(ovz_conn, '_generate_tc_rules') - ovz_conn._generate_tc_rules(fakes.INSTANCE, self.network_info, False) - self.mox.ReplayAll() - ovz_conn._set_instance_size( - fakes.INSTANCE, self.network_info) - - def test_generate_tc_rules(self): - self.mox.StubOutWithMock(openvz_conn.ovzboot, 'OVZBootFile') - openvz_conn.ovzboot.OVZBootFile( - mox.IgnoreArg(), mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(0, 700)) - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata( - fakes.INSTANCE['id']).AndReturn(fakes.METADATA) - self.mox.StubOutWithMock(ovz_utils, 'remove_instance_metadata_key') - ovz_utils.remove_instance_metadata_key( - fakes.INSTANCE['id'], fakes.METAKEY) - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - mox.IgnoreArg(), mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(0, 700)) - self.mox.StubOutWithMock(openvz_conn.ovztc, 'OVZTcRules') - openvz_conn.ovztc.OVZTcRules().MultipleTimes().AndReturn( - fakes.FakeOVZTcRules()) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - ovz_conn._generate_tc_rules(fakes.INSTANCE, self.network_info) - - def test_set_onboot_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--onboot', 'no', '--save', - run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_onboot(fakes.INSTANCE) - - def test_set_onboot_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--onboot', 'no', '--save', - run_as_root=True).AndRaise( - exception.InstanceUnacceptable( - fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_onboot, fakes.INSTANCE) - - def test_set_cpuunits_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpuunits', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', '')) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource(mox.IgnoreArg()).AndReturn(fakes.RES_PERCENT) - self.mox.ReplayAll() - conn._set_cpuunits( - fakes.INSTANCE, conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']) - ) - - def test_set_cpuunits_over_subscribe(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpuunits', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', '')) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource( - mox.IgnoreArg()).AndReturn(fakes.RES_OVER_PERCENT) - self.mox.ReplayAll() - conn._set_cpuunits( - fakes.INSTANCE, conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']) - ) - - def test_set_cpuunits_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpuunits', - mox.IgnoreArg(), run_as_root=True).AndRaise( - processutils.ProcessExecutionError(fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource(mox.IgnoreArg()).AndReturn(fakes.RES_PERCENT) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, conn._set_cpuunits, fakes.INSTANCE, - conn._percent_of_resource(fakes.INSTANCETYPE['memory_mb'])) - - def test_set_cpulimit_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpulimit', - fakes.UTILITY['CPULIMIT'] * fakes.RES_PERCENT, - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource(mox.IgnoreArg()).AndReturn( - fakes.RES_PERCENT - ) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - conn._set_cpulimit( - fakes.INSTANCE, conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']) - ) - - def test_set_cpulimit_over_subscribe(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpulimit', - fakes.UTILITY['CPULIMIT'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource( - mox.IgnoreArg()).AndReturn(fakes.RES_OVER_PERCENT) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - conn._set_cpulimit( - fakes.INSTANCE, conn._percent_of_resource( - fakes.INSTANCETYPE['memory_mb']) - ) - - def test_set_cpulimit_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpulimit', - fakes.UTILITY['CPULIMIT'] * fakes.RES_PERCENT, - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_percent_of_resource') - conn._percent_of_resource(mox.IgnoreArg()).AndReturn(fakes.RES_PERCENT) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, conn._set_cpulimit, fakes.INSTANCE, - conn._percent_of_resource(fakes.INSTANCETYPE['memory_mb'])) - - def test_set_cpus_too_many_vcpus_success(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpus', - fakes.UTILITY['CPULIMIT'] / 100, - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - conn._set_cpus(fakes.INSTANCE, fakes.HOSTSTATS['vcpus'] * 200) - - def test_set_cpus_success(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpus', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - conn._set_cpus(fakes.INSTANCE, fakes.INSTANCETYPE['vcpus']) - - def test_set_cpus_failure(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--cpus', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.assertRaises( - exception.InstanceUnacceptable, conn._set_cpus, fakes.INSTANCE, - fakes.INSTANCETYPE['vcpus']) - - def test_calc_pages_success(self): - # this test is a little sketchy because it is testing the default - # values of memory for instance type id 1. if this value changes then - # we will have a mismatch. - - # TODO(imsplitbit): make this work better. This test is very brittle - # because it relies on the default memory size for flavor 1 never - # changing. Need to fix this. - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertEqual( - conn._calc_pages(fakes.INSTANCE['memory_mb']), 524288) - - def test_get_cpuunits_capability_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzcpucheck', run_as_root=True).AndReturn( - (fakes.CPUCHECKNOCONT, fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_utils.get_cpuunits_capability() - - def test_get_cpuunits_capability_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzcpucheck', run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, ovz_utils.get_cpuunits_capability) - - def test_get_cpuunits_usage_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzcpucheck', '-v', run_as_root=True).AndReturn( - (fakes.CPUCHECKCONT, fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._get_cpuunits_usage() - - def test_get_cpuunits_usage_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzcpucheck', '-v', run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._get_cpuunits_usage) - - def test_percent_of_resource(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, 'utility') - conn.utility = fakes.UTILITY - self.mox.ReplayAll() - self.assertEqual( - float, type(conn._percent_of_resource(fakes.INSTANCE['memory_mb'])) - ) - - def test_set_ioprio_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--ioprio', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - conn._set_ioprio( - fakes.INSTANCE, fakes.INSTANCE['memory_mb']) - - def test_set_ioprio_too_high_success(self): - # Artificially inflate the memory for the instance to test the case - # where the logarithm would result in a value higher than 7, the - # code should set 7 as the cap. - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--ioprio', - 7, run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - conn._set_ioprio( - fakes.INSTANCE, fakes.INSTANCE['memory_mb'] * 100) - - def test_set_ioprio_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--ioprio', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, conn._set_ioprio, fakes.INSTANCE, - fakes.INSTANCE['memory_mb']) - - def test_set_diskspace_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--diskspace', - mox.IgnoreArg(), run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._set_diskspace(fakes.INSTANCE, fakes.INSTANCETYPE['root_gb']) - - def test_set_diskspace_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--diskspace', - mox.IgnoreArg(), run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._set_diskspace, - fakes.INSTANCE, fakes.INSTANCETYPE['root_gb']) - - def test_attach_volumes_success(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, 'attach_volume') - conn.attach_volume( - fakes.BDM['block_device_mapping'][0]['connection_info'], - fakes.INSTANCE['name'], - (fakes.BDM['block_device_mapping'][0] - ['connection_info']['mount_device'])) - self.mox.ReplayAll() - conn._attach_volumes(fakes.INSTANCE['name'], fakes.BDM) - - def test_attach_volume(self): - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile( - self.ext_str_filename, self.ext_str_permissions).AndReturn( - fakes.FakeOvzFile( - self.ext_str_filename, self.ext_str_permissions)) - self.mox.StubOutWithMock(openvz_conn.ovziscsi, 'OVZISCSIStorageDriver') - openvz_conn.ovziscsi.OVZISCSIStorageDriver( - fakes.INSTANCE['id'], - fakes.BDM['block_device_mapping'][0]['mount_device'], - fakes.BDM['block_device_mapping'][0]['connection_info']).AndReturn( - fakes.FakeOVZISCSIStorageDriver()) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - ovz_conn.attach_volume( - fakes.BDM['block_device_mapping'][0]['connection_info'], - fakes.INSTANCE, - fakes.BDM['block_device_mapping'][0]['mount_device']) - - def test_detach_volume(self): - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile( - self.ext_str_filename, self.ext_str_permissions).AndReturn( - fakes.FakeOvzFile( - self.ext_str_filename, self.ext_str_permissions)) - self.mox.StubOutWithMock(openvz_conn.ovziscsi, 'OVZISCSIStorageDriver') - openvz_conn.ovziscsi.OVZISCSIStorageDriver( - fakes.INSTANCE['id'], - fakes.BDM['block_device_mapping'][0]['mount_device'], - fakes.BDM['block_device_mapping'][0]['connection_info']).AndReturn( - fakes.FakeOVZISCSIStorageDriver()) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.ReplayAll() - ovz_conn.detach_volume( - fakes.BDM['block_device_mapping'][0]['connection_info'], - fakes.INSTANCE) - - def test_get_available_resource(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, 'get_host_stats') - ovz_conn.get_host_stats(refresh=True).AndReturn(fakes.HOSTSTATS) - self.mox.ReplayAll() - ovz_conn.get_available_resource(None) - - def test_get_volume_connector(self): - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_iscsi_initiator') - openvz_conn.ovz_utils.get_iscsi_initiator().AndReturn( - fakes.ISCSIINITIATOR) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - iscsi_initiator = ovz_conn.get_volume_connector(fakes.INSTANCE) - self.assertTrue(isinstance(iscsi_initiator, dict)) - self.assertEqual(CONF.my_ip, iscsi_initiator['ip']) - self.assertEqual(fakes.ISCSIINITIATOR, iscsi_initiator['initiator']) - self.assertEqual(CONF.host, iscsi_initiator['host']) - - def test_gratuitous_arp_all_addresses(self): - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn, '_send_garp') - conn._send_garp( - fakes.INSTANCE['id'], mox.IgnoreArg(), - mox.IgnoreArg()).MultipleTimes() - self.mox.ReplayAll() - conn._gratuitous_arp_all_addresses(fakes.INSTANCE, self.network_info) - - def test_send_garp_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'exec2', fakes.INSTANCE['id'], 'arping', '-q', '-c', '5', - '-A', '-I', - self.network_info[0]['network'].get_meta('bridge_interface'), - self.network_info[0]['network']['subnets'][0]['ips'][0]['address'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - conn._send_garp( - fakes.INSTANCE['id'], - self.network_info[0]['network']['subnets'][0]['ips'][0]['address'], - self.network_info[0]['network'].get_meta('bridge_interface')) - - def test_send_garp_faiure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'exec2', fakes.INSTANCE['id'], 'arping', '-q', '-c', '5', - '-A', '-I', - self.network_info[0]['network'].get_meta('bridge_interface'), - self.network_info[0]['network']['subnets'][0]['ips'][0]['address'], - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn._send_garp, - fakes.INSTANCE['id'], - self.network_info[0]['network']['subnets'][0]['ips'][0]['address'], - self.network_info[0]['network'].get_meta('bridge_interface')) - - def test_init_host_success(self): - self.mox.StubOutWithMock(openvz_conn.ovzboot, 'OVZBootFile') - openvz_conn.ovzboot.OVZBootFile( - mox.IgnoreArg(), mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(0, 700)) - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - mox.IgnoreArg(), mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(0, 700)) - self.mox.StubOutWithMock(openvz_conn.ovztc, 'OVZTcRules') - openvz_conn.ovztc.OVZTcRules().AndReturn(fakes.FakeOVZTcRules()) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_refresh_host_stats') - ovz_conn._refresh_host_stats() - self.mox.StubOutWithMock(ovz_conn, '_get_cpulimit') - ovz_conn._get_cpulimit() - self.mox.ReplayAll() - ovz_conn.init_host() - - def test_get_host_stats(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_refresh_host_stats') - ovz_conn._refresh_host_stats() - self.mox.ReplayAll() - result = ovz_conn.get_host_stats(True) - self.assertTrue(isinstance(result, dict)) - - def test_refresh_host_stats(self): - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_vcpu_total') - openvz_conn.ovz_utils.get_vcpu_total().AndReturn( - fakes.HOSTSTATS['vcpus']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_vcpu_used') - openvz_conn.ovz_utils.get_vcpu_used().AndReturn( - fakes.HOSTSTATS['vcpus_used']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_cpuinfo') - openvz_conn.ovz_utils.get_cpuinfo().AndReturn( - fakes.PROCINFO) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_memory_mb_total') - openvz_conn.ovz_utils.get_memory_mb_total().AndReturn( - fakes.HOSTSTATS['memory_mb']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_memory_mb_used') - openvz_conn.ovz_utils.get_memory_mb_used().AndReturn( - fakes.HOSTSTATS['memory_mb_used']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_local_gb_total') - openvz_conn.ovz_utils.get_local_gb_total().AndReturn( - fakes.HOSTSTATS['disk_total']) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'get_local_gb_used') - openvz_conn.ovz_utils.get_local_gb_used().AndReturn( - fakes.HOSTSTATS['disk_used']) - self.mox.StubOutWithMock( - openvz_conn.ovz_utils, 'get_hypervisor_version') - openvz_conn.ovz_utils.get_hypervisor_version().AndReturn( - fakes.HOSTSTATS['hypervisor_version']) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._refresh_host_stats() - - def test_set_hostname_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--hostname', - fakes.INSTANCE['hostname'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_hostname(fakes.INSTANCE) - - def test_set_hostname_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--hostname', - fakes.INSTANCE['hostname'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn._set_hostname, - fakes.INSTANCE) - - def test_set_name_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--name', - fakes.INSTANCE['name'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._set_name(fakes.INSTANCE) - - def test_set_name_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'set', fakes.INSTANCE['id'], '--save', '--name', - fakes.INSTANCE['name'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn._set_name, fakes.INSTANCE) - - def test_find_by_name_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzlist', '-H', '-o', 'ctid,status,name', '--all', '--name_filter', - fakes.INSTANCE['name'], run_as_root=True).AndReturn( - (fakes.VZLISTDETAIL, fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - meta = ovz_conn._find_by_name(fakes.INSTANCE['name']) - self.assertEqual(fakes.INSTANCE['hostname'], meta['name']) - self.assertEqual(str(fakes.INSTANCE['id']), meta['id']) - self.assertEqual('running', meta['state']) - - def test_find_by_name_not_found(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzlist', '-H', '-o', 'ctid,status,name', '--all', '--name_filter', - fakes.INSTANCE['name'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.NotFound, ovz_conn._find_by_name, fakes.INSTANCE['name']) - - def test_find_by_name_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzlist', '-H', '-o', 'ctid,status,name', '--all', '--name_filter', - fakes.INSTANCE['name'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn._find_by_name, - fakes.INSTANCE['name']) - - def test_plug_vifs(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.vif_driver = mox.MockAnything() - ovz_conn.vif_driver.plug( - fakes.INSTANCE, mox.IgnoreArg(), mox.IgnoreArg()) - self.mox.ReplayAll() - ovz_conn.plug_vifs(fakes.INSTANCE, self.network_info) - - def test_reboot_success(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_conn.ovzboot, 'OVZBootFile') - openvz_conn.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - mox.IgnoreArg()).MultipleTimes() - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'restart', fakes.INSTANCE['id'], - run_as_root=True).AndReturn(('', '')) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info( - fakes.INSTANCE).MultipleTimes().AndReturn(fakes.GOODSTATUS) - self.mox.ReplayAll() - timer = ovz_conn.reboot( - fakes.ADMINCONTEXT, fakes.INSTANCE, self.network_info, None) - timer.wait() - - def test_reboot_fail_in_get_info(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - mox.IgnoreArg()).MultipleTimes() - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'restart', fakes.INSTANCE['id'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndRaise(exception.NotFound) - self.mox.ReplayAll() - timer = ovz_conn.reboot( - fakes.ADMINCONTEXT, fakes.INSTANCE, self.network_info, None) - self.assertRaises(exception.NotFound, timer.wait) - - def test_reboot_fail_because_not_found(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - mox.IgnoreArg()).MultipleTimes() - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'restart', fakes.INSTANCE['id'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndReturn(fakes.NOSTATUS) - self.mox.ReplayAll() - timer = ovz_conn.reboot( - fakes.ADMINCONTEXT, fakes.INSTANCE, self.network_info, None) - timer.wait() - - def test_reboot_failure(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - {'power_state': power_state.PAUSED}) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'restart', fakes.INSTANCE['id'], - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn.reboot, - fakes.ADMINCONTEXT, fakes.INSTANCE, self.network_info, None) - - def test_inject_files(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, 'inject_file') - ovz_conn.inject_file( - fakes.INSTANCE, mox.IgnoreArg(), - base64.b64encode(fakes.FILECONTENTS)).MultipleTimes() - self.mox.ReplayAll() - ovz_conn._inject_files(fakes.INSTANCE, fakes.FILESTOINJECT) - - def test_inject_file(self): - full_path = '%s/%s/%s' % (CONF.ovz_ve_private_dir, - fakes.INSTANCE['id'], - fakes.FILESTOINJECT[0][0]) - self.mox.StubOutWithMock(openvz_conn.ovzfile, 'OVZFile') - openvz_conn.ovzfile.OVZFile( - full_path, 644).AndReturn(fakes.FakeOvzFile(full_path, 644)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.inject_file( - fakes.INSTANCE, base64.b64encode(fakes.FILESTOINJECT[0][0]), - base64.b64encode(fakes.FILESTOINJECT[0][1])) - - def test_set_admin_password_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'exec2', fakes.INSTANCE['id'], 'echo', - 'root:%s' % fakes.ROOTPASS, '|', 'chpasswd', - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.set_admin_password( - fakes.ADMINCONTEXT, fakes.INSTANCE['id'], fakes.ROOTPASS) - - def test_set_admin_password_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'exec2', fakes.INSTANCE['id'], 'echo', - 'root:%s' % fakes.ROOTPASS, '|', 'chpasswd', - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, ovz_conn.set_admin_password, - fakes.ADMINCONTEXT, fakes.INSTANCE['id'], fakes.ROOTPASS) - - def test_pause_success(self): - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'stop', fakes.INSTANCE['id'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.SHUTDOWN}) - self.mox.ReplayAll() - conn.pause(fakes.INSTANCE) - - def test_pause_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'stop', fakes.INSTANCE['id'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.StubOutWithMock(openvz_conn.ovzshutdown, 'OVZShutdownFile') - openvz_conn.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn.pause, fakes.INSTANCE) - - def test_suspend_success(self): - self.mox.StubOutWithMock(openvz_conn.context, 'get_admin_context') - openvz_conn.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--suspend', - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - {'power_state': power_state.SUSPENDED}) - self.mox.ReplayAll() - conn.suspend(fakes.INSTANCE) - - def test_suspend_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--suspend', - run_as_root=True).AndRaise( - exception.InstanceUnacceptable( - fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn.suspend, fakes.INSTANCE) - - def test_suspend_dberror(self): - self.mox.StubOutWithMock(openvz_conn.context, 'get_admin_context') - openvz_conn.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--suspend', - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - {'power_state': power_state.SUSPENDED}).AndRaise( - exception.InstanceNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn.suspend(fakes.INSTANCE) - - def test_unpause_success(self): - self.mox.StubOutWithMock(openvz_conn.ovzboot, 'OVZBootFile') - openvz_conn.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'start', fakes.INSTANCE['id'], - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), True) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.RUNNING}) - - self.mox.ReplayAll() - conn.unpause(fakes.INSTANCE) - - def test_unpause_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'start', fakes.INSTANCE['id'], run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn.unpause, fakes.INSTANCE) - - def test_resume_success(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--resume', - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), True) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.RUNNING}) - - self.mox.ReplayAll() - conn.resume(fakes.INSTANCE, self.network_info) - - def test_resume_db_not_found(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--resume', - run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), True) - self.mox.StubOutWithMock(conn.virtapi, 'instance_update') - conn.virtapi.instance_update( - mox.IgnoreArg(), fakes.INSTANCE['uuid'], - {'power_state': power_state.RUNNING}).AndRaise( - exception.InstanceNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn.resume(fakes.INSTANCE, self.network_info) - - def test_resume_failure(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'vzctl', 'chkpnt', fakes.INSTANCE['id'], '--resume', - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - conn = openvz_conn.OpenVzDriver(manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.InstanceUnacceptable, conn.resume, fakes.INSTANCE, None, - None) - - def test_clean_orphaned_files(self): - self.mox.StubOutWithMock(openvz_conn.os, 'listdir') - openvz_conn.os.listdir(mox.IgnoreArg()).MultipleTimes().AndReturn( - fakes.OSLISTDIR) - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'rm', '-f', mox.IgnoreArg(), - run_as_root=True).MultipleTimes().AndReturn(('', '')) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._clean_orphaned_files(fakes.INSTANCE['id']) - - def test_destroy_fail_on_exec(self): - self.mox.StubOutWithMock( - openvz_conn.ovz_utils, 'remove_instance_metadata') - openvz_conn.ovz_utils.remove_instance_metadata(fakes.INSTANCE['id']) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.vif_driver = mox.MockAnything() - ovz_conn.vif_driver.unplug( - fakes.INSTANCE, mox.IgnoreArg(), mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_stop') - ovz_conn._stop(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndReturn(fakes.GOODSTATUS) - self.mox.StubOutWithMock(ovz_conn, '_destroy') - ovz_conn._destroy(fakes.INSTANCE['id']).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceTerminationFailure, ovz_conn.destroy, - fakes.INSTANCE, self.network_info) - - def test_destroy_success(self): - self.mox.StubOutWithMock( - openvz_conn.ovz_utils, 'remove_instance_metadata') - openvz_conn.ovz_utils.remove_instance_metadata(fakes.INSTANCE['id']) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.vif_driver = mox.MockAnything() - ovz_conn.vif_driver.unplug( - fakes.INSTANCE, mox.IgnoreArg(), mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - dir(ovz_conn.get_info) - ovz_conn.get_info(fakes.INSTANCE).AndReturn( - fakes.GOODSTATUS) - ovz_conn.get_info(fakes.INSTANCE).AndRaise(exception.InstanceNotFound( - fakes.ERRORMSG)) - self.mox.StubOutWithMock(ovz_conn, '_stop') - ovz_conn._stop(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_destroy') - ovz_conn._destroy(fakes.INSTANCE['id']) - self.mox.StubOutWithMock(ovz_conn, '_clean_orphaned_files') - ovz_conn._clean_orphaned_files(fakes.INSTANCE['id']) - self.mox.StubOutWithMock(ovz_conn, '_detach_volumes') - ovz_conn._detach_volumes(fakes.INSTANCE, fakes.BDM) - self.mox.ReplayAll() - ovz_conn.destroy(fakes.INSTANCE, self.network_info, fakes.BDM) - - def test_get_info_running_state(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndReturn( - fakes.FINDBYNAME) - self.mox.ReplayAll() - meta = ovz_conn.get_info(fakes.INSTANCE) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta['state'], power_state.RUNNING) - - def test_get_info_shutdown_state(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndReturn( - fakes.FINDBYNAMESHUTDOWN) - self.mox.ReplayAll() - meta = ovz_conn.get_info(fakes.INSTANCE) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta['state'], power_state.SHUTDOWN) - - def test_get_info_no_state(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndReturn( - fakes.FINDBYNAMENOSTATE) - self.mox.ReplayAll() - meta = ovz_conn.get_info(fakes.INSTANCE) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta['state'], power_state.NOSTATE) - - def test_get_info_state_is_None(self): - BADFINDBYNAME = fakes.FINDBYNAME.copy() - BADFINDBYNAME['state'] = None - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndReturn(BADFINDBYNAME) - self.mox.ReplayAll() - meta = ovz_conn.get_info(fakes.INSTANCE) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta['state'], power_state.NOSTATE) - - def test_get_info_state_is_shutdown(self): - BADFINDBYNAME = fakes.FINDBYNAME.copy() - BADFINDBYNAME['state'] = 'shutdown' - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndReturn(BADFINDBYNAME) - self.mox.ReplayAll() - meta = ovz_conn.get_info(fakes.INSTANCE) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta['state'], power_state.SHUTDOWN) - - def test_get_info_notfound(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_find_by_name') - ovz_conn._find_by_name(fakes.INSTANCE['name']).AndRaise( - exception.NotFound) - self.mox.ReplayAll() - self.assertRaises( - exception.NotFound, ovz_conn.get_info, fakes.INSTANCE) - - def test_percent_of_memory_over_subscribe(self): - # Force the utility storage to have really low memory so as to test the - # code that doesn't allow more than a 1.x multiplier. - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.utility['MEMORY_MB'] = 16 - self.mox.StubOutWithMock(ovz_utils, 'get_memory_mb_total') - ovz_utils.get_memory_mb_total().AndReturn(1024) - self.mox.ReplayAll() - self.assertEqual( - 1, ovz_conn._percent_of_resource(fakes.INSTANCE['memory_mb'])) - - def test_percent_of_memory_normal_subscribe(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.utility['MEMORY_MB'] = 16384 - # get_memory_mb_total just returns 1 if you're not on linux - self.mox.StubOutWithMock(ovz_utils, 'get_memory_mb_total') - ovz_utils.get_memory_mb_total().AndReturn(16384) - self.mox.ReplayAll() - self.assertTrue( - ovz_conn._percent_of_resource(fakes.INSTANCE['memory_mb']) < 1) - - def test_get_cpulimit_success(self): - self.mox.StubOutWithMock(ovz_utils.multiprocessing, 'cpu_count') - ovz_utils.multiprocessing.cpu_count().AndReturn(2) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._get_cpulimit() - self.assertEqual(ovz_conn.utility['CPULIMIT'], 200) - - def test_spawn_success(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_get_cpuunits_usage') - ovz_conn._get_cpuunits_usage() - self.mox.StubOutWithMock(ovz_conn, '_cache_image') - ovz_conn._cache_image(fakes.ADMINCONTEXT, fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_create_vz') - ovz_conn._create_vz(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_vz_os_hint') - ovz_conn._set_vz_os_hint(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_configure_vz') - ovz_conn._configure_vz(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_description') - ovz_conn._set_description(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_setup_networking') - ovz_conn._setup_networking(fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, '_set_onboot') - ovz_conn._set_onboot(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_name') - ovz_conn._set_name(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, 'plug_vifs') - ovz_conn.plug_vifs(fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, '_set_hostname') - ovz_conn._set_hostname(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_attach_volumes') - ovz_conn._attach_volumes(fakes.INSTANCE, fakes.BDM) - self.mox.StubOutWithMock(ovz_conn, '_inject_files') - ovz_conn._inject_files(fakes.INSTANCE, fakes.FILESTOINJECT) - self.mox.StubOutWithMock(ovz_conn, '_start') - ovz_conn._start(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_gratuitous_arp_all_addresses') - ovz_conn._gratuitous_arp_all_addresses( - fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, 'set_admin_password') - ovz_conn.set_admin_password( - fakes.ADMINCONTEXT, fakes.INSTANCE['id'], - fakes.INSTANCE['admin_pass']) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndReturn(fakes.GOODSTATUS) - self.mox.ReplayAll() - timer = ovz_conn.spawn( - fakes.ADMINCONTEXT, fakes.INSTANCE, None, fakes.FILESTOINJECT, - fakes.ROOTPASS, self.network_info, fakes.BDM) - timer.wait() - - def test_spawn_failure(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn.virtapi, 'instance_update') - ovz_conn.virtapi.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], mox.IgnoreArg()) - self.mox.StubOutWithMock(ovz_conn, '_get_cpuunits_usage') - ovz_conn._get_cpuunits_usage() - self.mox.StubOutWithMock(ovz_conn, '_cache_image') - ovz_conn._cache_image(fakes.ADMINCONTEXT, fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_create_vz') - ovz_conn._create_vz(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_vz_os_hint') - ovz_conn._set_vz_os_hint(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_configure_vz') - ovz_conn._configure_vz(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_description') - ovz_conn._set_description(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_setup_networking') - ovz_conn._setup_networking(fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, '_set_onboot') - ovz_conn._set_onboot(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_name') - ovz_conn._set_name(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, 'plug_vifs') - ovz_conn.plug_vifs(fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, '_set_hostname') - ovz_conn._set_hostname(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_attach_volumes') - ovz_conn._attach_volumes(fakes.INSTANCE, fakes.BDM) - self.mox.StubOutWithMock(ovz_conn, '_inject_files') - ovz_conn._inject_files(fakes.INSTANCE, fakes.FILESTOINJECT) - self.mox.StubOutWithMock(ovz_conn, '_start') - ovz_conn._start(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_gratuitous_arp_all_addresses') - ovz_conn._gratuitous_arp_all_addresses( - fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, 'set_admin_password') - ovz_conn.set_admin_password( - fakes.ADMINCONTEXT, fakes.INSTANCE['id'], - fakes.INSTANCE['admin_pass']) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndRaise(exception.NotFound) - self.mox.ReplayAll() - timer = ovz_conn.spawn( - fakes.ADMINCONTEXT, fakes.INSTANCE, None, fakes.FILESTOINJECT, - fakes.ROOTPASS, self.network_info, fakes.BDM) - timer.wait() - - def test_snapshot(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.snapshot( - fakes.ADMINCONTEXT, fakes.INSTANCE, fakes.INSTANCE['image_ref'], - True) - - def test_rescue(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.rescue( - fakes.ADMINCONTEXT, fakes.INSTANCE, self.network_info, - fakes.INSTANCE['image_ref'], fakes.ROOTPASS) - - def test_unrescue(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.unrescue(fakes.INSTANCE, self.network_info) - - def test_get_diagnostics(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.get_diagnostics(fakes.INSTANCE['name']) - - def test_list_disks(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.list_disks(fakes.INSTANCE['name']) - self.assertTrue(isinstance(result, list)) - self.assertEqual(result[0], 'A_DISK') - - def test_list_interfaces(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.list_interfaces(fakes.INSTANCE['name']) - self.assertTrue(isinstance(result, list)) - self.assertEqual(result[0], 'A_VIF') - - def test_block_stats(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.block_stats( - fakes.INSTANCE['name'], 'c49a7247-731e-4135-8420-7a3c67002582') - self.assertTrue(isinstance(result, list)) - self.assertEqual(result[0], 0L) - self.assertEqual(result[1], 0L) - self.assertEqual(result[2], 0L) - self.assertEqual(result[3], 0L) - self.assertEqual(result[4], None) - - def test_interface_stats(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.interface_stats(fakes.INSTANCE['name'], 'eth0') - self.assertTrue(isinstance(result, list)) - self.assertEqual(result[0], 0L) - self.assertEqual(result[1], 0L) - self.assertEqual(result[2], 0L) - self.assertEqual(result[3], 0L) - self.assertEqual(result[4], 0L) - self.assertEqual(result[5], 0L) - self.assertEqual(result[6], 0L) - self.assertEqual(result[7], 0L) - - def test_get_console_output(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.get_console_output(fakes.INSTANCE) - self.assertTrue(isinstance(result, str)) - self.assertEqual(result, 'FAKE CONSOLE OUTPUT') - - def test_get_ajax_console(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.get_ajax_console(fakes.INSTANCE) - self.assertTrue(isinstance(result, str)) - self.assertEqual(result, 'http://fakeajaxconsole.com/?token=FAKETOKEN') - - def test_get_console_pool_info(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.get_console_pool_info(None) - self.assertTrue(isinstance(result, dict)) - self.assertEqual(result['address'], '127.0.0.1') - self.assertEqual(result['username'], 'fakeuser') - self.assertEqual(result['password'], 'fakepassword') - - def test_refresh_security_group_rules(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.refresh_security_group_rules(None) - self.assertTrue(result) - - def test_refresh_security_group_members(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.refresh_security_group_members(None) - self.assertTrue(result) - - def test_poll_rebooting_instances(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.poll_rebooting_instances(5, fakes.INSTANCES) - - def test_poll_rescued_instances(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.poll_rescued_instances(5) - - def test_power_off(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.power_off(fakes.INSTANCE) - - def test_power_on(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.power_on(fakes.INSTANCE) - - def test_compare_cpu(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.compare_cpu(fakes.PROCINFO) - - def test_poll_unconfirmed_resizes(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.poll_unconfirmed_resizes(None) - - def test_host_power_action(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.host_power_action(CONF.host, 'reboot') - - def test_set_host_enabled(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.set_host_enabled(CONF.host, True) - - def test_ensure_filtering_rules_for_instance(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.ensure_filtering_rules_for_instance( - fakes.INSTANCE, self.network_info) - - def test_unfilter_instance(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.unfilter_instance(fakes.INSTANCE, self.network_info) - - def test_refresh_provider_fw_rules(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.refresh_provider_fw_rules() - - def test_agent_update(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.agent_update(fakes.INSTANCE, None, None) - - def test_update_host_status(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.update_host_status() - - def test_get_all_bw_usage(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.get_all_bw_usage(fakes.INSTANCES, 'now') - self.assertTrue(isinstance(result, list)) - self.assertTrue(len(result) == 0) - - def test_snapshot_instance(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - result = ovz_conn.snapshot_instance( - fakes.ADMINCONTEXT, fakes.INSTANCE['id'], - fakes.INSTANCE['image_ref']) - - def test_resize(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.resize(fakes.INSTANCE, None) - - def test_get_host_ip_addr(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.get_host_ip_addr() - - def test_migrate_disk_and_power_off_success_with_storage(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_stop') - ovz_conn._stop(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_pymigration_send_to_host') - ovz_conn._pymigration_send_to_host( - fakes.INSTANCE, ovz_utils.generate_network_dict( - fakes.INSTANCE['id'], self.network_info), - fakes.BDM, fakes.DESTINATION, False) - self.mox.StubOutWithMock(ovz_conn, '_detach_volumes') - ovz_conn._detach_volumes(fakes.INSTANCE, fakes.BDM, True, False) - self.mox.ReplayAll() - ovz_conn.migrate_disk_and_power_off( - fakes.ADMINCONTEXT, fakes.INSTANCE, fakes.DESTINATION, - fakes.INSTANCETYPE, self.network_info, fakes.BDM) - - def test_migrate_disk_and_power_off_success_without_storage(self): - INSTANCE = fakes.INSTANCE.copy() - INSTANCE['block_device_mapping'] = {} - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, 'suspend') - ovz_conn.suspend(INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_pymigration_send_to_host') - ovz_conn._pymigration_send_to_host( - INSTANCE, ovz_utils.generate_network_dict( - INSTANCE['id'], self.network_info), - None, fakes.DESTINATION, True) - self.mox.ReplayAll() - ovz_conn.migrate_disk_and_power_off( - fakes.ADMINCONTEXT, INSTANCE, fakes.DESTINATION, - fakes.INSTANCETYPE, self.network_info) - - def test_migrate_disk_and_power_off_no_dest(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.assertRaises( - exception.MigrationError, ovz_conn.migrate_disk_and_power_off, - fakes.ADMINCONTEXT, fakes.INSTANCE, None, fakes.INSTANCETYPE, - self.network_info) - - def test_migrate_disk_and_power_off_same_host(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_utils, 'save_instance_metadata') - ovz_utils.save_instance_metadata( - fakes.INSTANCE['id'], 'migration_type', 'resize_in_place') - self.mox.ReplayAll() - ovz_conn.migrate_disk_and_power_off( - fakes.ADMINCONTEXT, fakes.INSTANCE, CONF.host, - fakes.INSTANCETYPE, self.network_info) - - def test_pymigration_send_to_host(self): - self.mox.StubOutWithMock( - migration.OVZMigration, 'dump_and_transfer_instance') - migration.OVZMigration.dump_and_transfer_instance() - self.mox.StubOutWithMock(migration.OVZMigration, 'send') - migration.OVZMigration.send() - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._pymigration_send_to_host( - fakes.INSTANCE, self.network_info, fakes.BDM, - fakes.DESTINATION, False) - - def test_vzmigration_send_to_host(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'vzmigrate', '--online', '-r', 'yes', '-v', fakes.DESTINATION, - fakes.INSTANCE['id'], run_as_root=True) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._vzmigration_send_to_host(fakes.INSTANCE, fakes.DESTINATION) - - def test_finish_migration_resize_in_place(self): - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn( - {'migration_type': 'resize_in_place'}) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE, self.network_info, False) - self.mox.ReplayAll() - ovz_conn.finish_migration( - fakes.ADMINCONTEXT, None, fakes.INSTANCE, None, self.network_info, - None, None, fakes.BDM) - - def test_finish_migration_no_resize(self): - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn({}) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_attach_volumes') - ovz_conn._attach_volumes(fakes.INSTANCE, fakes.BDM) - self.mox.StubOutWithMock(ovz_conn, '_pymigrate_finish_migration') - ovz_conn._pymigrate_finish_migration( - fakes.INSTANCE, self.network_info, False) - self.mox.StubOutWithMock(ovz_conn, '_set_name') - ovz_conn._set_name(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_description') - ovz_conn._set_description(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_generate_tc_rules') - ovz_conn._generate_tc_rules(fakes.INSTANCE, self.network_info, True) - self.mox.StubOutWithMock(ovz_conn, '_start') - ovz_conn._start(fakes.INSTANCE) - self.mox.ReplayAll() - ovz_conn.finish_migration( - fakes.ADMINCONTEXT, None, fakes.INSTANCE, None, self.network_info, - None, False, fakes.BDM) - - def test_finish_migration_resize(self): - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn({}) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_attach_volumes') - ovz_conn._attach_volumes(fakes.INSTANCE, fakes.BDM) - self.mox.StubOutWithMock(ovz_conn, '_pymigrate_finish_migration') - ovz_conn._pymigrate_finish_migration( - fakes.INSTANCE, self.network_info, False) - self.mox.StubOutWithMock(ovz_conn, '_set_name') - ovz_conn._set_name(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_set_instance_size') - ovz_conn._set_instance_size(fakes.INSTANCE, self.network_info, True) - self.mox.StubOutWithMock(ovz_conn, '_set_description') - ovz_conn._set_description(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, '_start') - ovz_conn._start(fakes.INSTANCE) - self.mox.ReplayAll() - ovz_conn.finish_migration( - fakes.ADMINCONTEXT, None, fakes.INSTANCE, None, self.network_info, - None, True, fakes.BDM) - - def test_pymigrate_finish_migration(self): - self.mox.StubOutWithMock(migration.OVZMigration, 'undump_instance') - migration.OVZMigration.undump_instance() - self.mox.StubOutWithMock(migration.OVZMigration, 'cleanup_destination') - migration.OVZMigration.cleanup_destination() - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn._pymigrate_finish_migration( - fakes.INSTANCE, self.network_info, False) - - def test_vzmigrate_setup_dest_host(self): - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, '_stop') - ovz_conn._stop(fakes.INSTANCE) - self.mox.StubOutWithMock(ovz_conn, 'plug_vifs') - ovz_conn.plug_vifs(fakes.INSTANCE, self.network_info) - self.mox.StubOutWithMock(ovz_conn, '_start') - ovz_conn._start(fakes.INSTANCE) - self.mox.ReplayAll() - ovz_conn._vzmigrate_setup_dest_host(fakes.INSTANCE, self.network_info) - - def test_confirm_migration_resize_in_place(self): - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn( - {'migration_type': 'resize_in_place'}) - self.mox.StubOutWithMock(ovz_utils, 'remove_instance_metadata_key') - ovz_utils.remove_instance_metadata_key( - fakes.INSTANCE['id'], 'migration_type') - self.mox.StubOutWithMock(openvz_conn.ext_storage, 'OVZExtStorage') - openvz_conn.ext_storage.OVZExtStorage(fakes.INSTANCE['id']).AndReturn( - fakes.FakeOVZExtStorage(fakes.INSTANCE['id'])) - self.mox.ReplayAll() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - ovz_conn.confirm_migration(None, fakes.INSTANCE, self.network_info) - - def test_confirm_migration(self): - self.mox.StubOutWithMock(migration.OVZMigration, 'cleanup_source') - migration.OVZMigration.cleanup_source() - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn({}) - self.mox.StubOutWithMock(openvz_conn.ext_storage, 'OVZExtStorage') - openvz_conn.ext_storage.OVZExtStorage(fakes.INSTANCE['id']).AndReturn( - fakes.FakeOVZExtStorage(fakes.INSTANCE['id'])) - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, 'get_info') - ovz_conn.get_info(fakes.INSTANCE).AndReturn(fakes.SHUTDOWNSTATUS) - self.mox.StubOutWithMock(ovz_conn, '_destroy') - ovz_conn._destroy(fakes.INSTANCE['id']) - self.mox.StubOutWithMock(ovz_conn, '_clean_orphaned_files') - ovz_conn._clean_orphaned_files(fakes.INSTANCE['id']) - self.mox.ReplayAll() - ovz_conn.confirm_migration(None, fakes.INSTANCE, self.network_info) - - def test_finish_revert_migration(self): - self.mox.StubOutWithMock(ovz_utils, 'read_instance_metadata') - ovz_utils.read_instance_metadata(fakes.INSTANCE['id']).AndReturn({}) - self.mox.StubOutWithMock(migration.OVZMigration, 'cleanup_files') - migration.OVZMigration.cleanup_files() - ovz_conn = openvz_conn.OpenVzDriver( - manager.ComputeVirtAPI(None), False) - self.mox.StubOutWithMock(ovz_conn, 'resume') - ovz_conn.resume(fakes.INSTANCE, self.network_info) - self.mox.ReplayAll() - ovz_conn.finish_revert_migration( - fakes.INSTANCE, self.network_info, None) diff --git a/ovznovadriver/tests/openvz/test_ext_storage.py b/ovznovadriver/tests/openvz/test_ext_storage.py deleted file mode 100644 index 60b6124..0000000 --- a/ovznovadriver/tests/openvz/test_ext_storage.py +++ /dev/null @@ -1,107 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -import json -from nova import test -from nova.tests.openvz import fakes -from ovznovadriver.openvz.file_ext import ext_storage -import os -from oslo.config import cfg - -CONF = cfg.CONF - - -class OpenVzExtStorageTestCase(test.TestCase): - def setUp(self): - super(OpenVzExtStorageTestCase, self).setUp() - self.filename = '%s/%s.ext_storage' % (CONF.ovz_config_dir, - fakes.INSTANCE['id']) - self.filename = os.path.abspath(self.filename) - self.permissions = 600 - - def test_new_object(self): - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - self.assertEqual(ext_str.instance_id, fakes.INSTANCE['id']) - self.assertEqual(ext_str.local_store.filename, self.filename) - self.assertEqual(ext_str.local_store.permissions, self.permissions) - - def test_load_volumes(self): - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - self.assertTrue(isinstance(ext_str._volumes, dict)) - - def test_add_volume_success(self): - BDM = fakes.BDM['block_device_mapping'][0] - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - for bdm in fakes.BDM['block_device_mapping']: - ext_str.add_volume(bdm['mount_device'], bdm['connection_info']) - - self.assertTrue(BDM['mount_device'] in ext_str._volumes) - self.assertEqual( - ext_str._volumes[BDM['mount_device']], BDM['connection_info']) - - def test_remove_volume_success(self): - BDM = fakes.BDM['block_device_mapping'][0] - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - for bdm in fakes.BDM['block_device_mapping']: - ext_str.add_volume(bdm['mount_device'], bdm['connection_info']) - - self.assertTrue(BDM['mount_device'] in ext_str._volumes) - self.assertEqual( - ext_str._volumes[BDM['mount_device']], BDM['connection_info']) - - ext_str.remove_volume(BDM['mount_device']) - - self.assertFalse(BDM['mount_device'] in ext_str._volumes) - - def test_remove_volume_failure(self): - BDM = fakes.BDM['block_device_mapping'][0] - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - ext_str.remove_volume(BDM['mount_device']) - - def test_save(self): - BDM = fakes.BDM['block_device_mapping'][0] - self.mox.StubOutWithMock(ext_storage.ovzfile, 'OVZFile') - ext_storage.ovzfile.OVZFile(self.filename, self.permissions).AndReturn( - fakes.FakeOvzFile(self.filename, self.permissions)) - self.mox.ReplayAll() - ext_str = ext_storage.OVZExtStorage(fakes.INSTANCE['id']) - for bdm in fakes.BDM['block_device_mapping']: - ext_str.add_volume(bdm['mount_device'], bdm['connection_info']) - - ext_str.save() - self.assertEqual( - json.dumps(ext_str._volumes), ext_str.local_store.contents) diff --git a/ovznovadriver/tests/openvz/test_file.py b/ovznovadriver/tests/openvz/test_file.py deleted file mode 100644 index 6b78bbe..0000000 --- a/ovznovadriver/tests/openvz/test_file.py +++ /dev/null @@ -1,126 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -import __builtin__ -import mox -from nova import exception -from nova import test -from nova.tests.openvz import fakes -from ovznovadriver.openvz import driver as openvz_conn -from ovznovadriver.openvz import file as ovzfile -from ovznovadriver.openvz import utils as ovz_utils -from oslo.config import cfg - -CONF = cfg.CONF - - -class OpenVzFileTestCase(test.TestCase): - def setUp(self): - super(OpenVzFileTestCase, self).setUp() - self.fake_file = mox.MockAnything() - self.fake_file.readlines().AndReturn(fakes.FILECONTENTS.split()) - self.fake_file.writelines(mox.IgnoreArg()) - self.fake_file.read().AndReturn(fakes.FILECONTENTS) - - def test_touch_file_success(self): - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - self.mox.StubOutWithMock(fh, 'make_path') - fh.make_path() - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'touch', fakes.TEMPFILE, run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - fh.touch() - - def test_touch_file_failure(self): - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - self.mox.StubOutWithMock(fh, 'make_path') - fh.make_path() - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'touch', fakes.TEMPFILE, run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises(exception.InstanceUnacceptable, fh.touch) - - def test_read_file_success(self): - self.mox.StubOutWithMock(__builtin__, 'open') - __builtin__.open(mox.IgnoreArg(), 'r').AndReturn(self.fake_file) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - fh.read() - - def test_read_file_failure(self): - self.mox.StubOutWithMock(__builtin__, 'open') - __builtin__.open(mox.IgnoreArg(), 'r').AndRaise( - exception.FileNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - self.assertRaises(exception.FileNotFound, fh.read) - - def test_write_to_file_success(self): - self.mox.StubOutWithMock(__builtin__, 'open') - __builtin__.open(mox.IgnoreArg(), 'w').AndReturn(self.fake_file) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - fh.write() - - def test_write_to_file_failure(self): - self.mox.StubOutWithMock(__builtin__, 'open') - __builtin__.open(mox.IgnoreArg(), 'w').AndRaise( - exception.FileNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - self.assertRaises(exception.FileNotFound, fh.write) - - def test_set_perms_success(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'chmod', 755, fakes.TEMPFILE, run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - fh.set_permissions(755) - - def test_set_perms_failure(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'chmod', 755, fakes.TEMPFILE, run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - self.assertRaises( - exception.InstanceUnacceptable, fh.set_permissions, 755) - - def test_make_path_and_dir_success(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'mkdir', '-p', mox.IgnoreArg(), run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.StubOutWithMock(openvz_conn.os.path, 'exists') - openvz_conn.os.path.exists(mox.IgnoreArg()).AndReturn(False) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - fh.make_path() - - def test_make_path_and_dir_exists(self): - self.mox.StubOutWithMock(openvz_conn.os.path, 'exists') - openvz_conn.os.path.exists(mox.IgnoreArg()).AndReturn(True) - self.mox.ReplayAll() - fh = ovzfile.OVZFile(fakes.TEMPFILE, 755) - fh.make_path() diff --git a/ovznovadriver/tests/openvz/test_network.py b/ovznovadriver/tests/openvz/test_network.py deleted file mode 100644 index 7f495df..0000000 --- a/ovznovadriver/tests/openvz/test_network.py +++ /dev/null @@ -1,220 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -import mox -from nova import exception -from nova import test -from nova.tests import fake_network -from nova.tests.openvz import fakes -from ovznovadriver.openvz import driver as openvz_conn -from ovznovadriver.openvz import network as openvz_net -from ovznovadriver.openvz.network_drivers import network_bridge -from oslo.config import cfg - -CONF = cfg.CONF -_fake_network_info = fake_network.fake_get_instance_nw_info - - -class OpenVzNetworkTestCase(test.TestCase): - def setUp(self): - super(OpenVzNetworkTestCase, self).setUp() - try: - CONF.injected_network_template - except AttributeError as err: - CONF.register_opt( - cfg.StrOpt( - 'injected_network_template', - default='ovznovadriver/interfaces.template', - help='Stub for network template for testing purposes') - ) - CONF.use_ipv6 = False - self.fake_file = mox.MockAnything() - self.fake_file.readlines().AndReturn(fakes.FILECONTENTS.split()) - self.fake_file.writelines(mox.IgnoreArg()) - self.fake_file.read().AndReturn(fakes.FILECONTENTS) - - def test_ovz_network_interfaces_add_success(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovztc, 'OVZTcRules') - openvz_net.ovztc.OVZTcRules().MultipleTimes().AndReturn( - fakes.FakeOVZTcRules()) - self.mox.StubOutWithMock(openvz_net.OVZNetworkInterfaces, '_add_netif') - openvz_net.OVZNetworkInterfaces._add_netif( - fakes.INTERFACEINFO[0]['id'], - mox.IgnoreArg(), - mox.IgnoreArg(), - mox.IgnoreArg()).MultipleTimes() - self.mox.StubOutWithMock( - openvz_net.OVZNetworkInterfaces, '_set_nameserver') - self.mox.StubOutWithMock(openvz_net, 'OVZNetworkFile') - openvz_net.OVZNetworkFile( - ('/var/lib/vz/private/%s/etc/network/interfaces' % - fakes.INSTANCE['id'])).AndReturn( - fakes.FakeOVZNetworkFile('/etc/network/interfaces')) - openvz_net.OVZNetworkInterfaces._set_nameserver( - fakes.INTERFACEINFO[0]['id'], fakes.INTERFACEINFO[0]['dns']) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces( - fakes.INTERFACEINFO) - ifaces.add() - - def test_ovz_network_interfaces_add_ip_success(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INTERFACEINFO[0]['id'], '--save', '--ipadd', - fakes.INTERFACEINFO[0]['address'], run_as_root=True).AndReturn( - ('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - ifaces._add_ip( - fakes.INTERFACEINFO[0]['id'], fakes.INTERFACEINFO[0]['address']) - - def test_ovz_network_interfaces_add_ip_failure(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INTERFACEINFO[0]['id'], '--save', - '--ipadd', fakes.INTERFACEINFO[0]['address'], - run_as_root=True).AndRaise( - exception.InstanceUnacceptable(fakes.ERRORMSG)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - self.assertRaises( - exception.InstanceUnacceptable, ifaces._add_ip, - fakes.INTERFACEINFO[0]['id'], fakes.INTERFACEINFO[0]['address']) - - def test_ovz_network_interfaces_add_netif(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INTERFACEINFO[0]['id'], '--save', - '--netif_add', - '%s,,veth%s.%s,%s,%s' % ( - fakes.INTERFACEINFO[0]['name'], - fakes.INTERFACEINFO[0]['id'], - fakes.INTERFACEINFO[0]['name'], - fakes.INTERFACEINFO[0]['mac'], - fakes.INTERFACEINFO[0]['bridge']), - run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - ifaces._add_netif( - fakes.INTERFACEINFO[0]['id'], - fakes.INTERFACEINFO[0]['name'], - fakes.INTERFACEINFO[0]['bridge'], - fakes.INTERFACEINFO[0]['mac'] - ) - - def test_filename_factory_debian_variant(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - for filename in ifaces._filename_factory(): - self.assertFalse('//' in filename) - - def test_set_nameserver_success(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovz_utils, 'execute') - openvz_net.ovz_utils.execute( - 'vzctl', 'set', fakes.INTERFACEINFO[0]['id'], '--save', - '--nameserver', fakes.INTERFACEINFO[0]['dns'], - run_as_root=True).AndReturn(('', fakes.ERRORMSG)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - ifaces._set_nameserver( - fakes.INTERFACEINFO[0]['id'], fakes.INTERFACEINFO[0]['dns']) - - def test_set_nameserver_failure(self): - self.mox.StubOutWithMock(openvz_net.ovzshutdown, 'OVZShutdownFile') - openvz_net.ovzshutdown.OVZShutdownFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZShutdownFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_net.ovzboot, 'OVZBootFile') - openvz_net.ovzboot.OVZBootFile( - fakes.INSTANCE['id'], mox.IgnoreArg()).AndReturn( - fakes.FakeOVZBootFile(fakes.INSTANCE['id'], 700)) - self.mox.StubOutWithMock(openvz_conn.ovz_utils, 'execute') - openvz_conn.ovz_utils.execute( - 'vzctl', 'set', fakes.INTERFACEINFO[0]['id'], '--save', - '--nameserver', fakes.INTERFACEINFO[0]['dns'], - run_as_root=True).AndRaise(exception.InstanceUnacceptable( - fakes.ERRORMSG)) - self.mox.ReplayAll() - ifaces = openvz_net.OVZNetworkInterfaces(fakes.INTERFACEINFO) - self.assertRaises( - exception.InstanceUnacceptable, ifaces._set_nameserver, - fakes.INTERFACEINFO[0]['id'], fakes.INTERFACEINFO[0]['dns']) - - def test_ovz_network_bridge_driver_plug(self): - self.mox.StubOutWithMock( - openvz_conn.linux_net.LinuxBridgeInterfaceDriver, - 'ensure_vlan_bridge' - ) - openvz_conn.linux_net.LinuxBridgeInterfaceDriver.ensure_vlan_bridge( - mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg() - ) - self.mox.ReplayAll() - driver = network_bridge.OVZNetworkBridgeDriver() - network_info = _fake_network_info(self.stubs, 1) - for vif in network_info: - # should_create_vlan isn't included in nova's fake network info by - # default so we need to inject it to hit this code - vif['network']['meta']['should_create_vlan'] = True - driver.plug(fakes.INSTANCE, vif) diff --git a/ovznovadriver/tests/openvz/test_utils.py b/ovznovadriver/tests/openvz/test_utils.py deleted file mode 100644 index dad8f6b..0000000 --- a/ovznovadriver/tests/openvz/test_utils.py +++ /dev/null @@ -1,302 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# Copyright 2013 Rackspace -# All Rights Reserved. -# -# 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. - -import mox -from nova import exception -from nova.openstack.common import processutils -from nova import test -from nova.tests.openvz import fakes -from ovznovadriver.openvz import utils as ovz_utils -from oslo.config import cfg -import uuid - -CONF = cfg.CONF - - -class OpenVzUtilsTestCase(test.TestCase): - def setUp(self): - super(OpenVzUtilsTestCase, self).setUp() - - def test_execute_process_execution_error(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'cat', '/proc/cpuinfo', run_as_root=False).AndRaise( - processutils.ProcessExecutionError(fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertRaises( - exception.InstanceUnacceptable, ovz_utils.execute, 'cat', - '/proc/cpuinfo', run_as_root=False) - - def test_execute_process_execution_error_no_raise_on_error(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'execute') - ovz_utils.utils.execute( - 'cat', '/proc/cpuinfo', run_as_root=False).AndRaise( - processutils.ProcessExecutionError) - self.mox.ReplayAll() - ovz_utils.execute( - 'cat', '/proc/cpuinfo', run_as_root=False, raise_on_error=False) - - def test_mkfs_uuid(self): - fs_uuid = uuid.uuid4() - path = '/dev/sdgg' - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'mkfs', '-F', '-t', 'ext3', '-U', fs_uuid, path, run_as_root=True) - self.mox.ReplayAll() - ovz_utils.mkfs(path, 'ext3', fs_uuid) - - def test_mkfs_label(self): - path = '/dev/sdgg' - fs_label = 'STORAGE' - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'mkfs', '-F', '-t', 'ext3', '-U', mox.IgnoreArg(), '-L', fs_label, - path, run_as_root=True) - self.mox.ReplayAll() - ovz_utils.mkfs(path, 'ext3', None, fs_label) - - def test_get_fs_uuid_success(self): - dev = '/dev/sdgg' - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'blkid', '-o', 'value', '-s', 'UUID', dev, - raise_on_error=False, run_as_root=True).AndReturn(fakes.BLKID) - self.mox.ReplayAll() - fs_uuid = ovz_utils.get_fs_uuid(dev) - self.assertEqual(fs_uuid, fakes.BLKID.strip()) - - def test_get_fs_uuid_failure(self): - dev = '/dev/sdgg' - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'blkid', '-o', 'value', '-s', 'UUID', dev, - raise_on_error=False, run_as_root=True).AndReturn('\n') - self.mox.ReplayAll() - fs_uuid = ovz_utils.get_fs_uuid(dev) - self.assertFalse(fs_uuid) - - def test_get_vcpu_total_success(self): - self.mox.StubOutWithMock( - ovz_utils.multiprocessing, 'cpu_count') - ovz_utils.multiprocessing.cpu_count().AndReturn( - fakes.HOSTSTATS['vcpus']) - self.mox.ReplayAll() - result = ovz_utils.get_vcpu_total() - self.assertEqual(result, fakes.HOSTSTATS['vcpus']) - - def test_get_vcpu_total_failure(self): - self.mox.StubOutWithMock( - ovz_utils.multiprocessing, 'cpu_count') - ovz_utils.multiprocessing.cpu_count().AndRaise(NotImplementedError) - self.mox.ReplayAll() - result = ovz_utils.get_vcpu_total() - self.assertEqual(result, 0) - - def test_get_cpuinfo_not_running_on_linux(self): - self.mox.StubOutWithMock(ovz_utils, 'sys') - self.mox.StubOutWithMock(ovz_utils.sys, 'platform') - self.mox.StubOutWithMock(ovz_utils.sys.platform, 'upper') - ovz_utils.sys.platform.upper().AndReturn('DARWIN') - self.mox.ReplayAll() - result = ovz_utils.get_cpuinfo() - self.assertEqual(result, 0) - - def test_iscsi_initiator(self): - self.mox.StubOutWithMock(ovz_utils.utils, 'read_file_as_root') - ovz_utils.utils.read_file_as_root( - '/etc/iscsi/initiatorname.iscsi').AndReturn(fakes.ISCSIINITIATOR) - self.mox.ReplayAll() - iscsi_initiator = ovz_utils.get_iscsi_initiator() - self.assertEqual(fakes.INITIATORNAME, iscsi_initiator) - - def test_get_cpuunits_capability(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'vzcpucheck', run_as_root=True).AndReturn('') - self.mox.ReplayAll() - self.assertRaises( - exception.InvalidCPUInfo, ovz_utils.get_cpuunits_capability) - - def test_get_vcpu_used(self): - self.mox.StubOutWithMock(ovz_utils, 'get_cpuunits_capability') - ovz_utils.get_cpuunits_capability().AndReturn(fakes.CPUUNITSCAPA) - self.mox.StubOutWithMock(ovz_utils, 'get_vcpu_total') - ovz_utils.get_vcpu_total().AndReturn(fakes.HOSTSTATS['vcpus']) - self.mox.ReplayAll() - used = int(fakes.HOSTSTATS['vcpus'] * - (float(fakes.CPUUNITSCAPA['subscribed']) / - fakes.CPUUNITSCAPA['total'])) - result = ovz_utils.get_vcpu_used() - self.assertEqual(result, used) - - def test_get_memory_mb_total_not_running_on_linux(self): - self.mox.StubOutWithMock(ovz_utils, 'sys') - self.mox.StubOutWithMock(ovz_utils.sys, 'platform') - self.mox.StubOutWithMock(ovz_utils.sys.platform, 'upper') - ovz_utils.sys.platform.upper().AndReturn('DARWIN') - self.mox.ReplayAll() - result = ovz_utils.get_memory_mb_total() - self.assertEqual(result, 1) - - def test_get_memory_mb_used(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'vzlist', '--all', '-H', '-o', 'ctid,privvmpages.l', - raise_on_error=False, run_as_root=True).AndReturn( - fakes.PRIVVMPAGES) - self.mox.ReplayAll() - memory_used = (((int( - fakes.PRIVVMPAGES_1024.strip().split()[1]) * 4096) / 1024 ** 2) + - ((int( - fakes.PRIVVMPAGES_2048.strip().split()[1]) * - 4096) / 1024 ** 2)) - result = ovz_utils.get_memory_mb_used() - self.assertEqual(memory_used, result) - - def test_get_memory_mb_used_instance(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'vzlist', '-H', '-o', 'ctid,privvmpages.l', - str(fakes.INSTANCE['id']), - raise_on_error=False, run_as_root=True).AndReturn( - fakes.PRIVVMPAGES_2048) - self.mox.ReplayAll() - memory_used = ((int( - fakes.PRIVVMPAGES_2048.strip().split()[1]) * 4096) / 1024 ** 2) - result = ovz_utils.get_memory_mb_used(fakes.INSTANCE['id']) - self.assertEqual(memory_used, result) - - def test_get_local_gb_total(self): - self.mox.StubOutWithMock(ovz_utils.os, 'statvfs') - ovz_utils.os.statvfs( - CONF.ovz_ve_private_dir).AndReturn(fakes.STATVFSRESULT) - self.mox.ReplayAll() - total = ((fakes.STATVFSRESULT.f_frsize * fakes.STATVFSRESULT.f_blocks) - / 1024 ** 3) - result = ovz_utils.get_local_gb_total() - self.assertEqual(total, result) - - def test_get_local_gb_used(self): - self.mox.StubOutWithMock(ovz_utils.os, 'statvfs') - ovz_utils.os.statvfs( - CONF.ovz_ve_private_dir).AndReturn(fakes.STATVFSRESULT) - self.mox.ReplayAll() - used = ((fakes.STATVFSRESULT.f_frsize * - (fakes.STATVFSRESULT.f_blocks - fakes.STATVFSRESULT.f_bfree) - ) / (1024 ** 3)) - result = ovz_utils.get_local_gb_used() - self.assertEqual(used, result) - - def test_get_hypervisor_version(self): - self.mox.StubOutWithMock(ovz_utils.platform, 'uname') - ovz_utils.platform.uname().AndReturn(fakes.UNAME) - self.mox.ReplayAll() - result = ovz_utils.get_hypervisor_version() - self.assertEqual(result, fakes.UNAME[2]) - - def test_delete_path_good(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'rmdir', CONF.ovz_ve_private_dir, - run_as_root=True).AndReturn(('', '')) - self.mox.ReplayAll() - self.assertTrue(ovz_utils.delete_path(CONF.ovz_ve_private_dir)) - - def test_delete_path_bad(self): - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute( - 'rmdir', CONF.ovz_ve_private_dir, - run_as_root=True).AndRaise(exception.InstanceUnacceptable( - fakes.ERRORMSG)) - self.mox.ReplayAll() - self.assertFalse(ovz_utils.delete_path(CONF.ovz_ve_private_dir)) - - def test_set_permissions(self): - perms = 755 - filename = '/tmp/testfile' - self.mox.StubOutWithMock(ovz_utils, 'execute') - ovz_utils.execute('chmod', perms, filename, run_as_root=True) - self.mox.ReplayAll() - ovz_utils.set_permissions(filename, perms) - - def test_save_instance_metadata_success(self): - self.mox.StubOutWithMock(ovz_utils.context, 'get_admin_context') - ovz_utils.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.conductor, 'instance_get') - ovz_utils.conductor.instance_get( - fakes.ADMINCONTEXT, fakes.INSTANCE['id']).AndReturn(fakes.INSTANCE) - self.mox.StubOutWithMock( - ovz_utils.conductor, 'instance_update') - ovz_utils.conductor.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - system_metadata=ovz_utils.format_system_metadata( - fakes.INSTANCE['system_metadata'])) - self.mox.ReplayAll() - ovz_utils.save_instance_metadata( - fakes.INSTANCE['id'], fakes.METAKEY, fakes.METAVALUE) - - def test_save_instance_metadata_not_found(self): - self.mox.StubOutWithMock(ovz_utils.context, 'get_admin_context') - ovz_utils.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.conductor, 'instance_get') - ovz_utils.conductor.instance_get( - fakes.ADMINCONTEXT, fakes.INSTANCE['id']).AndReturn(fakes.INSTANCE) - self.mox.StubOutWithMock( - ovz_utils.conductor, 'instance_update') - ovz_utils.conductor.instance_update( - fakes.ADMINCONTEXT, fakes.INSTANCE['uuid'], - system_metadata=ovz_utils.format_system_metadata( - fakes.INSTANCE['system_metadata'])).AndRaise( - exception.InstanceNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - ovz_utils.save_instance_metadata( - fakes.INSTANCE['id'], fakes.METAKEY, fakes.METAVALUE) - - def test_read_instance_metadata_success(self): - self.mox.StubOutWithMock(ovz_utils.context, 'get_admin_context') - ovz_utils.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.conductor, 'instance_get') - ovz_utils.conductor.instance_get( - fakes.ADMINCONTEXT, fakes.INSTANCE['id']).AndReturn(fakes.INSTANCE) - self.mox.ReplayAll() - meta = ovz_utils.read_instance_metadata(fakes.INSTANCE['id']) - self.assertTrue(isinstance(meta, dict)) - self.assertEqual(meta[fakes.METAKEY], fakes.METAVALUE) - - def test_read_instance_metadata_not_found(self): - self.mox.StubOutWithMock(ovz_utils.context, 'get_admin_context') - ovz_utils.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.conductor, 'instance_get') - ovz_utils.conductor.instance_get( - fakes.ADMINCONTEXT, fakes.INSTANCE['id']).AndRaise( - exception.InstanceNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - meta = ovz_utils.read_instance_metadata(fakes.INSTANCE['id']) - self.assertTrue(isinstance(meta, dict)) - self.assertTrue(len(meta) == 0) - - def test_read_instance_metadata_dberror(self): - self.mox.StubOutWithMock(ovz_utils.context, 'get_admin_context') - ovz_utils.context.get_admin_context().AndReturn(fakes.ADMINCONTEXT) - self.mox.StubOutWithMock(ovz_utils.conductor, 'instance_get') - ovz_utils.conductor.instance_get( - fakes.ADMINCONTEXT, fakes.INSTANCE['id']).AndRaise( - exception.InstanceNotFound(fakes.ERRORMSG)) - self.mox.ReplayAll() - meta = ovz_utils.read_instance_metadata(fakes.INSTANCE['id']) - self.assertTrue(isinstance(meta, dict)) - self.assertTrue(len(meta) == 0) diff --git a/setup.py b/setup.py deleted file mode 100644 index c2f1827..0000000 --- a/setup.py +++ /dev/null @@ -1,33 +0,0 @@ -# vim: tabstop=4 shiftwidth=4 softtabstop=4 - -# 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. - -import setuptools - - -setuptools.setup( - name='openvz-nova-driver', - version='0.1.0', - description='The OpenVZ Driver for Nova', - author='Rackspace', - packages=setuptools.find_packages(exclude=['debian', 'etc']), - include_package_data=True, - # i dont know where to put this package to make sure its built - classifiers=[ - 'Development Status :: 4 - Beta', - 'License :: OSI Approved :: Apache Software License', - 'Operating System :: POSIX :: Linux', - 'Programming Language :: Python :: 2.6', - 'Environment :: No Input/Output (Daemon)', - ] -)