Merge "virt: introduce libosinfo library to set hardware policy"
This commit is contained in:
commit
26ea5eee77
@ -2067,3 +2067,8 @@ class RealtimeMaskNotFoundOrInvalid(Invalid):
|
||||
msg_fmt = _("Realtime policy needs vCPU(s) mask configured with at least "
|
||||
"1 RT vCPU and 1 ordinary vCPU. See hw:cpu_realtime_mask "
|
||||
"or hw_cpu_realtime_mask")
|
||||
|
||||
|
||||
class OsInfoNotFound(NotFound):
|
||||
msg_fmt = _("No configuration information found for operating system "
|
||||
"%(os_name)s")
|
||||
|
53
nova/tests/unit/virt/test_osinfo.py
Normal file
53
nova/tests/unit/virt/test_osinfo.py
Normal file
@ -0,0 +1,53 @@
|
||||
# Copyright 2015 Red Hat, Inc
|
||||
#
|
||||
# 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 mock
|
||||
|
||||
from nova import exception
|
||||
from nova import test
|
||||
from nova.virt import osinfo
|
||||
|
||||
|
||||
class LibvirtOsInfoTest(test.NoDBTestCase):
|
||||
|
||||
def setUp(self):
|
||||
super(LibvirtOsInfoTest, self).setUp()
|
||||
osinfo.libosinfo = mock.Mock()
|
||||
|
||||
def test_get_os(self):
|
||||
filter_mock = mock.Mock()
|
||||
osinfo.libosinfo = mock.Mock()
|
||||
osinfo.libosinfo.Filter.new.return_value = filter_mock
|
||||
osinfo_mock = mock.Mock()
|
||||
filtered_list = osinfo_mock.new_filtered
|
||||
filtered_list.return_value.get_length.return_value = 1
|
||||
os_info_db = osinfo._OsInfoDatabase.get_instance()
|
||||
os_info_db.oslist = osinfo_mock
|
||||
os_info_db.get_os('test33')
|
||||
filter_mock.add_constraint.assert_called_once_with('short-id',
|
||||
'test33')
|
||||
self.assertTrue(filtered_list.return_value.get_nth.called)
|
||||
|
||||
def test_get_os_fails(self):
|
||||
filter_mock = mock.Mock()
|
||||
osinfo.libosinfo = mock.Mock()
|
||||
osinfo.libosinfo.Filter.return_value.new.return_value = filter_mock
|
||||
osinfo_mock = mock.Mock()
|
||||
filtered = osinfo_mock.new_filtered.return_value
|
||||
filtered.get_length.return_value = 0
|
||||
os_info_db = osinfo._OsInfoDatabase.get_instance()
|
||||
os_info_db.oslist = osinfo_mock
|
||||
self.assertRaises(exception.OsInfoNotFound,
|
||||
os_info_db.get_os,
|
||||
'test33')
|
113
nova/virt/osinfo.py
Normal file
113
nova/virt/osinfo.py
Normal file
@ -0,0 +1,113 @@
|
||||
# Copyright 2015 Red Hat, Inc
|
||||
#
|
||||
# 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 oslo_log import log as logging
|
||||
from oslo_utils import importutils
|
||||
|
||||
from nova import exception
|
||||
from nova.i18n import _, _LE
|
||||
|
||||
libosinfo = None
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
# TODO(vladikr) The current implementation will serve only as a temporary
|
||||
# solution, due to it's dependency on the libosinfo gobject library.
|
||||
# In the future it will be replaced by a pure python library or by a direct
|
||||
# parsing of the libosinfo XML files. However, it will be possible only when
|
||||
# libosinfo project will declare the XML structure to be a stable ABI.
|
||||
|
||||
|
||||
class _OsInfoDatabase(object):
|
||||
|
||||
_instance = None
|
||||
|
||||
def __init__(self):
|
||||
|
||||
global libosinfo
|
||||
if libosinfo is None:
|
||||
try:
|
||||
libosinfo = importutils.import_module(
|
||||
'gi.repository.Libosinfo')
|
||||
except ImportError as exp:
|
||||
raise exception.NovaException(
|
||||
_("Cannot load Libosinfo: (%s)") % exp)
|
||||
|
||||
self.loader = libosinfo.Loader()
|
||||
self.loader.process_default_path()
|
||||
|
||||
self.db = self.loader.get_db()
|
||||
self.oslist = self.db.get_os_list()
|
||||
|
||||
@classmethod
|
||||
def get_instance(cls):
|
||||
"""Get libosinfo connection
|
||||
"""
|
||||
if cls._instance is None:
|
||||
cls._instance = _OsInfoDatabase()
|
||||
|
||||
return cls._instance
|
||||
|
||||
def get_os(self, os_name):
|
||||
"""Retrieve OS object based on id, unique URI identifier of the OS
|
||||
:param os_name: id - the unique operating systemidentifier
|
||||
e.g. http://fedoraproject.org/fedora/21,
|
||||
http://microsoft.com/win/xp,
|
||||
or a
|
||||
short-id - the short name of the OS
|
||||
e.g. fedora21, winxp
|
||||
:returns: The operation system object Libosinfo.Os
|
||||
:raise exception.OsInfoNotFound: If os hasn't been found
|
||||
"""
|
||||
if not os_name:
|
||||
raise exception.OsInfoNotFound(os_name='Empty')
|
||||
fltr = libosinfo.Filter.new()
|
||||
flt_field = 'id' if os_name.startswith('http') else 'short-id'
|
||||
fltr.add_constraint(flt_field, os_name)
|
||||
filttered = self.oslist.new_filtered(fltr)
|
||||
list_len = filttered.get_length()
|
||||
if not list_len:
|
||||
raise exception.OsInfoNotFound(os_name=os_name)
|
||||
return filttered.get_nth(0)
|
||||
|
||||
|
||||
class OsInfo(object):
|
||||
"""OS Information Structure
|
||||
"""
|
||||
|
||||
def __init__(self, os_name):
|
||||
self._os_obj = self._get_os_obj(os_name)
|
||||
|
||||
def _get_os_obj(self, os_name):
|
||||
try:
|
||||
return _OsInfoDatabase.get_instance().get_os(os_name)
|
||||
except exception.NovaException as e:
|
||||
LOG.error(_LE("Cannot find OS information - Reason: (%s)"), e)
|
||||
|
||||
@property
|
||||
def network_model(self):
|
||||
if self._os_obj is not None:
|
||||
fltr = libosinfo.Filter()
|
||||
fltr.add_constraint("class", "net")
|
||||
devs = self._os_obj.get_all_devices(fltr)
|
||||
if devs.get_length():
|
||||
return devs.get_nth(0).get_name()
|
||||
|
||||
@property
|
||||
def disk_model(self):
|
||||
if self._os_obj is not None:
|
||||
fltr = libosinfo.Filter()
|
||||
fltr.add_constraint("class", "block")
|
||||
devs = self._os_obj.get_all_devices(fltr)
|
||||
if devs.get_length():
|
||||
return devs.get_nth(0).get_name()
|
Loading…
Reference in New Issue
Block a user