openmainframeproject / feilong

Feilong is a open source z/VM cloud connector project under the Open Mainframe Project umbrella that will accelerate the z/VM adoption, extending its ecosystem and its user experience. It provides a set of APIs to operate z/VM including guest, image, network, volume etc.
https://www.openmainframeproject.org/projects/feilong
Apache License 2.0
36 stars 70 forks source link

get_volume_connector_based_on_pchid_info #748

Closed jackydalong closed 1 year ago

jackydalong commented 1 year ago

modification summary

zvmsdk/volumeop.py

def get_volume_connector(self, assigner_id, reserve,
                         fcp_template_id=None, sp_name=None, pchid_info=None):

    if reserve:

        # add is_reserved_changed
        is_reserved_changed, fcp_list, fcp_template_id = 

            self.fcp_mgr.allocate_fcp_devices(assigner_id, fcp_template_id,
                                              sp_name, pchid_info)

    else:

        # add is_reserved_changed
        is_reserved_changed, fcp_list = 

            self.fcp_mgr.release_fcp_devices(assigner_id, fcp_template_id)

    # more info added in connector 
    connector = {'zvm_fcp': fcp_ids,
                 'wwpns': wwpns,
                 'phy_to_virt_initiators': phy_virt_wwpn_map,
                 'host': ret_host,
                 'fcp_paths': len(fcp_list),
                 'fcp_template_id': fcp_template_id,
                 'cpc_sn': cpc_sn,                          --| 
                 'cpc_name': cpc_name,                        |
                 'lpar': lpar,                                |- new added
                 'hypervisor_hostname': hypervisor_hostname,  |
                 'pchid_fcp_map': pchid_fcp_map,              |
                 'is_reserved_changed': is_reserved_changed --|
                 }
    return connector

def allocate_fcp_devices(self, assigner_id, fcp_template_id,
                         sp_name, pchid_info):

    # add is_reserved_changed
    is_reserved_changed = False

    # add pchid and path in fcp_list
    fcp_list = self.db.get_allocated_fcps_from_assigner(
                        assigner_id, fcp_template_id)

    if not fcp_list:

        _sync_db_with_zvm()

        if CONF.volume.get_fcp_pair_with_same_index:

            # add pchid and path in fcp_list
            fcp_list = self.db.get_fcp_devices_with_same_index(
                            fcp_template_id)

        else:

            # add pchid and path in fcp_list
            fcp_list = self.db.get_fcp_devices(fcp_template_id, pchid_info)

        # reserve_fcps
        fcp_ids = [fcp['fcp_id'] for fcp in fcp_list]
        self.db.reserve_fcps(fcp_ids, assigner_id, fcp_template_id)

        # is_reserved_changed
        is_reserved_changed = True

    return is_reserved_changed, fcp_list, fcp_template_id

zvmsdk/database.py

get_fcp_devices_with_pchid


Tests: call ZCC API directly

Cases for reserve=True

case1: 1st time, reserve=True for a userid

>>> pf = {'02e4': {'allocated': 126, 'max': 128},
...       '021C': {'allocated': 104, 'max': 110},
...       '0264': {'allocated': 126, 'max': 128},
...       'CCCC': {'allocated': 100, 'max': 90}}
>>>
... tid = '5129ba98-3b34-11ee-82df-0201012eebe3';
>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=True, fcp_template_id=tid, pchid_info=pf))

{'errmsg': '',
 'modID': None,
 'output': {'cpc_name': 'M54',
            'cpc_sn': '0000000000082F57',
            'fcp_paths': 2,
            'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3',
            'host': 'BOEM5401_JACKTEST',
            'hypervisor_hostname': 'BOEM5401',
            'is_reserved_changed': True,         <-------
            'lpar': 'ZVM4OCP1',
            'pchid_fcp_map': {'0264': ['1C17'], '02E4': ['1D17']},
            'phy_to_virt_initiators': {'c05076de33000363': 'c05076de33002e41',
                                       'c05076de3300036a': 'c05076de33002641'},
            'wwpns': ['c05076de3300036a', 'c05076de33000363'],
            'zvm_fcp': ['1c17', '1d17']},
 'overallRC': 0,
 'rc': 0,
 'rs': 0}

