[PATCH 0/3] (WIP) Storagepool SCSI/FC

NOTICE: THIS FEATURE IS STILL UNDER DISCUSSION/AGREEMENT/DEVELOPMENT This patch set implements the basic functions in order to create a SCSI storagepool based in fibre channel protocol. --- What is implemented? --- * backend API It is possible to create a pool with curl POST request like: curl -X POST -u <USER> -H 'Content-type: application/json' \ -H 'Accept: application/json' http://localhost:8000/storagepools \ --data '{ \ "name": "testFC", \ "source": { "adapter_type": "scsi_host", \ "adapter_name": "scsi_hostX", \ "wwnn":"112233789", \ "wwpn":"44332211" }, \ "path": "/dev/disk/by-id", \ "type": "scsi" }' * json schema updated * created a function to test the host libvirt version SCSI FC pool and volumes have theirself configuration only after libvirt version 1.0.5. If lesser, I must use older configuration tags * updates the VM guest template with proper disk xml Create volumes in a SCSI pool is not supported by libvirt, because volumes are the LUNS preconfigured and available in the SAN. Disk will have the biggest LUN found assigned. --- What does need to be discussed? Ideas? --- 1) Backend expects right information from UI, so UI would have to ask and send 'adapter_name', 'wwnn' and 'wwpn' (other fields can be fi xed). However, the UI coud show the FC_Hosts available and let user select which one he wants. This would require to implement more ba ck-end functions to gather FC_host info, automatically (name, wwnn, wwpn). So, at this moment, just create an UI with input fields or facili tate the users life ? 2) Currently the user have no choice on with LUN to assign to a guest. LUN is selected automatically and if not LUN is available, guest will not have any disk. In order to improve this, the guest creation fase could have one more step, if the pool in the template in SCSI type. If SCSI, user could choose which LUN he wants to assign to VM. Notice that the disk size in the template have been, and will be, ig nored. What do you guys think about this approach ? 3) LUNs refresh: Once the storage admin creates more LUNs, the host admin needs to perform some commands in order to kernel 'see' and map new devices. I am implementing this backend functionality. A refresh bu tton will be necessary in the UI, where could it be placed? - In the storagepool creation window ? When select SCSI type - In the window to select the LUN, when creating new guest (if approved this extra step) - In the storagepool tab, in the pool section, if its a SCSI type - Also, when the user expands a SCSI pool section, which will show the volumes (LUNs), this function can be triggered. 4) More ideas/concerns/suggestions ? Rodrigo Trujillo (3): Storagepool: SCSI/Fibre Channel backend implementation Storagepools: Function to check libvirt version Storagepools: Assign SCSI fibre channel LUN as disk to a new guest docs/API.md | 6 ++++ src/kimchi/API.json | 18 ++++++++++- src/kimchi/model.py | 79 +++++++++++++++++++++++++++++++++++++++++++++--- src/kimchi/utils.py | 14 +++++++++ src/kimchi/vmtemplate.py | 40 +++++++++++++++++++++++- 5 files changed, 151 insertions(+), 6 deletions(-) -- 1.8.1.4

