Browse Source

Add the ability to manage RAID settings

This patch adds the ability to get and set the settings for RAID
settings.

Change-Id: Ifc63ca7d9a30378e75b160739b709a1264ffe550
(cherry picked from commit c3bb9606aa)
tags/1.7.0^0
mpardhi23 3 months ago
committed by Christopher Dearborn
parent
commit
7be050e66f
11 changed files with 3393 additions and 18 deletions
  1. +37
    -0
      dracclient/client.py
  2. +262
    -1
      dracclient/resources/raid.py
  3. +14
    -4
      dracclient/resources/uris.py
  4. +178
    -0
      dracclient/tests/test_raid.py
  5. +15
    -0
      dracclient/tests/utils.py
  6. +2347
    -0
      dracclient/tests/wsman_mocks/raid_enumeration-enum-ok.xml
  7. +416
    -0
      dracclient/tests/wsman_mocks/raid_integer-enum-ok.xml
  8. +21
    -0
      dracclient/tests/wsman_mocks/raid_service-invoke-set_attributes-error.xml
  9. +24
    -0
      dracclient/tests/wsman_mocks/raid_service-invoke-set_attributes-ok.xml
  10. +49
    -0
      dracclient/tests/wsman_mocks/raid_string-enum-ok.xml
  11. +30
    -13
      dracclient/utils.py

+ 37
- 0
dracclient/client.py View File

@@ -758,6 +758,43 @@ class DRACClient(object):
"""
return self._raid_mgmt.list_raid_controllers()

def list_raid_settings(self):
"""List the RAID configuration settings

:returns: a dictionary with the RAID settings using InstanceID as the
key. The attributes are either RAIDEnumerableAttribute,
RAIDStringAttribute objects.
:raises: WSManRequestFailure on request failures
:raises: WSManInvalidResponse when receiving invalid response
:raises: DRACOperationFailed on error reported back by the DRAC
interface
"""
return self._raid_mgmt.list_raid_settings()

def set_raid_settings(self, raid_fqdd, settings):
"""Sets the RAID configuration

It sets the pending_value parameter for each of the attributes
passed in. For the values to be applied, a config job must
be created.
:param raid_fqdd: the FQDD of the RAID setting.
:param settings: a dictionary containing the proposed values, with
each key being the name of attribute and the value
being the proposed value.
:returns: a dictionary containing:
- The is_commit_required key with a boolean value indicating
whether a config job must be created for the values to be
applied.
- The is_reboot_required key with a RebootRequired enumerated
value indicating whether the server must be rebooted for the
values to be applied. Possible values are true and false.
:raises: WSManRequestFailure on request failures
:raises: WSManInvalidResponse when receiving invalid response
:raises: DRACOperationFailed on error reported back by the DRAC
interface
"""
return self._raid_mgmt.set_raid_settings(raid_fqdd, settings)

def list_virtual_disks(self):
"""Returns the list of RAID arrays



+ 262
- 1
dracclient/resources/raid.py View File

@@ -125,7 +125,6 @@ VirtualDiskTuple = collections.namedtuple(
'status', 'raid_status', 'span_depth', 'span_length',
'pending_operations', 'physical_disks'])


NO_FOREIGN_DRIVES = ["STOR058", "STOR018"]


@@ -159,8 +158,222 @@ class VirtualDisk(VirtualDiskTuple):
return self.raid_status


class RAIDAttribute(object):
"""Generic RAID attribute class"""

def __init__(self, name, instance_id, current_value, pending_value,
read_only, fqdd):
"""Creates RAIDAttribute object

:param name: name of the RAID attribute
:param instance_id: InstanceID of the RAID attribute
:param current_value: list containing the current values of the
RAID attribute
:param pending_value: pending value of the RAID attribute, reflecting
an unprocessed change (eg. config job not completed)
:param read_only: indicates whether this RAID attribute can be changed
:param fqdd: Fully Qualified Device Description of the RAID Attribute
"""

self.name = name
self.instance_id = instance_id
self.current_value = current_value
self.pending_value = pending_value
self.read_only = read_only
self.fqdd = fqdd