[2023-08-30 04:18:38] [INFO] get_volume_connector: Enter allocate_fcp_devices. [2023-08-30 04:18:38] [INFO] Previously allocated FCP devices [] for instance JACKTEST in FCP Multipath Template 5129ba98-3b34-11ee-82df-0201012eebe3. [2023-08-30 04:18:38] [INFO] Enter: Sync FCP DB with FCP info queried from z/VM. [2023-08-30 04:18:38] [INFO] Querying FCP status on z/VM. [2023-08-30 04:18:41] [INFO] New FCP devices found on z/VM: set() [2023-08-30 04:18:41] [INFO] FCP devices exist in FCP table but not in z/VM any more: set() [2023-08-30 04:18:41] [INFO] FCP devices removed from FCP table: set() [2023-08-30 04:18:41] [INFO] FCP devices exist in both FCP table and z/VM: {'1b0a', '1d1c', '1c18', '1a1c', '1c07', '1c14', '1d01', '1d11', '1d19', '1d1b', '1a13', '1b05', '1b1c', '1c0e', '1d17', '1a10', '1a1a', '1d13', '1c03', '1d0b', '1d12', '1d06', '1d18', '1b1a', '1a16', '1a17', '1c02', '1b13', '1c05', '1b04', '1b06', '1b19', '1d04', '1b17', '1d15', '1d1a', '1a15', '1a0e', '1d08', '1d02', '1b1b', '1a18', '1c0d', '1d0d', '1c17', '1d10', '1c13', '1a00', '1d0e', '1b01', '1b15', '1b1e', '1a1f', '000e', '1b11', '1a03', '1a0a', '1b07', '1d05', '1a14', '1b0f', '1a19', '1c1d', '1b0e', '1b0d', '1c1c', '1c09', '1d1d', '1c00', '1a02', '1b0b', '1c04', '1b03', '1c1b', '1d03', '1a0c', '1c11', '1b02', '1c15', '1a04', '1c0f', '1a1d', '1d0f', '1b09', '1c1e', '1c1f', '1a09', '1b16', '1b1f', '1c0c', '1c01', '1b10', '1d14', '1a1e', '1d09', '1a0f', '1d16', '1c16', '1a12', '1c0a', '1d0a', '1b08', '1a0b', '1c12', '1c10', '1c0b', '1b18', '1c1a', '1c08', '1a08', '1d0c', '1a06', '1a1b', '1a0d', '1b12', '1a07', '1d1f', '1b00', '1c06', '1a11', '1c19', '1b0c', '1b1d', '1a05', '1b14', '1d00', '1d07', '1d1e'} [2023-08-30 04:18:41] [INFO] FCP devices need to update records in fcp table: [] [2023-08-30 04:18:41] [INFO] Exit: Sync FCP DB with FCP info queried from z/VM. [2023-08-30 04:18:41] [INFO] There is no previously allocated FCP devices for the instance JACKTEST, allocating new ones. [2023-08-30 04:18:41] [INFO] free_pchids_per_path:

{0: ['0264', '02E4'], 
 1: ['021C', '02E4']}

[2023-08-30 04:18:41] [INFO] free_count_in_pchid_info:

{'02E4': 2, 
 '021C': 6, 
 '0264': 2, 
 'CCCC': -10}

[2023-08-30 04:18:41] [INFO] after _calculate_weight, pchids_per_path_combinations:

[{0: '0264', 1: '021C', 'weight': 2.0}, 
 {0: '0264', 1: '02E4', 'weight': 2.0}, 
 {0: '02E4', 1: '021C', 'weight': 2.0}, 
 {0: '02E4', 1: '02E4', 'weight': 1.0}]

[2023-08-30 04:18:41] [INFO] after _remove_invalid_weight, pchids_per_path_combinations:

[{0: '0264', 1: '021C', 'weight': 2.0}, 
 {0: '0264', 1: '02E4', 'weight': 2.0}, 
 {0: '02E4', 1: '021C', 'weight': 2.0}, 
 {0: '02E4', 1: '02E4', 'weight': 1.0}]

[2023-08-30 04:18:41] [INFO] after _select_max_weight, pchids_per_path_combinations:

[{0: '0264', 1: '021C', 'weight': 2.0}, 
 {0: '0264', 1: '02E4', 'weight': 2.0}, 
 {0: '02E4', 1: '021C', 'weight': 2.0}]

[2023-08-30 04:18:41] [INFO] after _select_most_distributed_pchids, pchids_per_path_combinations:

[{0: '0264', 1: '021C'}, 
 {0: '0264', 1: '02E4'}, 
 {0: '02E4', 1: '021C'}]

[2023-08-30 04:18:41] [INFO] final_pchid_per_path:

{0: '0264', 1: '02E4'}

[2023-08-30 04:18:41] [INFO] after _get_one_random_fcp_combinations, fcp_list:

[{'fcp_id': '1C17', 'wwpn_npiv': 'c05076de3300036a', 'wwpn_phy': 'c05076de33002641', 'path': 0, 'pchid': '0264'}, 
 {'fcp_id': '1D17', 'wwpn_npiv': 'c05076de33000363', 'wwpn_phy': 'c05076de33002e41', 'path': 1, 'pchid': '02E4'}]

[2023-08-30 04:18:41] [INFO] Newly allocated ['1C17', '1D17'] FCP devices for instance JACKTEST and FCP Multipath Template 5129ba98-3b34-11ee-82df-0201012eebe3 [2023-08-30 04:18:41] [INFO] get_volume_connector: Exit allocate_fcp_devices ['1C17', '1D17'] [2023-08-30 04:18:41] [INFO] get_volume_connector returns

{'zvm_fcp': ['1c17', '1d17'], 
 'wwpns': ['c05076de3300036a', 'c05076de33000363'], 
 'phy_to_virt_initiators': {'c05076de3300036a': 'c05076de33002641', 'c05076de33000363': 'c05076de33002e41'}, 
 'host': 'BOEM5401_JACKTEST', 
 'fcp_paths': 2, 
 'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3', 
 'cpc_sn': '0000000000082F57', 
 'cpc_name': 'M54', 
 'lpar': 'ZVM4OCP1', 
 'hypervisor_hostname': 'BOEM5401', 
 'pchid_fcp_map': {'0264': ['1C17'], '02E4': ['1D17']}, 
 'is_reserved_changed': True} for instance JACKTEST and FCP Multipath Template 5129ba98-3b34-11ee-82df-0201012eebe3

[2023-08-30 04:18:41] [INFO] synchronized: released lock volumeAttachOrDetach-JACKTEST, held 2.32 seconds, current thread: Thread-57 [2023-08-30 04:18:41] [INFO] synchronized: after releasing lock volumeAttachOrDetach-JACKTEST, concurrent thread count 0, current thread: Thread-57

- sqlite FCP DB
```shell
sqlite> SELECT fcp.fcp_id, path, pchid, assigner_id, reserved, tf.tmpl_id FROM template_fcp_mapping as tf INNER JOIN fcp ON tf.fcp_id=fcp.fcp_id WHERE tf.tmpl_id='5129ba98-3b34-11ee-82df-0201012eebe3' AND reserved = 1 ORDER BY path, pchid, fcp.fcp_id;
fcp_id      path        pchid       assigner_id  reserved    tmpl_id
----------  ----------  ----------  -----------  ----------  ------------------------------------
1c17        0           0264        JACKTEST     1           5129ba98-3b34-11ee-82df-0201012eebe3
1a18        0           02e4        JACK0002     1           5129ba98-3b34-11ee-82df-0201012eebe3
1b17        1           021c        JACK0002     1           5129ba98-3b34-11ee-82df-0201012eebe3
1d17        1           02e4        JACKTEST     1           5129ba98-3b34-11ee-82df-0201012eebe3

case2: 2nd time, reserve=True for a userid

>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=True, fcp_template_id=tid, pchid_info=pf))
{'errmsg': '',
 'modID': None,
 'output': {'cpc_name': 'M54',
            'cpc_sn': '0000000000082F57',
            'fcp_paths': 2,
            'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3',
            'host': 'BOEM5401_JACKTEST',
            'hypervisor_hostname': 'BOEM5401',
            'is_reserved_changed': False,        <-------
            'lpar': 'ZVM4OCP1',
            'pchid_fcp_map': {'0264': ['1C17'], '02E4': ['1D17']},
            'phy_to_virt_initiators': {'c05076de33000363': 'c05076de33002e41',
                                       'c05076de3300036a': 'c05076de33002641'},
            'wwpns': ['c05076de3300036a', 'c05076de33000363'],
            'zvm_fcp': ['1c17', '1d17']},
 'overallRC': 0,
 'rc': 0,
 'rs': 0}

case3: reserve=True without passing pchid_info : raise Exception as expected

>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=True, fcp_template_id=tid))
{'errmsg':
 'Failed to get volume connector of JACKTEST because The PCHIDs '
           "['021C', '0264', '02E4'] are missing in the pchid_info {}, though "
           'are included in the FCP multipath template '
           '(id=5129ba98-3b34-11ee-82df-0201012eebe3).',
 'modID': 30,
 'output': '',
 'overallRC': 300,
 'rc': 300,
 'rs': 11}

[2023-09-03 09:50:14] [INFO] The msg <{'overallRC': 300, 'modID': 30, 'rc': 300, 'rs': 11, 'errmsg': "Failed to get volume connector of JACKTEST because The PCHIDs ['021C', '0264', '02E4'] are missing in the pchid_info {}, though are included in the FCP multipath template (id=5129ba98-3b34-11ee-82df-0201012eebe3).", 'output': ''}> lead to return internal error


#### case4: reserve=True for a userid, when
- some path of the template does NOT have free FCP devices

```python
>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=True, fcp_template_id=tid, pchid_info=pf))
{'errmsg': '',
 'modID': None,
 'output': {'cpc_name': 'M54',
            'cpc_sn': '0000000000082F57',
            'fcp_paths': 0,
            'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3',
            'host': '',
            'hypervisor_hostname': 'BOEM5401',
            'is_reserved_changed': False,        <-------
            'lpar': 'ZVM4OCP1',
            'pchid_fcp_map': {},
            'phy_to_virt_initiators': {},
            'wwpns': [],
            'zvm_fcp': []},
 'overallRC': 0,
 'rc': 0,
 'rs': 0}