This patch creates basic functions that allow kimchi users to create an libvirt SCSI storagepool using the rest API. Signed-off-by: Rodrigo Trujillo <rodrigo.trujillo@linux.vnet.ibm.com> --- docs/API.md | 6 ++++++ src/kimchi/API.json | 18 +++++++++++++++++- src/kimchi/model.py | 55 +++++++++++++++++++++++++++++++++++++++++++++++++---- 3 files changed, 74 insertions(+), 5 deletions(-) diff --git a/docs/API.md b/docs/API.md index 4d7bdff..a09bd0c 100644 --- a/docs/API.md +++ b/docs/API.md @@ -205,6 +205,12 @@ Represents a snapshot of the Virtual Machine's primary monitor. Pool types: 'iscsi'. * username: Login username of the iSCSI target. * password: Login password of the iSCSI target. + * adapter_type: Host adapter type: 'scsi_host' or 'fc_host'. + * adapter_name: Scsi host name. + Required if 'scsi_host' type is selected. + * wwnn: Word Wide Node Name. + * wwpn: Word Wide Port Name. + ### Resource: Storage Pool diff --git a/src/kimchi/API.json b/src/kimchi/API.json index 3a3c48f..3ed5526 100644 --- a/src/kimchi/API.json +++ b/src/kimchi/API.json @@ -16,7 +16,7 @@ "type": { "description": "The type of the defined Storage Pool", "type": "string", - "pattern": "^dir|netfs|logical$", + "pattern": "^dir|netfs|logical|scsi$", "required": true }, "path": { @@ -55,6 +55,22 @@ "minimum": 1, "maximum": 65535 }, + "adapter_type": { + "description": "Host adapter type: 'scsi_host' or 'fc_host'", + "type": "string" + }, + "adapter_name": { + "description": "SCSI host name", + "type": "string" + }, + "wwnn": { + "description": "Fibre channel Word Wide Node Name", + "type": "string" + }, + "wwpn": { + "description": "Fibre channel Word Wide Port Name", + "type": "string" + }, "auth": { "description": "Storage back-end authentication information", "type": "object", diff --git a/src/kimchi/model.py b/src/kimchi/model.py index ed613b1..9cfc91c 100644 --- a/src/kimchi/model.py +++ b/src/kimchi/model.py @@ -70,7 +70,8 @@ from kimchi.networkxml import to_network_xml from kimchi.objectstore import ObjectStore from kimchi.scan import Scanner from kimchi.screenshot import VMScreenshot -from kimchi.utils import get_enabled_plugins, is_digit, kimchi_log +from kimchi.utils import get_enabled_plugins, is_digit +from kimchi.utils import is_libvirt_version_lesser, kimchi_log from kimchi.vmtemplate import VMTemplate @@ -80,7 +81,11 @@ HOST_STATS_INTERVAL = 1 VM_STATIC_UPDATE_PARAMS = {'name': './name'} VM_LIVE_UPDATE_PARAMS = {} STORAGE_SOURCES = {'netfs': {'addr': '/pool/source/host/@name', - 'path': '/pool/source/dir/@path'}} + 'path': '/pool/source/dir/@path'}, + 'scsi': {'adapter_type': '/pool/source/adapter/@type', + 'adapter_name': '/pool/source/adapter/@name', + 'wwnn': '/pool/source/adapter/@wwnn', + 'wwpn': '/pool/source/adapter/@wwpn'}} def _uri_to_name(collection, uri): @@ -1024,9 +1029,10 @@ class Model(object): return name pool = conn.storagePoolDefineXML(xml, 0) - if params['type'] in ['logical', 'dir', 'netfs']: + if params['type'] in ['logical', 'dir', 'netfs', 'scsi']: pool.build(libvirt.VIR_STORAGE_POOL_BUILD_NEW) - # autostart dir and logical storage pool created from kimchi + # autostart dir, logical, netfs and scsi storage pools created + # from kimchi pool.setAutostart(1) else: # disable autostart for others @@ -1563,6 +1569,47 @@ class LogicalPoolDef(StoragePoolDef): return xml +class ScsiPoolDef(StoragePoolDef): + poolType = 'scsi' + + def prepare(self, conn=None): + # Adapters type are only available in libvirt >= 1.0.5 + if is_libvirt_version_lesser('1.0.5'): + self.poolArgs['source']['adapter_type'] = 'scsi_host' + tmp_name = self.poolArgs['source']['adapter_name'] + self.poolArgs['source']['adapter_name'] = tmp_name.replace('scsi_','') + msg = "Libvirt version <= 1.0.5. Setting SCSI host name as '%s'; "\ + "setting SCSI adapter type as 'scsi_host'; "\ + "ignoring wwnn and wwpn." %tmp_name + kimchi_log.info(msg) + + @property + def xml(self): + # Required parameters + # name: + # source[adapter_type]: + # source[adapter_name]: + # source[wwnn]: + # source[wwpn]: + # path: + + xml = """ + <pool type='scsi'> + <name>{name}</name> + <source> + <adapter type='{source[adapter_type]}'\ + name='{source[adapter_name]}'\ + wwnn='{source[wwnn]}'\ + wwpn='{source[wwpn]}'/> + </source> + <target> + <path>{path}</path> + </target> + </pool> + """.format(**self.poolArgs) + return xml + + class IscsiPoolDef(StoragePoolDef): poolType = 'iscsi' -- 1.8.1.4