def __eq__(self, other):
return self.__dict__ == other.__dict__

@classmethod
def parse(cls, namespace, raid_attr_xml):
"""Parses XML and creates RAIDAttribute object"""

name = utils.get_wsman_resource_attr(
raid_attr_xml, namespace, 'AttributeName')
instance_id = utils.get_wsman_resource_attr(
raid_attr_xml, namespace, 'InstanceID')
current_value = [attr.text for attr in
utils.find_xml(raid_attr_xml, 'CurrentValue',
namespace, find_all=True)]
pending_value = utils.get_wsman_resource_attr(
raid_attr_xml, namespace, 'PendingValue', nullable=True)
read_only = utils.get_wsman_resource_attr(
raid_attr_xml, namespace, 'IsReadOnly')
fqdd = utils.get_wsman_resource_attr(
raid_attr_xml, namespace, 'FQDD')

return cls(name, instance_id, current_value, pending_value,
(read_only == 'true'), fqdd)


class RAIDEnumerableAttribute(RAIDAttribute):
"""Enumerable RAID attribute class"""

namespace = uris.DCIM_RAIDEnumeration

def __init__(self, name, instance_id, current_value, pending_value,
read_only, fqdd, possible_values):
"""Creates RAIDEnumerableAttribute object

:param name: name of the RAID attribute
:param instance_id: InstanceID of the RAID attribute
:param current_value: list containing the current values of the
RAID attribute
:param pending_value: pending value of the RAID attribute, reflecting
an unprocessed change (eg. config job not completed)
:param read_only: indicates whether this RAID attribute can be changed
:param fqdd: Fully Qualified Device Description of the RAID
Attribute
:param possible_values: list containing the allowed values for the RAID
attribute
"""
super(RAIDEnumerableAttribute, self).__init__(name, instance_id,
current_value,
pending_value,
read_only, fqdd)

self.possible_values = possible_values

@classmethod
def parse(cls, raid_attr_xml):
"""Parses XML and creates RAIDEnumerableAttribute object"""

raid_attr = RAIDAttribute.parse(cls.namespace, raid_attr_xml)
possible_values = [attr.text for attr
in utils.find_xml(raid_attr_xml,
'PossibleValues',
cls.namespace, find_all=True)]

return cls(raid_attr.name, raid_attr.instance_id,
raid_attr.current_value, raid_attr.pending_value,
raid_attr.read_only, raid_attr.fqdd, possible_values)

def validate(self, new_value):
"""Validates new value"""

if str(new_value) not in self.possible_values:
msg = ("Attribute '%(attr)s' cannot be set to value '%(val)s'."
" It must be in %(possible_values)r.") % {
'attr': self.name,
'val': new_value,
'possible_values': self.possible_values}
return msg


class RAIDStringAttribute(RAIDAttribute):
"""String RAID attribute class"""

namespace = uris.DCIM_RAIDString

def __init__(self, name, instance_id, current_value, pending_value,
read_only, fqdd, min_length, max_length):
"""Creates RAIDStringAttribute object

:param name: name of the RAID attribute
:param instance_id: InstanceID of the RAID attribute
:param current_value: list containing the current values of the
RAID attribute
:param pending_value: pending value of the RAID attribute, reflecting
an unprocessed change (eg. config job not completed)
:param read_only: indicates whether this RAID attribute can be changed
:param fqdd: Fully Qualified Device Description of the RAID
Attribute
:param min_length: minimum length of the string
:param max_length: maximum length of the string
"""
super(RAIDStringAttribute, self).__init__(name, instance_id,
current_value, pending_value,
read_only, fqdd)
self.min_length = min_length
self.max_length = max_length

@classmethod
def parse(cls, raid_attr_xml):
"""Parses XML and creates RAIDStringAttribute object"""

raid_attr = RAIDAttribute.parse(cls.namespace, raid_attr_xml)
min_length = int(utils.get_wsman_resource_attr(
raid_attr_xml, cls.namespace, 'MinLength'))
max_length = int(utils.get_wsman_resource_attr(
raid_attr_xml, cls.namespace, 'MaxLength'))