[2023-08-31 00:38:15] [INFO] get_volume_connector: Enter allocate_fcp_devices. [2023-08-31 00:38:15] [INFO] Previously allocated FCP devices [] for instance JACKTEST in FCP Multipath Template 5129ba98-3b34-11ee-82df-0201012eebe3. [2023-08-31 00:38:15] [INFO] Enter: Sync FCP DB with FCP info queried from z/VM. [2023-08-31 00:38:15] [INFO] Querying FCP status on z/VM. [2023-08-31 00:38:18] [INFO] New FCP devices found on z/VM: set() [2023-08-31 00:38:18] [INFO] FCP devices exist in FCP table but not in z/VM any more: set() [2023-08-31 00:38:18] [INFO] FCP devices removed from FCP table: set() [2023-08-31 00:38:18] [INFO] FCP devices exist in both FCP table and z/VM: {'1d1b', '1a0f', '1a09', '1b18', '1b02', '1d0d', '1a15', '1c15', '1b0b', '1a08', '1b0e', '1b01', '1c1a', '1a0a', '1d06', '1c0e', '1a0c', '1c0c', '1a19', '1b09', '1a10', '1c13', '1c0f', '1a1b', '1a04', '1a05', '1d14', '1b12', '1b17', '1a18', '1d00', '1c1d', '1d1c', '1c02', '1c18', '1d05', '1b16', '1c09', '1b13', '1c0d', '1c01', '1b19', '1a1a', '1a06', '1c05', '1d1e', '1c08', '1b11', '1c1b', '1b1c', '1b04', '1a14', '1c11', '1a17', '1d09', '1c14', '1c03', '1a16', '1d08', '1c06', '1d0a', '1b1e', '1a1f', '1b07', '1b0d', '1c19', '1a1d', '1c16', '1d16', '1a11', '1d11', '1d13', '1a0d', '1b1a', '1d1d', '1a0e', '1d17', '1d1a', '1c0b', '1d0e', '1b0c', '1d0b', '1b03', '1c07', '1c04', '1b1d', '1a0b', '1c10', '1b00', '1d12', '1d0c', '1a12', '1c0a', '1a00', '1b0f', '1d19', '1d18', '1a1c', '1b15', '1d03', '1b1f', '1c1e', '1c1c', '000e', '1a07', '1b10', '1b06', '1c1f', '1d02', '1d15', '1d10', '1b14', '1d07', '1d1f', '1b0a', '1c12', '1a13', '1b1b', '1a02', '1a1e', '1d0f', '1b08', '1c00', '1d04', '1a03', '1c17', '1d01', '1b05'} [2023-08-31 00:38:18] [INFO] FCP devices need to update records in fcp table: [] [2023-08-31 00:38:18] [INFO] Exit: Sync FCP DB with FCP info queried from z/VM. [2023-08-31 00:38:18] [INFO] There is no previously allocated FCP devices for the instance JACKTEST, allocating new ones. [2023-08-31 00:38:18] [INFO] free_pchids_per_path:

 {1: ['021C', '02E4']}