On 01/10/2014 03:34 PM, Rodrigo Trujillo wrote:
This patch creates basic functions that allow kimchi users to create an libvirt SCSI storagepool using the rest API.
Signed-off-by: Rodrigo Trujillo <rodrigo.trujillo@linux.vnet.ibm.com> --- docs/API.md | 6 ++++++ src/kimchi/API.json | 18 +++++++++++++++++- src/kimchi/model.py | 55 +++++++++++++++++++++++++++++++++++++++++++++++++---- 3 files changed, 74 insertions(+), 5 deletions(-)
diff --git a/docs/API.md b/docs/API.md index 4d7bdff..a09bd0c 100644 --- a/docs/API.md +++ b/docs/API.md @@ -205,6 +205,12 @@ Represents a snapshot of the Virtual Machine's primary monitor. Pool types: 'iscsi'. * username: Login username of the iSCSI target. * password: Login password of the iSCSI target. + * adapter_type: Host adapter type: 'scsi_host' or 'fc_host'. + * adapter_name: Scsi host name. + Required if 'scsi_host' type is selected.
Even if using 'fc_host', can't user provide SCSI host name and then Kimchi can get the pairs wwnn:wwpn automatically?
+ * wwnn: Word Wide Nde Name. + * wwpn: Word Wide Port Name. +
### Resource: Storage Pool
diff --git a/src/kimchi/API.json b/src/kimchi/API.json index 3a3c48f..3ed5526 100644 --- a/src/kimchi/API.json +++ b/src/kimchi/API.json @@ -16,7 +16,7 @@ "type": { "description": "The type of the defined Storage Pool", "type": "string", - "pattern": "^dir|netfs|logical$", + "pattern": "^dir|netfs|logical|scsi$", "required": true }, "path": { @@ -55,6 +55,22 @@ "minimum": 1, "maximum": 65535 }, + "adapter_type": { + "description": "Host adapter type: 'scsi_host' or 'fc_host'", + "type": "string" + }, + "adapter_name": { + "description": "SCSI host name", + "type": "string" + }, + "wwnn": { + "description": "Fibre channel Word Wide Node Name", + "type": "string" + }, + "wwpn": { + "description": "Fibre channel Word Wide Port Name", + "type": "string" + }, "auth": { "description": "Storage back-end authentication information", "type": "object", diff --git a/src/kimchi/model.py b/src/kimchi/model.py index ed613b1..9cfc91c 100644 --- a/src/kimchi/model.py +++ b/src/kimchi/model.py @@ -70,7 +70,8 @@ from kimchi.networkxml import to_network_xml from kimchi.objectstore import ObjectStore from kimchi.scan import Scanner from kimchi.screenshot import VMScreenshot -from kimchi.utils import get_enabled_plugins, is_digit, kimchi_log +from kimchi.utils import get_enabled_plugins, is_digit +from kimchi.utils import is_libvirt_version_lesser, kimchi_log from kimchi.vmtemplate import VMTemplate
@@ -80,7 +81,11 @@ HOST_STATS_INTERVAL = 1 VM_STATIC_UPDATE_PARAMS = {'name': './name'} VM_LIVE_UPDATE_PARAMS = {} STORAGE_SOURCES = {'netfs': {'addr': '/pool/source/host/@name', - 'path': '/pool/source/dir/@path'}} + 'path': '/pool/source/dir/@path'}, + 'scsi': {'adapter_type': '/pool/source/adapter/@type', + 'adapter_name': '/pool/source/adapter/@name', + 'wwnn': '/pool/source/adapter/@wwnn', + 'wwpn': '/pool/source/adapter/@wwpn'}}
def _uri_to_name(collection, uri): @@ -1024,9 +1029,10 @@ class Model(object): return name
pool = conn.storagePoolDefineXML(xml, 0) - if params['type'] in ['logical', 'dir', 'netfs']: + if params['type'] in ['logical', 'dir', 'netfs', 'scsi']: pool.build(libvirt.VIR_STORAGE_POOL_BUILD_NEW) - # autostart dir and logical storage pool created from kimchi + # autostart dir, logical, netfs and scsi storage pools created + # from kimchi pool.setAutostart(1) else: # disable autostart for others @@ -1563,6 +1569,47 @@ class LogicalPoolDef(StoragePoolDef): return xml
+class ScsiPoolDef(StoragePoolDef): + poolType = 'scsi' + + def prepare(self, conn=None): + # Adapters type are only available in libvirt >= 1.0.5 + if is_libvirt_version_lesser('1.0.5'): + self.poolArgs['source']['adapter_type'] = 'scsi_host' + tmp_name = self.poolArgs['source']['adapter_name'] + self.poolArgs['source']['adapter_name'] = tmp_name.replace('scsi_','') + msg = "Libvirt version <= 1.0.5. Setting SCSI host name as '%s'; "\ + "setting SCSI adapter type as 'scsi_host'; "\ + "ignoring wwnn and wwpn." %tmp_name + kimchi_log.info(msg) + + @property + def xml(self): + # Required parameters + # name: + # source[adapter_type]: + # source[adapter_name]: + # source[wwnn]: + # source[wwpn]: + # path: + + xml = """ + <pool type='scsi'> + <name>{name}</name> + <source> + <adapter type='{source[adapter_type]}'\ + name='{source[adapter_name]}'\ + wwnn='{source[wwnn]}'\ + wwpn='{source[wwpn]}'/> + </source> + <target> + <path>{path}</path> + </target> + </pool> + """.format(**self.poolArgs) + return xml + + class IscsiPoolDef(StoragePoolDef): poolType = 'iscsi'