return cls(raid_attr.name, raid_attr.instance_id,
raid_attr.current_value, raid_attr.pending_value,
raid_attr.read_only, raid_attr.fqdd,
min_length, max_length)


class RAIDIntegerAttribute(RAIDAttribute):
"""Integer RAID attribute class"""

namespace = uris.DCIM_RAIDInteger

def __init__(self, name, instance_id, current_value, pending_value,
read_only, fqdd, lower_bound, upper_bound):
"""Creates RAIDIntegerAttribute object

:param name: name of the RAID attribute
:param instance_id: InstanceID of the RAID attribute
:param current_value: list containing the current value of the
RAID attribute
:param pending_value: pending value of the RAID attribute,
reflecting an unprocessed change
(eg. config job not completed)
:param read_only: indicates whether this RAID attribute can be
changed
:param fqdd: Fully Qualified Device Description of the RAID
Attribute
:param lower_bound: minimum value for the RAID attribute
:param upper_bound: maximum value for the RAID attribute
"""
super(RAIDIntegerAttribute, self).__init__(name, instance_id,
current_value,
pending_value,
read_only, fqdd)
self.lower_bound = lower_bound
self.upper_bound = upper_bound

@classmethod
def parse(cls, raid_attr_xml):
"""Parses XML and creates RAIDIntegerAttribute object"""

raid_attr = RAIDAttribute.parse(cls.namespace, raid_attr_xml)
lower_bound = utils.get_wsman_resource_attr(
raid_attr_xml, cls.namespace, 'LowerBound')
upper_bound = utils.get_wsman_resource_attr(
raid_attr_xml, cls.namespace, 'UpperBound')

if raid_attr.current_value:
raid_attr.current_value = int(raid_attr.current_value[0])
if raid_attr.pending_value:
raid_attr.pending_value = int(raid_attr.pending_value)

return cls(raid_attr.name, raid_attr.instance_id,
raid_attr.current_value, raid_attr.pending_value,
raid_attr.read_only, raid_attr.fqdd,
int(lower_bound), int(upper_bound))

def validate(self, new_value):
"""Validates new value"""

val = int(new_value)
if val < self.lower_bound or val > self.upper_bound:
msg = ('Attribute %(attr)s cannot be set to value %(val)d.'
' It must be between %(lower)d and %(upper)d.') % {
'attr': self.name,
'val': new_value,
'lower': self.lower_bound,
'upper': self.upper_bound}
return msg


class RAIDManagement(object):

NAMESPACES = [(uris.DCIM_RAIDEnumeration, RAIDEnumerableAttribute),
(uris.DCIM_RAIDString, RAIDStringAttribute),
(uris.DCIM_RAIDInteger, RAIDIntegerAttribute)]

def __init__(self, client):
"""Creates RAIDManagement object

@@ -168,6 +381,54 @@ class RAIDManagement(object):
"""
self.client = client

def list_raid_settings(self):
"""List the RAID configuration settings

:returns: a dictionary with the RAID settings using InstanceID as the
key. The attributes are either RAIDEnumerableAttribute,
RAIDStringAttribute objects.
:raises: WSManRequestFailure on request failures
:raises: WSManInvalidResponse when receiving invalid response
:raises: DRACOperationFailed on error reported back by the DRAC
interface
"""

return utils.list_settings(self.client, self.NAMESPACES,
by_name=False)

def set_raid_settings(self, raid_fqdd, new_settings):
"""Sets the RAID configuration

It sets the pending_value parameter for each of the attributes
passed in. For the values to be applied, a config job must
be created.
:param raid_fqdd: the FQDD of the RAID setting.
:param new_settings: a dictionary containing the proposed values, with
each key being the name of attribute and the value
being the proposed value.
:returns: a dictionary containing:
- The is_commit_required key with a boolean value indicating
whether a config job must be created for the values to be
applied.
- The is_reboot_required key with a RebootRequired enumerated
value indicating whether the server must be rebooted for the
values to be applied. Possible values are true and false.
:raises: WSManRequestFailure on request failures
:raises: WSManInvalidResponse when receiving invalid response
:raises: DRACOperationFailed on error reported back by the DRAC
interface
"""