[2023-08-31 00:38:18] [INFO]

Not all paths of FCP Multipath Template (id=5129ba98-3b34-11ee-82df-0201012eebe3) have available FCP devices. 
The count of minimum FCP device path is 2. 
The count of total paths is 2. 
The count of paths with available FCP devices is 1, 
which is less than the total path count.

[2023-08-31 00:38:18] [ERROR]

The count of paths with available FCP devices must not be less than that of minimum FCP device path, 
return empty list to abort the volume attachment.

[2023-08-31 00:38:18] [INFO] get_volume_connector: Exit allocate_fcp_devices [] [2023-08-31 00:38:18] [ERROR]

Not enough available FCP devices found from FCP Multipath Template(id=5129ba98-3b34-11ee-82df-0201012eebe3)

[2023-08-31 00:38:18] [INFO] synchronized: released lock volumeAttachOrDetach-JACKTEST, held 2.64 seconds, current thread: Thread-1302 [2023-08-31 00:38:18] [INFO] synchronized: after releasing lock volumeAttachOrDetach-JACKTEST, concurrent thread count 0, current thread: Thread-1302


### Cases for reserve=False (no need to pass pchid_info)
#### case1: reserve=False for a userid, when
- connections != 0
- without passing pchid_info
```python
>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=False, fcp_template_id=tid))
{'errmsg': '',
 'modID': None,
 'output': {'cpc_name': 'M54',
            'cpc_sn': '0000000000082F57',
            'fcp_paths': 2,
            'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3',
            'host': 'BOEM5401_JACKTEST',
            'hypervisor_hostname': 'BOEM5401',
            'is_reserved_changed': False,        <-------
            'lpar': 'ZVM4OCP1',
            'pchid_fcp_map': {'0264': ['1C17'], '02E4': ['1D17']},
            'phy_to_virt_initiators': {'c05076de33000363': 'c05076de33002e41',
                                       'c05076de3300036a': 'c05076de33002641'},
            'wwpns': ['c05076de3300036a', 'c05076de33000363'],
            'zvm_fcp': ['1c17', '1d17']},
 'overallRC': 0,
 'rc': 0,
 'rs': 0}

case2: reserve=False for a userid, when

pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=False, fcp_template_id=tid, pchid_info=pf)) {'errmsg': '', 'modID': None, 'output': {'cpc_name': 'M54', 'cpc_sn': '0000000000082F57', 'fcp_paths': 2, 'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3', 'host': 'BOEM5401_JACKTEST', 'hypervisor_hostname': 'BOEM5401', 'is_reserved_changed': False, <------- 'lpar': 'ZVM4OCP1', 'pchid_fcp_map': {'0264': ['1C17'], '02E4': ['1D17']}, 'phy_to_virt_initiators': {'c05076de33000363': 'c05076de33002e41', 'c05076de3300036a': 'c05076de33002641'}, 'wwpns': ['c05076de3300036a', 'c05076de33000363'], 'zvm_fcp': ['1c17', '1d17']}, 'overallRC': 0, 'rc': 0, 'rs': 0}

case3: reserve=False for a userid, when

case4: reserve=False for a userid, when

>>> pp(conn.send_request('get_volume_connector', 'JACKTEST', reserve=False, fcp_template_id=tid))
{'errmsg': '',
 'modID': None,
 'output': {'cpc_name': 'M54',
            'cpc_sn': '0000000000082F57',
            'fcp_paths': 0,
            'fcp_template_id': '5129ba98-3b34-11ee-82df-0201012eebe3',
            'host': '',
            'hypervisor_hostname': 'BOEM5401',
            'is_reserved_changed': False,        <-------
            'lpar': 'ZVM4OCP1',
            'pchid_fcp_map': {},
            'phy_to_virt_initiators': {},
            'wwpns': [],
            'zvm_fcp': []},
 'overallRC': 0,
 'rc': 0,
 'rs': 0}