As Kimchi supports a large range of Linux distributions and libvirt versions may differ. Libvirt functionalities may not be available, what requires different implementations of kimchi code. This patch implements a function to help identify libvirt version. Signed-off-by: Rodrigo Trujillo <rodrigo.trujillo@linux.vnet.ibm.com> --- src/kimchi/utils.py | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/src/kimchi/utils.py b/src/kimchi/utils.py index af245c6..64edc1c 100644 --- a/src/kimchi/utils.py +++ b/src/kimchi/utils.py @@ -27,6 +27,7 @@ import urllib2 from cherrypy.lib.reprconf import Parser +from libvirt import getVersion from kimchi import config @@ -96,3 +97,16 @@ def check_url_path(path): return False return True + + +def is_libvirt_version_lesser(version): + """ + Receives an string as version (ex: '0.7.1' or '1.1.2') and compares with + system libvirt version. + Returns booleanr: True if libvirt version lesser than given version + False if libvirt version is greater or equal + """ + # Versions numbers are integers: 1000000*major + 1000*minor + release + ver = version.split('.') + test_version = 1000000*int(ver[0]) + 1000*int(ver[1]) + int(ver[2]) + return (cmp(getVersion(), test_version) < 0) -- 1.8.1.4

On 01/10/2014 03:34 PM, Rodrigo Trujillo wrote:
As Kimchi supports a large range of Linux distributions and libvirt versions may differ. Libvirt functionalities may not be available, what requires different implementations of kimchi code. This patch implements a function to help identify libvirt version.
Signed-off-by: Rodrigo Trujillo <rodrigo.trujillo@linux.vnet.ibm.com> --- src/kimchi/utils.py | 14 ++++++++++++++ 1 file changed, 14 insertions(+)
diff --git a/src/kimchi/utils.py b/src/kimchi/utils.py index af245c6..64edc1c 100644 --- a/src/kimchi/utils.py +++ b/src/kimchi/utils.py @@ -27,6 +27,7 @@ import urllib2
from cherrypy.lib.reprconf import Parser +from libvirt import getVersion
from kimchi import config @@ -96,3 +97,16 @@ def check_url_path(path): return False
return True + + +def is_libvirt_version_lesser(version): + """ + Receives an string as version (ex: '0.7.1' or '1.1.2') and compares with + system libvirt version. + Returns booleanr: True if libvirt version lesser than given version + False if libvirt version is greater or equal + """ + # Versions numbers are integers: 1000000*major + 1000*minor + release + ver = version.split('.') + test_version = 1000000*int(ver[0]) + 1000*int(ver[1]) + int(ver[2]) + return (cmp(getVersion(), test_version) < 0)
We usually use FeatureTests to identify qemu/libvirt capabilities. Isn't there a way to create a feature test for this case instead of verifying the libvirt version?

