# Copyright 2016-2017 IBM Corp. 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.

"""
Unit tests for _hba module.
"""

from __future__ import absolute_import, print_function

import pytest
import re
import copy

from zhmcclient import Client, Hba, HTTPError, NotFound
from zhmcclient_mock import FakedSession
from tests.common.utils import assert_resources


# Object IDs and names of our faked HBAs:
HBA1_OID = 'hba 1-oid'
HBA1_NAME = 'hba 1'
HBA2_OID = 'hba 2-oid'
HBA2_NAME = 'hba 2'

# URIs and Object IDs of elements referenced in HBA properties:
FCP1_OID = 'fake-fcp1-oid'
PORT11_OID = 'fake-port11-oid'
PORT11_URI = '/api/adapters/{}/storage-ports/{}'.format(FCP1_OID, PORT11_OID)


class TestHba(object):
    """All tests for Hba and HbaManager classes."""

    def setup_method(self):
        """
        Set up a faked session, and add a faked CPC in DPM mode with one
        partition that has no HBAs.
        Add one FCP adapter and port.
        """

        self.session = FakedSession('fake-host', 'fake-hmc', '2.13.1', '1.8')
        self.client = Client(self.session)

        # Add a CPC in DPM mode
        self.faked_cpc = self.session.hmc.cpcs.add({
            'element-id': 'fake-cpc1-oid',
            # element-uri is set up automatically
            'parent': None,
            'class': 'cpc',
            'name': 'fake-cpc1-name',
            'description': 'CPC #1 (DPM mode)',
            'status': 'active',
            'dpm-enabled': True,
            'is-ensemble-member': False,
            'iml-mode': 'dpm',
        })
        self.cpc = self.client.cpcs.find(name='fake-cpc1-name')

        # Add a partition to the CPC
        self.faked_partition = self.faked_cpc.partitions.add({
            'element-id': 'fake-part1-oid',
            # element-uri will be automatically set
            'parent': self.faked_cpc.uri,
            'class': 'partition',
            'name': 'fake-part1-name',
            'description': 'Partition #1',
            'status': 'active',
            'initial-memory': 1024,
            'maximum-memory': 2048,
        })
        self.partition = self.cpc.partitions.find(name='fake-part1-name')

        # Add an FCP adapter and port to the CPC
        self.faked_fcp1 = self.faked_cpc.adapters.add({
            'object-id': FCP1_OID,
            'parent': self.faked_cpc.uri,
            'class': 'adapter',
            'name': 'fcp1',
            'description': 'FCP #1',
            'status': 'active',
            'type': 'fcp',
            'adapter-id': '123',
            'detected-card-type': '10gbe-roce-express',
            'card-location': '1234-5678-J.01',
            'port-count': 1,
            'network-port-uris': [],
            'state': 'online',
            'configured-capacity': 80,
            'used-capacity': 0,
            'allowed-capacity': 80,
            'maximum-total-capacity': 80,
            'physical-channel-status': 'operating',
        })
        self.faked_port11 = self.faked_fcp1.ports.add({
            'element-id': PORT11_OID,
            'parent': self.faked_fcp1.uri,
            'class': 'storage-port',
            'index': 1,
            'name': 'fake-port11-name',
            'description': 'FCP #1 Port #1',
        })
        assert PORT11_URI == self.faked_port11.uri

    def add_hba1(self):
        """Add a faked HBA 1 to the faked partition."""
        faked_hba = self.faked_partition.hbas.add({
            'element-id': HBA1_OID,
            # element-uri will be automatically set
            'parent': self.faked_partition.uri,
            'class': 'hba',
            'name': HBA1_NAME,
            'description': 'HBA ' + HBA1_NAME,
            'adapter-port-uri': PORT11_URI,
            'wwpn': 'AABBCCDDEEFF0011',
            'device-number': '1111',
        })
        return faked_hba

    def add_hba2(self):
        """Add a faked HBA 2 to the faked partition."""
        faked_hba = self.faked_partition.hbas.add({
            'element-id': HBA2_OID,
            # element-uri will be automatically set
            'parent': self.faked_partition.uri,
            'class': 'hba',
            'name': HBA2_NAME,
            'description': 'HBA ' + HBA2_NAME,
            'adapter-port-uri': PORT11_URI,
            'wwpn': 'AABBCCDDEEFF0012',
            'device-number': '1112',
        })
        return faked_hba

    def test_hbamanager_initial_attrs(self):
        """Test initial attributes of HbaManager."""

        hba_mgr = self.partition.hbas

        # Verify all public properties of the manager object
        assert hba_mgr.resource_class == Hba
        assert hba_mgr.session == self.session
        assert hba_mgr.parent == self.partition
        assert hba_mgr.partition == self.partition

    # TODO: Test for HbaManager.__repr__()

    @pytest.mark.parametrize(
        "full_properties_kwargs, prop_names", [
            (dict(),
             ['element-uri']),
            (dict(full_properties=False),
             ['element-uri']),
            (dict(full_properties=True),
             None),
        ]
    )
    def test_hbamanager_list_full_properties(
            self, full_properties_kwargs, prop_names):
        """Test HbaManager.list() with full_properties."""

        # Add two faked HBAs
        faked_hba1 = self.add_hba1()
        faked_hba2 = self.add_hba2()

        exp_faked_hbas = [faked_hba1, faked_hba2]
        hba_mgr = self.partition.hbas

        # Execute the code to be tested
        hbas = hba_mgr.list(**full_properties_kwargs)

        assert_resources(hbas, exp_faked_hbas, prop_names)

    @pytest.mark.parametrize(
        "filter_args, exp_oids", [
            ({'element-id': HBA1_OID},
             [HBA1_OID]),
            ({'element-id': HBA2_OID},
             [HBA2_OID]),
            ({'element-id': [HBA1_OID, HBA2_OID]},
             [HBA1_OID, HBA2_OID]),
            ({'element-id': [HBA1_OID, HBA1_OID]},
             [HBA1_OID]),
            ({'element-id': HBA1_OID + 'foo'},
             []),
            ({'element-id': [HBA1_OID, HBA2_OID + 'foo']},
             [HBA1_OID]),
            ({'element-id': [HBA2_OID + 'foo', HBA1_OID]},
             [HBA1_OID]),
            ({'name': HBA1_NAME},
             [HBA1_OID]),
            ({'name': HBA2_NAME},
             [HBA2_OID]),
            ({'name': [HBA1_NAME, HBA2_NAME]},
             [HBA1_OID, HBA2_OID]),
            ({'name': HBA1_NAME + 'foo'},
             []),
            ({'name': [HBA1_NAME, HBA2_NAME + 'foo']},
             [HBA1_OID]),
            ({'name': [HBA2_NAME + 'foo', HBA1_NAME]},
             [HBA1_OID]),
            ({'name': [HBA1_NAME, HBA1_NAME]},
             [HBA1_OID]),
            ({'name': '.*hba 1'},
             [HBA1_OID]),
            ({'name': 'hba 1.*'},
             [HBA1_OID]),
            ({'name': 'hba .'},
             [HBA1_OID, HBA2_OID]),
            ({'name': '.ba 1'},
             [HBA1_OID]),
            ({'name': '.+'},
             [HBA1_OID, HBA2_OID]),
            ({'name': 'hba 1.+'},
             []),
            ({'name': '.+hba 1'},
             []),
            ({'name': HBA1_NAME,
              'element-id': HBA1_OID},
             [HBA1_OID]),
            ({'name': HBA1_NAME,
              'element-id': HBA1_OID + 'foo'},
             []),
            ({'name': HBA1_NAME + 'foo',
              'element-id': HBA1_OID},
             []),
            ({'name': HBA1_NAME + 'foo',
              'element-id': HBA1_OID + 'foo'},
             []),
        ]
    )
    def test_hbamanager_list_filter_args(self, filter_args, exp_oids):
        """Test HbaManager.list() with filter_args."""

        # Add two faked HBAs
        self.add_hba1()
        self.add_hba2()

        hba_mgr = self.partition.hbas

        # Execute the code to be tested
        hbas = hba_mgr.list(filter_args=filter_args)

        assert len(hbas) == len(exp_oids)
        if exp_oids:
            oids = [hba.properties['element-id'] for hba in hbas]
            assert set(oids) == set(exp_oids)

    @pytest.mark.parametrize(
        "initial_partition_status, exp_status_exc", [
            ('stopped', None),
            ('terminated', None),
            ('starting', HTTPError({'http-status': 409, 'reason': 1})),
            ('active', None),
            ('stopping', HTTPError({'http-status': 409, 'reason': 1})),
            ('degraded', None),
            ('reservation-error', None),
            ('paused', None),
        ]
    )
    @pytest.mark.parametrize(
        "input_props, exp_prop_names, exp_prop_exc", [
            ({},
             None,
             HTTPError({'http-status': 400, 'reason': 5})),
            ({'name': 'fake-hba-x'},
             None,
             HTTPError({'http-status': 400, 'reason': 5})),
            ({'adapter-port-uri': PORT11_URI},
             None,
             HTTPError({'http-status': 400, 'reason': 5})),
            ({'name': 'fake-hba-x',
              'adapter-port-uri': PORT11_URI},
             ['element-uri', 'name', 'adapter-port-uri'],
             None),
        ]
    )
    def test_hbamanager_create(
            self, input_props, exp_prop_names, exp_prop_exc,
            initial_partition_status, exp_status_exc):
        """Test HbaManager.create()."""

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = initial_partition_status

        hba_mgr = self.partition.hbas

        if exp_status_exc:
            exp_exc = exp_status_exc
        elif exp_prop_exc:
            exp_exc = exp_prop_exc
        else:
            exp_exc = None

        if exp_exc:

            with pytest.raises(exp_exc.__class__) as exc_info:

                # Execute the code to be tested
                hba = hba_mgr.create(properties=input_props)

            exc = exc_info.value
            if isinstance(exp_exc, HTTPError):
                assert exc.http_status == exp_exc.http_status
                assert exc.reason == exp_exc.reason

        else:

            # Execute the code to be tested.
            # Note: the Hba object returned by Hba.create() has
            # the input properties plus 'element-uri' plus 'element-id'.
            hba = hba_mgr.create(properties=input_props)

            # Check the resource for consistency within itself
            assert isinstance(hba, Hba)
            hba_name = hba.name
            exp_hba_name = hba.properties['name']
            assert hba_name == exp_hba_name
            hba_uri = hba.uri
            exp_hba_uri = hba.properties['element-uri']
            assert hba_uri == exp_hba_uri

            # Check the properties against the expected names and values
            for prop_name in exp_prop_names:
                assert prop_name in hba.properties
                if prop_name in input_props:
                    value = hba.properties[prop_name]
                    exp_value = input_props[prop_name]
                    assert value == exp_value

    def test_hba_repr(self):
        """Test Hba.__repr__()."""

        # Add a faked hba
        faked_hba = self.add_hba1()

        hba_mgr = self.partition.hbas
        hba = hba_mgr.find(name=faked_hba.name)

        # Execute the code to be tested
        repr_str = repr(hba)

        repr_str = repr_str.replace('\n', '\\n')
        # We check just the begin of the string:
        assert re.match(r'^{classname}\s+at\s+0x{id:08x}\s+\(\\n.*'.
                        format(classname=hba.__class__.__name__,
                               id=id(hba)),
                        repr_str)

    @pytest.mark.parametrize(
        "initial_partition_status, exp_exc", [
            ('stopped', None),
            ('terminated', None),
            ('starting', HTTPError({'http-status': 409, 'reason': 1})),
            ('active', None),
            ('stopping', HTTPError({'http-status': 409, 'reason': 1})),
            ('degraded', None),
            ('reservation-error', None),
            ('paused', None),
        ]
    )
    def test_hba_delete(self, initial_partition_status, exp_exc):
        """Test Hba.delete()."""

        # Add a faked HBA to be tested and another one
        faked_hba = self.add_hba1()
        self.add_hba2()

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = initial_partition_status

        hba_mgr = self.partition.hbas

        hba = hba_mgr.find(name=faked_hba.name)

        if exp_exc:

            with pytest.raises(exp_exc.__class__) as exc_info:

                # Execute the code to be tested
                hba.delete()

            exc = exc_info.value
            if isinstance(exp_exc, HTTPError):
                assert exc.http_status == exp_exc.http_status
                assert exc.reason == exp_exc.reason

            # Check that the HBA still exists
            hba_mgr.find(name=faked_hba.name)

        else:

            # Execute the code to be tested.
            hba.delete()

            # Check that the HBA no longer exists
            with pytest.raises(NotFound) as exc_info:
                hba_mgr.find(name=faked_hba.name)

    def test_hba_delete_create_same_name(self):
        """Test Hba.delete() followed by Hba.create() with same name."""

        # Add a faked HBA to be tested and another one
        faked_hba = self.add_hba1()
        hba_name = faked_hba.name
        self.add_hba2()

        # Construct the input properties for a third HBA with same name
        part3_props = copy.deepcopy(faked_hba.properties)
        part3_props['description'] = 'Third HBA'

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = 'stopped'  # deletable

        hba_mgr = self.partition.hbas
        hba = hba_mgr.find(name=hba_name)

        # Execute the deletion code to be tested.
        hba.delete()

        # Check that the HBA no longer exists
        with pytest.raises(NotFound):
            hba_mgr.find(name=hba_name)

        # Execute the creation code to be tested.
        hba_mgr.create(part3_props)

        # Check that the HBA exists again under that name
        hba3 = hba_mgr.find(name=hba_name)
        description = hba3.get_property('description')
        assert description == 'Third HBA'

    @pytest.mark.parametrize(
        "input_props", [
            {},
            {'description': 'New HBA description'},
            {'device-number': 'FEDC',
             'description': 'New HBA description'},
        ]
    )
    def test_hba_update_properties(self, input_props):
        """Test Hba.update_properties()."""

        # Add a faked HBA
        faked_hba = self.add_hba1()

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = 'stopped'  # updatable

        hba_mgr = self.partition.hbas
        hba = hba_mgr.find(name=faked_hba.name)

        hba.pull_full_properties()
        saved_properties = copy.deepcopy(hba.properties)

        # Execute the code to be tested
        hba.update_properties(properties=input_props)

        # Verify that the resource object already reflects the property
        # updates.
        for prop_name in saved_properties:
            if prop_name in input_props:
                exp_prop_value = input_props[prop_name]
            else:
                exp_prop_value = saved_properties[prop_name]
            assert prop_name in hba.properties
            prop_value = hba.properties[prop_name]
            assert prop_value == exp_prop_value

        # Refresh the resource object and verify that the resource object
        # still reflects the property updates.
        hba.pull_full_properties()
        for prop_name in saved_properties:
            if prop_name in input_props:
                exp_prop_value = input_props[prop_name]
            else:
                exp_prop_value = saved_properties[prop_name]
            assert prop_name in hba.properties
            prop_value = hba.properties[prop_name]
            assert prop_value == exp_prop_value

    def test_hba_update_name(self):
        """Test Hba.update_properties() with 'name' property."""

        # Add a faked HBA
        faked_hba = self.add_hba1()
        hba_name = faked_hba.name

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = 'stopped'  # updatable

        hba_mgr = self.partition.hbas
        hba = hba_mgr.find(name=hba_name)

        new_hba_name = "new-" + hba_name

        # Execute the code to be tested
        hba.update_properties(properties={'name': new_hba_name})

        # Verify that the resource is no longer found by its old name, using
        # list() (this does not use the name-to-URI cache).
        hbas_list = hba_mgr.list(
            filter_args=dict(name=hba_name))
        assert len(hbas_list) == 0

        # Verify that the resource is no longer found by its old name, using
        # find() (this uses the name-to-URI cache).
        with pytest.raises(NotFound):
            hba_mgr.find(name=hba_name)

        # Verify that the resource object already reflects the update, even
        # though it has not been refreshed yet.
        assert hba.properties['name'] == new_hba_name

        # Refresh the resource object and verify that it still reflects the
        # update.
        hba.pull_full_properties()
        assert hba.properties['name'] == new_hba_name

        # Verify that the resource can be found by its new name, using find()
        new_hba_find = hba_mgr.find(name=new_hba_name)
        assert new_hba_find.properties['name'] == new_hba_name

        # Verify that the resource can be found by its new name, using list()
        new_hbas_list = hba_mgr.list(
            filter_args=dict(name=new_hba_name))
        assert len(new_hbas_list) == 1
        new_hba_list = new_hbas_list[0]
        assert new_hba_list.properties['name'] == new_hba_name

    @pytest.mark.parametrize(
        "initial_partition_status, exp_exc", [
            ('stopped', None),
            ('terminated', None),
            ('starting', HTTPError({'http-status': 409, 'reason': 1})),
            ('active', None),
            ('stopping', HTTPError({'http-status': 409, 'reason': 1})),
            ('degraded', None),
            ('reservation-error', None),
            ('paused', None),
        ]
    )
    def test_hba_reassign_port(self, initial_partition_status, exp_exc):
        """Test Hba.reassign_port()."""

        # Add a faked HBA to be tested.
        # Its port points to a faked URI.
        faked_hba = self.add_hba1()

        # Add a faked FCP with one port that the HBA will be reassigned to
        faked_adapter = self.faked_cpc.adapters.add({
            'object-id': 'fake-fcp1-oid',
            # object-uri is auto-set based upon object-id
            'parent': self.faked_cpc.uri,
            'class': 'adapter',
            'name': 'fake-fcp1',
            'description': 'FCP #1',
            'status': 'active',
            'type': 'fcp',
            # adapter-family is auto-set based upon type
            'adapter-id': '123',
            'detected-card-type': 'ficon-express-16s',
            'card-location': '1234-5678-J.01',
            'port-count': 1,
            'storage-port-uris': [],
            'state': 'online',
            'configured-capacity': 80,
            'used-capacity': 0,
            'allowed-capacity': 80,
            'maximum-total-capacity': 80,
            'channel-path-id': '1B',
            'physical-channel-status': 'operating',
        })
        adapter = self.cpc.adapters.find(name='fake-fcp1')
        faked_adapter.ports.add({
            'element-id': 'fake-port1-oid',
            # element-uri is auto-set based upon object-id
            'parent': faked_adapter.uri,
            'class': 'storage-port',
            'name': 'fake-port1',
            'description': 'FCP #1 Port 1',
            'index': 0,
            'fabric-id': None,
        })
        port = adapter.ports.find(name='fake-port1')

        # Set the status of the faked partition
        self.faked_partition.properties['status'] = initial_partition_status

        # The HBA object we will perform the test on
        hba = self.partition.hbas.find(name=faked_hba.name)

        # Save the HBA properties for later comparison
        hba.pull_full_properties()
        saved_properties = copy.deepcopy(hba.properties)

        if exp_exc:

            with pytest.raises(exp_exc.__class__) as exc_info:

                # Execute the code to be tested
                hba.reassign_port(port)

            exc = exc_info.value
            if isinstance(exp_exc, HTTPError):
                assert exc.http_status == exp_exc.http_status
                assert exc.reason == exp_exc.reason

            # Check that the port of the HBA is unchanged ...
            prop_name = 'adapter-port-uri'
            # ... in the resource object:
            assert hba.properties[prop_name] == saved_properties[prop_name]
            # ... and again when refreshed from the mock state:
            hba.pull_full_properties()
            assert hba.properties[prop_name] == saved_properties[prop_name]

        else:

            # Execute the code to be tested.
            hba.reassign_port(port)

            # Check that the port of the HBA has been set ...
            # ... in the resource object:
            prop_name = 'adapter-port-uri'
            assert hba.properties[prop_name] == port.uri
            # ... and again when refreshed from the mock state:
            hba.pull_full_properties()
            assert hba.properties[prop_name] == port.uri