return utils.set_settings('RAID',
self.client,
self.NAMESPACES,
new_settings,
uris.DCIM_RAIDService,
"DCIM_RAIDService",
"DCIM:RAIDService",
raid_fqdd,
by_name=False)

def list_raid_controllers(self):
"""Returns the list of RAID controllers



+ 14
- 4
dracclient/resources/uris.py View File

@@ -94,20 +94,30 @@ DCIM_PCIeSSDView = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
DCIM_PhysicalDiskView = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_PhysicalDiskView')

DCIM_RAIDEnumeration = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_RAIDEnumeration')

DCIM_RAIDInteger = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_RAIDInteger')

DCIM_RAIDService = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_RAIDService')

DCIM_SystemView = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemView')

DCIM_RAIDString = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_RAIDString')

DCIM_SystemEnumeration = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemEnumeration')

DCIM_SystemInteger = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemInteger')

DCIM_SystemString = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemString')

DCIM_SystemInteger = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemInteger')
DCIM_SystemView = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_SystemView')

DCIM_VirtualDiskView = ('http://schemas.dell.com/wbem/wscim/1/cim-schema/2/'
'DCIM_VirtualDiskView')

+ 178
- 0
dracclient/tests/test_raid.py View File

@@ -16,6 +16,7 @@ import collections
import lxml.etree
import mock
import random
import re
import requests_mock

import dracclient.client
@@ -117,6 +118,183 @@ class ClientRAIDManagementTestCase(base.BaseTest):
device_protocol=None,
bus=None)

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
def test_list_raid_settings(self, mock_requests,
mock_wait_until_idrac_is_ready):
expected_enum_attr = raid.RAIDEnumerableAttribute(
name='RAIDCurrentControllerMode',
instance_id='RAID.Integrated.1-1:RAIDCurrentControllerMode', # noqa
current_value=['RAID'],
pending_value=None,
read_only=True,
fqdd='RAID.Integrated.1-1',
possible_values=['RAID', 'Enhanced HBA'])
expected_string_attr = raid.RAIDStringAttribute(
name='Name',
instance_id='Disk.Virtual.1:RAID.Integrated.1-1:Name', # noqa
current_value='Virtual Disk 1',
pending_value=None,
read_only=True,
fqdd='Disk.Virtual.1:RAID.Integrated.1-1',
min_length=0,
max_length=129)
expected_integer_attr = raid.RAIDIntegerAttribute(
name='RAIDmaxSupportedVD',
instance_id='RAID.Integrated.1-1:RAIDmaxSupportedVD', # noqa
current_value=240,
pending_value=None,
read_only=True,
fqdd='RAID.Integrated.1-1',
lower_bound=0,
upper_bound=0)
# expected_string_attr
mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']}
])

raid_settings = self.drac_client.list_raid_settings()
self.assertEqual(219, len(raid_settings))
# enumerable attribute
self.assertIn(
'RAID.Integrated.1-1:RAIDCurrentControllerMode', # noqa
raid_settings)
self.assertEqual(expected_enum_attr.fqdd, raid_settings[
'RAID.Integrated.1-1:RAIDCurrentControllerMode'].fqdd) # noqa
# string attribute
self.assertIn(
'Disk.Virtual.1:RAID.Integrated.1-1:Name', # noqa
raid_settings)
self.assertEqual(expected_string_attr.fqdd,
raid_settings['Disk.Virtual.1:RAID.Integrated.1-1:Name'].fqdd) # noqa
# integer attribute
self.assertIn(
'RAID.Integrated.1-1:RAIDmaxSupportedVD', # noqa
raid_settings)
self.assertEqual(expected_integer_attr.fqdd, raid_settings[
'RAID.Integrated.1-1:RAIDmaxSupportedVD'].fqdd) # noqa

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
@mock.patch.object(dracclient.client.WSManClient,
'invoke', spec_set=True,
autospec=True)
def test_set_raid_settings(self, mock_requests,
mock_invoke,
mock_wait_until_idrac_is_ready):
mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']}])
mock_invoke.return_value = lxml.etree.fromstring(
test_utils.RAIDInvocations[uris.DCIM_RAIDService][
'SetAttributes']['ok'])

result = self.drac_client.set_raid_settings(
self.raid_controller_fqdd,
{'RAID.Integrated.1-1:RAIDRequestedControllerMode': 'RAID'})

self.assertEqual({'is_commit_required': True,
'is_reboot_required': constants.RebootRequired.true
},
result)

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
def test_set_raid_settings_with_unknown_attr(
self, mock_requests, mock_wait_until_idrac_is_ready):
mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']},
{'text': test_utils.RAIDInvocations[
uris.DCIM_RAIDService]['SetAttributes']['error']}])

self.assertRaises(exceptions.InvalidParameterValue,
self.drac_client.set_raid_settings,
self.raid_controller_fqdd, {'foo': 'bar'})

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
def test_set_raid_settings_with_unchanged_attr(
self, mock_requests, mock_wait_until_idrac_is_ready):
mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']}])
attrKey = 'Disk.Virtual.1:RAID.Integrated.1-1:RAIDdefaultWritePolicy'
result = self.drac_client.set_raid_settings(
self.raid_controller_fqdd,
{attrKey: 'WriteBack'})

self.assertEqual({'is_commit_required': False,
'is_reboot_required':
constants.RebootRequired.false},
result)

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
def test_set_raid_settings_with_readonly_attr(
self, mock_requests, mock_wait_until_idrac_is_ready):
expected_message = (
"Cannot set read-only RAID attributes: "
"['RAID.Integrated.1-1:RAIDCurrentControllerMode']."
)
mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']}])

self.assertRaisesRegexp(
exceptions.DRACOperationFailed, re.escape(expected_message),
self.drac_client.set_raid_settings,
self.raid_controller_fqdd,
{'RAID.Integrated.1-1:RAIDCurrentControllerMode': 'Enhanced HBA'})

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)
def test_set_raid_settings_with_incorrect_enum_value(
self, mock_requests, mock_wait_until_idrac_is_ready):
expected_message = ("Attribute 'RAIDRequestedControllerMode' cannot "
"be set to value 'foo'. It must be in "
"['RAID', 'Enhanced HBA', 'None'].")

mock_requests.post('https://1.2.3.4:443/wsman', [
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDEnumeration]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDString]['ok']},
{'text': test_utils.RAIDEnumerations[
uris.DCIM_RAIDInteger]['ok']}])
self.assertRaisesRegexp(
exceptions.DRACOperationFailed, re.escape(expected_message),
self.drac_client.set_raid_settings,
self.raid_controller_fqdd,
{'RAID.Integrated.1-1:RAIDRequestedControllerMode': 'foo'})

@mock.patch.object(dracclient.client.WSManClient,
'wait_until_idrac_is_ready', spec_set=True,
autospec=True)


+ 15
- 0
dracclient/tests/utils.py View File

@@ -249,6 +249,15 @@ RAIDEnumerations = {
'Raid_Status_ok': load_wsman_xml(
'virtual_disk_view-enum-with-raid-status-ok'),
'ok': load_wsman_xml('virtual_disk_view-enum-ok')
},
uris.DCIM_RAIDEnumeration: {
'ok': load_wsman_xml('raid_enumeration-enum-ok')
},
uris.DCIM_RAIDString: {
'ok': load_wsman_xml('raid_string-enum-ok')
},
uris.DCIM_RAIDInteger: {
'ok': load_wsman_xml('raid_integer-enum-ok')
}
}

@@ -287,6 +296,12 @@ RAIDInvocations = {
'raid_service-invoke-clear_foreign_config-invalid_controller'),
'foreign_drive_operation_not_supported': load_wsman_xml(
'raid_service-invoke-clear_foreign_config-not_supported'),
},
'SetAttributes': {
'ok': load_wsman_xml(
'raid_service-invoke-set_attributes-ok'),
'error': load_wsman_xml(
'raid_service-invoke-set_attributes-error'),
}
}
}


+ 2347
- 0
dracclient/tests/wsman_mocks/raid_enumeration-enum-ok.xml
File diff suppressed because it is too large
View File


+ 416
- 0
dracclient/tests/wsman_mocks/raid_integer-enum-ok.xml View File

@@ -0,0 +1,416 @@
<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope" xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing" xmlns:wsen="http://schemas.xmlsoap.org/ws/2004/09/enumeration" xmlns:wsman="http://schemas.dmtf.org/wbem/wsman/1/wsman.xsd" xmlns:n1="http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDInteger" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<s:Header>
<wsa:To>http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous</wsa:To>
<wsa:Action>http://schemas.xmlsoap.org/ws/2004/09/enumeration/EnumerateResponse</wsa:Action>
<wsa:RelatesTo>uuid:40206465-1566-46e3-bf05-9952ba57ec3c</wsa:RelatesTo>
<wsa:MessageID>uuid:6af777f7-9ef1-1ef1-b067-84d3878fd94c</wsa:MessageID>
</s:Header>
<s:Body>
<wsen:EnumerateResponse>
<wsman:Items>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSupportedVD</n1:AttributeName>
<n1:CurrentValue>240</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDmaxSupportedVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxPDsInSpan</n1:AttributeName>
<n1:CurrentValue>32</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDmaxPDsInSpan</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSpansInVD</n1:AttributeName>
<n1:CurrentValue>8</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDmaxSpansInVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDrebuildRate</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDrebuildRate</n1:InstanceID>
<n1:IsReadOnly>false</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDccRate</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDccRate</n1:InstanceID>
<n1:IsReadOnly>false</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDreconstructRate</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDreconstructRate</n1:InstanceID>
<n1:IsReadOnly>false</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDbgiRate</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDbgiRate</n1:InstanceID>
<n1:IsReadOnly>false</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprRate</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDprRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDspinDownIdleTime</n1:AttributeName>
<n1:CurrentValue>30</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDspinDownIdleTime</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>65535</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprIterations</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>RAID.Integrated.1-1:RAIDprIterations</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>1</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSupportedVD</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDmaxSupportedVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxPDsInSpan</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDmaxPDsInSpan</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSpansInVD</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDmaxSpansInVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDrebuildRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDrebuildRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDccRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDccRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDreconstructRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDreconstructRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDbgiRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDbgiRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDprRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDspinDownIdleTime</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDspinDownIdleTime</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>65535</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprIterations</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.2-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.2-1:RAIDprIterations</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>1</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSupportedVD</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDmaxSupportedVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxPDsInSpan</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDmaxPDsInSpan</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDmaxSpansInVD</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDmaxSpansInVD</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>0</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDrebuildRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDrebuildRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDccRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDccRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDreconstructRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDreconstructRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDbgiRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDbgiRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprRate</n1:AttributeName>
<n1:CurrentValue>255</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDprRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>100</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDspinDownIdleTime</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDspinDownIdleTime</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>0</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>65535</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDprIterations</n1:AttributeName>
<n1:CurrentValue>0</n1:CurrentValue>
<n1:FQDD>AHCI.Embedded.1-1</n1:FQDD>
<n1:InstanceID>AHCI.Embedded.1-1:RAIDprIterations</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>1</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.0:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.0:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.1:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.1:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.2:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.2:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.3:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.3:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.4:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.4:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.5:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.5:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.6:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.6:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.7:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.7:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.8:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.8:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
<n1:DCIM_RAIDInteger>
<n1:AttributeName>RAIDNominalMediumRotationRate</n1:AttributeName>
<n1:CurrentValue>10000</n1:CurrentValue>
<n1:FQDD>Disk.Bay.9:Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Bay.9:Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDNominalMediumRotationRate</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:LowerBound>2</n1:LowerBound>
<n1:PendingValue xsi:nil="true"/>
<n1:UpperBound>4294967295</n1:UpperBound>
</n1:DCIM_RAIDInteger>
</wsman:Items>
<wsman:EndOfSequence/>
</wsen:EnumerateResponse>
</s:Body>
</s:Envelope>

+ 21
- 0
dracclient/tests/wsman_mocks/raid_service-invoke-set_attributes-error.xml View File

@@ -0,0 +1,21 @@
<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope"
xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing"
xmlns:n1="http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDService">
<s:Header>
<wsa:To>http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous
</wsa:To>
<wsa:Action>http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDService/SetAttributesResponse
</wsa:Action>
<wsa:RelatesTo>uuid:bf8adefe-6fc0-456d-b97c-fd8d4aca2d6c
</wsa:RelatesTo>
<wsa:MessageID>uuid:84abf7b9-7176-1176-a11c-a53ffbd9bed4
</wsa:MessageID>
</s:Header>
<s:Body>
<n1:SetAttributes_OUTPUT>
<n1:Message>Invalid parameter value</n1:Message>
<n1:MessageID>STOR004</n1:MessageID>
<n1:ReturnValue>2</n1:ReturnValue>
</n1:SetAttributes_OUTPUT>
</s:Body>
</s:Envelope>

+ 24
- 0
dracclient/tests/wsman_mocks/raid_service-invoke-set_attributes-ok.xml View File

@@ -0,0 +1,24 @@
<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope"
xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing"
xmlns:n1="http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDService">
<s:Header>
<wsa:To>http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous
</wsa:To>
<wsa:Action>http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDService/SetAttributesResponse
</wsa:Action>
<wsa:RelatesTo>uuid:bf8adefe-6fc0-456d-b97c-fd8d4aca2d6c
</wsa:RelatesTo>
<wsa:MessageID>uuid:84abf7b9-7176-1176-a11c-a53ffbd9bed4
</wsa:MessageID>
</s:Header>
<s:Body>
<n1:SetAttributes_OUTPUT>
<n1:MessageID>STOR001</n1:MessageID>
<n1:Message>The command was successful for all attributes</n1:Message>
<n1:ReturnValue>0</n1:ReturnValue>
<n1:RebootRequired>Yes</n1:RebootRequired>
<n1:SetResult>Set PendingValue</n1:SetResult>
</n1:SetAttributes_OUTPUT>
</s:Body>
</s:Envelope>

+ 49
- 0
dracclient/tests/wsman_mocks/raid_string-enum-ok.xml View File

@@ -0,0 +1,49 @@
<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope"
xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing"
xmlns:wsen="http://schemas.xmlsoap.org/ws/2004/09/enumeration"
xmlns:wsman="http://schemas.dmtf.org/wbem/wsman/1/wsman.xsd"
xmlns:n1="http://schemas.dell.com/wbem/wscim/1/cim-schema/2/DCIM_RAIDString"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<s:Header>
<wsa:To>http://schemas.xmlsoap.org/ws/2004/08/addressing/role/anonymous</wsa:To>
<wsa:Action>http://schemas.xmlsoap.org/ws/2004/09/enumeration/EnumerateResponse</wsa:Action>
<wsa:RelatesTo>uuid:6f1e7eae-511a-4268-9913-c1ce1bb414be</wsa:RelatesTo>
<wsa:MessageID>uuid:6da65cf0-9cbb-1cbb-9773-deda878fd94c</wsa:MessageID>
</s:Header>
<s:Body>
<wsen:EnumerateResponse>
<wsman:Items>
<n1:DCIM_RAIDString>
<n1:AttributeName>Name</n1:AttributeName>
<n1:CurrentValue>Virtual Disk 0</n1:CurrentValue>
<n1:FQDD>Disk.Virtual.0:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Virtual.0:RAID.Integrated.1-1:Name</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:MaxLength>129</n1:MaxLength>
<n1:MinLength>0</n1:MinLength>
<n1:PendingValue xsi:nil="true"/>
</n1:DCIM_RAIDString>
<n1:DCIM_RAIDString>
<n1:AttributeName>Name</n1:AttributeName>
<n1:CurrentValue>Virtual Disk 1</n1:CurrentValue>
<n1:FQDD>Disk.Virtual.1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Disk.Virtual.1:RAID.Integrated.1-1:Name</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:MaxLength>129</n1:MaxLength>
<n1:MinLength>0</n1:MinLength>
<n1:PendingValue xsi:nil="true"/>
</n1:DCIM_RAIDString>
<n1:DCIM_RAIDString>
<n1:AttributeName>RAIDEffectiveSASAddress</n1:AttributeName>
<n1:CurrentValue>500056B3239C1AFD</n1:CurrentValue>
<n1:FQDD>Enclosure.Internal.0-1:RAID.Integrated.1-1</n1:FQDD>
<n1:InstanceID>Enclosure.Internal.0-1:RAID.Integrated.1-1:RAIDEffectiveSASAddress</n1:InstanceID>
<n1:IsReadOnly>true</n1:IsReadOnly>
<n1:MaxLength>16</n1:MaxLength>
<n1:MinLength>16</n1:MinLength>
<n1:PendingValue xsi:nil="true"/>
</n1:DCIM_RAIDString>
</wsman:Items>
</wsen:EnumerateResponse>
</s:Body>
</s:Envelope>

+ 30
- 13
dracclient/utils.py View File

@@ -320,7 +320,8 @@ def set_settings(settings_type,
target,
name_formatter=None,
include_commit_required=False,
wait_for_idrac=True):
wait_for_idrac=True,
by_name=True):
"""Generically handles setting various types of settings on the iDRAC