This patch implements basic routines to add a disk (scsi) to a new vm template. At this moment, the LUN that will be assigned to guest template will be the first and with more space found. Signed-off-by: Rodrigo Trujillo <rodrigo.trujillo@linux.vnet.ibm.com> --- src/kimchi/model.py | 24 ++++++++++++++++++++++++ src/kimchi/vmtemplate.py | 40 +++++++++++++++++++++++++++++++++++++++- 2 files changed, 63 insertions(+), 1 deletion(-) diff --git a/src/kimchi/model.py b/src/kimchi/model.py index 9cfc91c..38efa20 100644 --- a/src/kimchi/model.py +++ b/src/kimchi/model.py @@ -1411,9 +1411,33 @@ class LibvirtVMTemplate(VMTemplate): xml = pool.XMLDesc(0) return xmlutils.xpath_get_text(xml, "/pool/target/path")[0] + def _get_storage_type(self): + pool = self._storage_validate() + xml = pool.XMLDesc(0) + return xmlutils.xpath_get_text(xml, "/pool/@type")[0] + + def _get_available_volumes(self): + pool = self._storage_validate() + vol_names = pool.listVolumes() + res = [] + for vol in vol_names: + # Considering a volume as available if there is not any format type + xml = pool.storageVolLookupByName(vol).XMLDesc(0) + if (xmlutils.xpath_get_text(xml, "/volume/target/format/@type")[0] + == 'unknown'): + res.append(( + xmlutils.xpath_get_text(xml, "/volume/target/path")[0], + int (xmlutils.xpath_get_text(xml, + "/volume/capacity")[0]) / 1024**3 ) + ) + res.sort(key=lambda x: x[1]) + return res + def fork_vm_storage(self, vm_uuid): # Provision storage: # TODO: Rebase on the storage API once upstream + if self._get_storage_type() == 'scsi': + return [] pool = self._storage_validate() vol_list = self.to_volume_list(vm_uuid) for v in vol_list: diff --git a/src/kimchi/vmtemplate.py b/src/kimchi/vmtemplate.py index 6587bbb..29c0c78 100644 --- a/src/kimchi/vmtemplate.py +++ b/src/kimchi/vmtemplate.py @@ -31,6 +31,7 @@ from kimchi import isoinfo from kimchi import osinfo from kimchi.exception import InvalidParameter, IsoFormatError from kimchi.isoinfo import IsoImage +from kimchi.utils import is_libvirt_version_lesser QEMU_NAMESPACE = "xmlns:qemu='http://libvirt.org/schemas/domain/qemu/1.0'" @@ -157,6 +158,32 @@ class VMTemplate(object): """ % params return ret + def _get_scsi_disks_xml(self): + ret = "" + # Passthrough configuration + disk_xml = """ + <disk type='volume' device='lun'> + <driver name='qemu' type='raw'/> + <source dev='%(src)s'/> + <target dev='%(dev)s' bus='scsi'/> + </disk>""" + if is_libvirt_version_lesser('1.0.5'): + disk_xml = disk_xml.replace('volume','block') + + luns = self._get_available_volumes() + for i, disk in enumerate(self.info['disks']): + index = disk.get('index', i) + try: + # Get luns with more space firstly + src = luns.pop()[0] + except IndexError: + # Skip if there is not available luns + continue + dev = "sd%s" % string.lowercase[index] + params = {'src': src, 'dev': dev} + ret = ret + disk_xml % params + return ret + def to_volume_list(self, vm_uuid): storage_path = self._get_storage_path() ret = [] @@ -202,12 +229,17 @@ class VMTemplate(object): params = dict(self.info) params['name'] = vm_name params['uuid'] = vm_uuid - params['disks'] = self._get_disks_xml(vm_uuid) params['networks'] = self._get_networks_xml() params['qemu-namespace'] = '' params['cdroms'] = '' params['qemu-stream-cmdline'] = '' + # SCSI FC disk are different + if self._get_storage_type() == 'scsi': + params['disks'] = self._get_scsi_disks_xml() + else: + params['disks'] = self._get_disks_xml(vm_uuid) + cdrom_xml = self._get_cdrom_xml(libvirt_stream, qemu_stream_dns) if not libvirt_stream and params.get('iso_stream', False): params['qemu-namespace'] = QEMU_NAMESPACE @@ -265,3 +297,9 @@ class VMTemplate(object): def _get_storage_path(self): return '' + + def _get_storage_type(self): + return '' + + def _get_available_volumes(self): + return [] -- 1.8.1.4