[((184, 5, 241, 5), 'pytest.mark.parametrize', 'pytest.mark.parametrize', ({(185, 8, 185, 31): '"""filter_args, exp_oids"""', (185, 33, 240, 9): "[({'element-id': HBA1_OID}, [HBA1_OID]), ({'element-id': HBA2_OID}, [\n    HBA2_OID]), ({'element-id': [HBA1_OID, HBA2_OID]}, [HBA1_OID, HBA2_OID]\n    ), ({'element-id': [HBA1_OID, HBA1_OID]}, [HBA1_OID]), ({'element-id': \n    HBA1_OID + 'foo'}, []), ({'element-id': [HBA1_OID, HBA2_OID + 'foo']},\n    [HBA1_OID]), ({'element-id': [HBA2_OID + 'foo', HBA1_OID]}, [HBA1_OID]),\n    ({'name': HBA1_NAME}, [HBA1_OID]), ({'name': HBA2_NAME}, [HBA2_OID]), (\n    {'name': [HBA1_NAME, HBA2_NAME]}, [HBA1_OID, HBA2_OID]), ({'name': \n    HBA1_NAME + 'foo'}, []), ({'name': [HBA1_NAME, HBA2_NAME + 'foo']}, [\n    HBA1_OID]), ({'name': [HBA2_NAME + 'foo', HBA1_NAME]}, [HBA1_OID]), ({\n    'name': [HBA1_NAME, HBA1_NAME]}, [HBA1_OID]), ({'name': '.*hba 1'}, [\n    HBA1_OID]), ({'name': 'hba 1.*'}, [HBA1_OID]), ({'name': 'hba .'}, [\n    HBA1_OID, HBA2_OID]), ({'name': '.ba 1'}, [HBA1_OID]), ({'name': '.+'},\n    [HBA1_OID, HBA2_OID]), ({'name': 'hba 1.+'}, []), ({'name': '.+hba 1'},\n    []), ({'name': HBA1_NAME, 'element-id': HBA1_OID}, [HBA1_OID]), ({\n    'name': HBA1_NAME, 'element-id': HBA1_OID + 'foo'}, []), ({'name': \n    HBA1_NAME + 'foo', 'element-id': HBA1_OID}, []), ({'name': HBA1_NAME +\n    'foo', 'element-id': HBA1_OID + 'foo'}, [])]"}, {}), "('filter_args, exp_oids', [({'element-id': HBA1_OID},\n    [HBA1_OID]), ({'element-id': HBA2_OID}, [HBA2_OID]), ({'element-id': [\n    HBA1_OID, HBA2_OID]}, [HBA1_OID, HBA2_OID]), ({'element-id': [HBA1_OID,\n    HBA1_OID]}, [HBA1_OID]), ({'element-id': HBA1_OID + 'foo'}, []), ({\n    'element-id': [HBA1_OID, HBA2_OID + 'foo']}, [HBA1_OID]), ({\n    'element-id': [HBA2_OID + 'foo', HBA1_OID]}, [HBA1_OID]), ({'name':\n    HBA1_NAME}, [HBA1_OID]), ({'name': HBA2_NAME}, [HBA2_OID]), ({'name': [\n    HBA1_NAME, HBA2_NAME]}, [HBA1_OID, HBA2_OID]), ({'name': HBA1_NAME +\n    'foo'}, []), ({'name': [HBA1_NAME, HBA2_NAME + 'foo']}, [HBA1_OID]), ({\n    'name': [HBA2_NAME + 'foo', HBA1_NAME]}, [HBA1_OID]), ({'name': [\n    HBA1_NAME, HBA1_NAME]}, [HBA1_OID]), ({'name': '.*hba 1'}, [HBA1_OID]),\n    ({'name': 'hba 1.*'}, [HBA1_OID]), ({'name': 'hba .'}, [HBA1_OID,\n    HBA2_OID]), ({'name': '.ba 1'}, [HBA1_OID]), ({'name': '.+'}, [HBA1_OID,\n    HBA2_OID]), ({'name': 'hba 1.+'}, []), ({'name': '.+hba 1'}, []), ({\n    'name': HBA1_NAME, 'element-id': HBA1_OID}, [HBA1_OID]), ({'name':\n    HBA1_NAME, 'element-id': HBA1_OID + 'foo'}, []), ({'name': HBA1_NAME +\n    'foo', 'element-id': HBA1_OID}, []), ({'name': HBA1_NAME + 'foo',\n    'element-id': HBA1_OID + 'foo'}, [])])", False, 'import pytest\n'), ((443, 5, 450, 5), 'pytest.mark.parametrize', 'pytest.mark.parametrize', ({(444, 8, 444, 21): '"""input_props"""', (444, 23, 449, 9): "[{}, {'description': 'New HBA description'}, {'device-number': 'FEDC',\n    'description': 'New HBA description'}]"}, {}), "('input_props', [{}, {'description':\n    'New HBA description'}, {'device-number': 'FEDC', 'description':\n    'New HBA description'}])", False, 'import pytest\n'), ((52, 23, 52, 77), 'zhmcclient_mock.FakedSession', 'FakedSession', ({(52, 36, 52, 47): '"""fake-host"""', (52, 49, 52, 59): '"""fake-hmc"""', (52, 61, 52, 69): '"""2.13.1"""', (52, 71, 52, 76): '"""1.8"""'}, {}), "('fake-host', 'fake-hmc', '2.13.1', '1.8')", False, 'from zhmcclient_mock import FakedSession\n'), ((53, 22, 53, 42), 'zhmcclient.Client', 'Client', ({(53, 29, 53, 41): 'self.session'}, {}), '(self.session)', False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((182, 8, 182, 58), 'tests.common.utils.assert_resources', 'assert_resources', ({(182, 25, 182, 29): 'hbas', (182, 31, 182, 45): 'exp_faked_hbas', (182, 47, 182, 57): 'prop_names'}, {}), '(hbas, exp_faked_hbas, prop_names)', False, 'from tests.common.utils import assert_resources\n'), ((419, 22, 419, 57), 'copy.deepcopy', 'copy.deepcopy', ({(419, 36, 419, 56): 'faked_hba.properties'}, {}), '(faked_hba.properties)', False, 'import copy\n'), ((464, 27, 464, 56), 'copy.deepcopy', 'copy.deepcopy', ({(464, 41, 464, 55): 'hba.properties'}, {}), '(hba.properties)', False, 'import copy\n'), ((605, 27, 605, 56), 'copy.deepcopy', 'copy.deepcopy', ({(605, 41, 605, 55): 'hba.properties'}, {}), '(hba.properties)', False, 'import copy\n'), ((432, 13, 432, 36), 'pytest.raises', 'pytest.raises', ({(432, 27, 432, 35): 'NotFound'}, {}), '(NotFound)', False, 'import pytest\n'), ((518, 13, 518, 36), 'pytest.raises', 'pytest.raises', ({(518, 27, 518, 35): 'NotFound'}, {}), '(NotFound)', False, 'import pytest\n'), ((307, 17, 307, 49), 'pytest.raises', 'pytest.raises', ({(307, 31, 307, 48): 'exp_exc.__class__'}, {}), '(exp_exc.__class__)', False, 'import pytest\n'), ((263, 25, 263, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(263, 35, 263, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((265, 25, 265, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(265, 35, 265, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((275, 13, 275, 57), 'zhmcclient.HTTPError', 'HTTPError', ({(275, 23, 275, 56): "{'http-status': 400, 'reason': 5}"}, {}), "({'http-status': 400, 'reason': 5})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((278, 13, 278, 57), 'zhmcclient.HTTPError', 'HTTPError', ({(278, 23, 278, 56): "{'http-status': 400, 'reason': 5}"}, {}), "({'http-status': 400, 'reason': 5})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((281, 13, 281, 57), 'zhmcclient.HTTPError', 'HTTPError', ({(281, 23, 281, 56): "{'http-status': 400, 'reason': 5}"}, {}), "({'http-status': 400, 'reason': 5})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((388, 17, 388, 49), 'pytest.raises', 'pytest.raises', ({(388, 31, 388, 48): 'exp_exc.__class__'}, {}), '(exp_exc.__class__)', False, 'import pytest\n'), ((407, 17, 407, 40), 'pytest.raises', 'pytest.raises', ({(407, 31, 407, 39): 'NotFound'}, {}), '(NotFound)', False, 'import pytest\n'), ((364, 25, 364, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(364, 35, 364, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((366, 25, 366, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(366, 35, 366, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((609, 17, 609, 49), 'pytest.raises', 'pytest.raises', ({(609, 31, 609, 48): 'exp_exc.__class__'}, {}), '(exp_exc.__class__)', False, 'import pytest\n'), ((545, 25, 545, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(545, 35, 545, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n'), ((547, 25, 547, 69), 'zhmcclient.HTTPError', 'HTTPError', ({(547, 35, 547, 68): "{'http-status': 409, 'reason': 1}"}, {}), "({'http-status': 409, 'reason': 1})", False, 'from zhmcclient import Client, Hba, HTTPError, NotFound\n')]