This method pulls the current list of settings from the iDRAC then compares
@@ -346,6 +347,8 @@ def set_settings(settings_type,
:param wait_for_idrac: indicates whether or not to wait for the
iDRAC to be ready to accept commands before issuing
the command
:param by_name: Controls whether returned dictionary uses RAID
attribute name or instance_id as key.
:returns: a dictionary containing:
- The commit_required key with a boolean value indicating
whether a config job must be created for the values to be
@@ -366,17 +369,14 @@ def set_settings(settings_type,
:raises: DRACUnexpectedReturnValue on return value mismatch
:raises: InvalidParameterValue on invalid new setting
"""

current_settings = list_settings(client, namespaces, by_name=True,
current_settings = list_settings(client, namespaces, by_name=by_name,
name_formatter=name_formatter,
wait_for_idrac=wait_for_idrac)

unknown_keys = set(new_settings) - set(current_settings)
if unknown_keys:
msg = ('Unknown %(settings_type)s attributes found: '
'%(unknown_keys)r' %
{'settings_type': settings_type,
'unknown_keys': unknown_keys})
msg = ('Unknown %(settings_type)s attributes found: %(unknown_keys)r' %
{'settings_type': settings_type, 'unknown_keys': unknown_keys})
raise exceptions.InvalidParameterValue(reason=msg)

read_only_keys = []
@@ -386,11 +386,18 @@ def set_settings(settings_type,
candidates = set(new_settings)

for attr in candidates:
if str(new_settings[attr]) == str(
current_settings[attr].current_value):
unchanged_attribs.append(attr)
elif current_settings[attr].read_only:
# There are RAID settings that can have multiple values,
# however these are all read-only attributes.
# Filter out all read-only attributes first so that we exclude
# these settings from further consideration
current_setting_value = current_settings[attr].current_value
if type(current_setting_value) is list:
current_setting_value = current_setting_value[0]

if current_settings[attr].read_only:
read_only_keys.append(attr)
elif str(new_settings[attr]) == str(current_setting_value):
unchanged_attribs.append(attr)
else:
validation_msg = current_settings[attr].validate(
new_settings[attr])
@@ -433,10 +440,20 @@ def set_settings(settings_type,
'SystemName': 'DCIM:ComputerSystem'}

properties = {'Target': target,
'AttributeName': attrib_names,
'AttributeValue': [new_settings[attr] for attr
in attrib_names]}

# To set RAID settings, above we fetched list raid settings using
# instance_id to retrieve attribute values. When we pass instance_id in
# setattribute method for setting any new RAID settings, wsman raises
# an error. So another approach to set those settings is to list raid
# settings using instance_id and for settings new settings, pass the
# attribute names in list to SetAttributes method along with the target.
# That's the reason, we need to handle RAID specific settings like below
if settings_type == 'RAID':
properties['AttributeName'] = [current_settings[attr].name for
attr in attrib_names]
else:
properties['AttributeName'] = attrib_names
doc = client.invoke(resource_uri, 'SetAttributes',
selectors, properties,
wait_for_idrac=wait_for_idrac)


Loading…
Cancel
Save