On 01/11/2014 01:34 AM, Rodrigo Trujillo wrote:
NOTICE: THIS FEATURE IS STILL UNDER DISCUSSION/AGREEMENT/DEVELOPMENT
This patch set implements the basic functions in order to create a SCSI storagepool based in fibre channel protocol.
--- What is implemented? --- * backend API It is possible to create a pool with curl POST request like: curl -X POST -u <USER> -H 'Content-type: application/json' \ -H 'Accept: application/json' http://localhost:8000/storagepools \ --data '{ \ "name": "testFC", \ "source": { "adapter_type": "scsi_host", \ "adapter_name": "scsi_hostX", \ "wwnn":"112233789", \ "wwpn":"44332211" }, \ "path": "/dev/disk/by-id", \ "type": "scsi" }'
* json schema updated
* created a function to test the host libvirt version SCSI FC pool and volumes have theirself configuration only after libvirt version 1.0.5. If lesser, I must use older configuration tags
* updates the VM guest template with proper disk xml Create volumes in a SCSI pool is not supported by libvirt, because volumes are the LUNS preconfigured and available in the SAN. Disk will have the biggest LUN found assigned. You could use 'volume' type of disk like this (since 1.0.5)
<disk type='volume' device='disk'> <driver name='qemu' type='raw'/> <source pool='blk-pool0' volume='blk-pool0-vol0'/> <target dev='hda' bus='ide'/> </disk>
--- What does need to be discussed? Ideas? --- 1) Backend expects right information from UI, so UI would have to ask and send 'adapter_name', 'wwnn' and 'wwpn' (other fields can be fi xed). However, the UI coud show the FC_Hosts available and let user select which one he wants. This would require to implement more ba ck-end functions to gather FC_host info, automatically (name, wwnn, wwpn). So, at this moment, just create an UI with input fields or facili tate the users life ?
Yes, it's better to collect all fc host info and provide a list of (wwnn, wwpn) to UI The host name is not very useful.
2) Currently the user have no choice on with LUN to assign to a guest. LUN is selected automatically and if not LUN is available, guest will not have any disk. In order to improve this, the guest creation fase could have one more step, if the pool in the template in SCSI type. If SCSI, user could choose which LUN he wants to assign to VM. Notice that the disk size in the template have been, and will be, ig nored. What do you guys think about this approach ?
You could use 'volume' type of disk. More importantly, we need allow creating VM from the scsi storage pool and iscsi storage poll. Otherwise, it's meaningless to add the storage pool to kimchi. At least: we should allow creating vm with existing volume (all the luns exported by scsi target are predefined) create vm with a raw image. We can't use qcow2 format on block device because we don't have monitoring facility and can't extend the disk size on demand as LVM
3) LUNs refresh: Once the storage admin creates more LUNs, the host admin needs to perform some commands in order to kernel 'see' and map new devices. I am implementing this backend functionality. A refresh bu tton will be necessary in the UI, where could it be placed? - In the storagepool creation window ? When select SCSI type - In the window to select the LUN, when creating new guest (if approved this extra step) - In the storagepool tab, in the pool section, if its a SCSI type - Also, when the user expands a SCSI pool section, which will show the volumes (LUNs), this function can be triggered.
4) More ideas/concerns/suggestions ?
Rodrigo Trujillo (3): Storagepool: SCSI/Fibre Channel backend implementation Storagepools: Function to check libvirt version Storagepools: Assign SCSI fibre channel LUN as disk to a new guest
docs/API.md | 6 ++++ src/kimchi/API.json | 18 ++++++++++- src/kimchi/model.py | 79 +++++++++++++++++++++++++++++++++++++++++++++--- src/kimchi/utils.py | 14 +++++++++ src/kimchi/vmtemplate.py | 40 +++++++++++++++++++++++- 5 files changed, 151 insertions(+), 6 deletions(-)

on 2014/01/11 01:34, Rodrigo Trujillo wrote:
NOTICE: THIS FEATURE IS STILL UNDER DISCUSSION/AGREEMENT/DEVELOPMENT
This patch set implements the basic functions in order to create a SCSI storagepool based in fibre channel protocol.
--- What is implemented? --- * backend API It is possible to create a pool with curl POST request like: curl -X POST -u <USER> -H 'Content-type: application/json' \ -H 'Accept: application/json' http://localhost:8000/storagepools \ --data '{ \ "name": "testFC", \ "source": { "adapter_type": "scsi_host", \ "adapter_name": "scsi_hostX", \ "wwnn":"112233789", \ "wwpn":"44332211" }, \ "path": "/dev/disk/by-id", \ "type": "scsi" }'
* json schema updated
* created a function to test the host libvirt version SCSI FC pool and volumes have theirself configuration only after libvirt version 1.0.5. If lesser, I must use older configuration tags
* updates the VM guest template with proper disk xml Create volumes in a SCSI pool is not supported by libvirt, because volumes are the LUNS preconfigured and available in the SAN. Disk will have the biggest LUN found assigned.
--- What does need to be discussed? Ideas? --- 1) Backend expects right information from UI, so UI would have to ask and send 'adapter_name', 'wwnn' and 'wwpn' (other fields can be fi xed). However, the UI coud show the FC_Hosts available and let user select which one he wants. This would require to implement more ba ck-end functions to gather FC_host info, automatically (name, wwnn, wwpn). So, at this moment, just create an UI with input fields or facili tate the users life ?
2) Currently the user have no choice on with LUN to assign to a guest. LUN is selected automatically and if not LUN is available, guest will not have any disk. In order to improve this, the guest creation fase could have one more step, if the pool in the template in SCSI type. If SCSI, user could choose which LUN he wants to assign to VM. Notice that the disk size in the template have been, and will be, ig nored. What do you guys think about this approach ?
I like this. When creating a guest, we can offer an check box saying "manually select volumes". If the user does not tick the box, the back-end selects a free volume automatically, otherwise, the front-end provides a volume list and user can pick one or more volumes.
3) LUNs refresh: Once the storage admin creates more LUNs, the host admin needs to perform some commands in order to kernel 'see' and map new devices. I am implementing this backend functionality. A refresh bu tton will be necessary in the UI, where could it be placed? - In the storagepool creation window ? When select SCSI type - In the window to select the LUN, when creating new guest (if approved this extra step) - In the storagepool tab, in the pool section, if its a SCSI type - Also, when the user expands a SCSI pool section, which will show the volumes (LUNs), this function can be triggered.
I like the 2nd and 3rd one, both are useful.
4) More ideas/concerns/suggestions ?
Rodrigo Trujillo (3): Storagepool: SCSI/Fibre Channel backend implementation Storagepools: Function to check libvirt version Storagepools: Assign SCSI fibre channel LUN as disk to a new guest
docs/API.md | 6 ++++ src/kimchi/API.json | 18 ++++++++++- src/kimchi/model.py | 79 +++++++++++++++++++++++++++++++++++++++++++++--- src/kimchi/utils.py | 14 +++++++++ src/kimchi/vmtemplate.py | 40 +++++++++++++++++++++++- 5 files changed, 151 insertions(+), 6 deletions(-)
-- Thanks and best regards! Zhou Zheng Sheng / 周征晟 E-mail: zhshzhou@linux.vnet.ibm.com Telephone: 86-10-82454397
participants (4)
-
Aline Manera
-
Mark Wu
-
Rodrigo Trujillo
-
Zhou Zheng Sheng