Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 14 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,19 @@ pip install .
## configuration
### specification
#### domains
| key | necessity | description |
| ---------- | --------- | ---------------------------------------------------------------------------------------- |
| dom_name | required | `str` name of the domain |
| dom_mem | required | `int` amount of memory in megabytes |
| dom_vcpu | required | `int` core count |
| net | required | `str` name of the libVirt network to associate with the VM |
| vol_pool | required | `str` name of the libVirt pool to associate with the VM |
| vol_size | required | `int` disk size in gigabytes |
| base_image | optional | `str` full name of the `cloud-init` capable cloud image[1] |
| ip | check[2] | `ipv4` ipv4 address or network to be associated with the primary interface of the VM |
| sshpwauth | optional | `bool` whether to allow ssh authentication via passwords (VM-wide, applies to all users) |
| gateway | check[3] | `ipv4` the next hop to the default route |
| key | necessity | description |
| -------------- | --------- | ---------------------------------------------------------------------------------------- |
| dom_name | required | `str` name of the domain |
| dom_mem | required | `int` amount of memory in megabytes |
| dom_vcpu | required | `int` core count |
| net | required | `str` name of the libVirt network to associate with the VM |
| isolated_port | optional | `bool` whether port is isolated. If unset, relevant config not emitted. |
| vol_pool | required | `str` name of the libVirt pool to associate with the VM |
| vol_size | required | `int` disk size in gigabytes |
| base_image | optional | `str` full name of the `cloud-init` capable cloud image[1] |
| ip | check[2] | `ipv4` ipv4 address or network to be associated with the primary interface of the VM |
| sshpwauth | optional | `bool` whether to allow ssh authentication via passwords (VM-wide, applies to all users) |
| gateway | check[3] | `ipv4` the next hop to the default route |

__[1]__ the cloud image specified must be present in the specified volume pool
and be reachable by libVirt before cloudvirt is executed. if none provided,
Expand Down Expand Up @@ -89,6 +90,7 @@ vmspec:
dom_mem: 2048
dom_vcpu: 2
net: cloudvirt
# isolated_port: no
# ip:
# gateway:
vol_pool: cloudvirt
Expand Down
13 changes: 13 additions & 0 deletions cloudvirt/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ def _parse_vmspec(self):
else:
self.logger.error("%s is not a file", self.vmspec_file)

self.logger.debug("VMSpec YAML: %s", yaml_parsed) # pylint: disable=possibly-used-before-assignment

# - - parse yaml - - #
self.logger.info("parsing VMSpec() yaml")

Expand Down Expand Up @@ -138,6 +140,17 @@ def _parse_vmspec(self):
except KeyError:
pass

try:
if vmspec_yaml["isolated_port"] is None:
self.logger.error("isolated_port cannot be specified then left blank")

if type(vmspec_yaml["isolated_port"]).__name__ != "bool":
self.logger.error("isolated port should be a bool.")

self.vmspec.isolated_port = vmspec_yaml["isolated_port"]
except KeyError:
self.logger.debug("isolated_port not set")

def _parse_userspec(self):
# - - load yaml - - #
if not self.userspec_file:
Expand Down
9 changes: 9 additions & 0 deletions cloudvirt/driver.py
Original file line number Diff line number Diff line change
Expand Up @@ -346,10 +346,18 @@ def _gen_dom(self):
ET.SubElement(domxml_dev_iface, "mac", {"address": self.vmspec.mac_addr})
ET.SubElement(domxml_dev_iface, "model", {"type": "virtio"})

if self.vmspec.isolated_port is not None:
isolated_opt = "no"
if self.vmspec.isolated_port is True:
isolated_opt = "yes"
ET.SubElement(domxml_dev_iface, "port", {"isolated": isolated_opt})

ET.SubElement(domxml_dev, "serial", {"type": "pty"})

domxml = ET.tostring(domxml_root, encoding="unicode")

self.logger.debug("DOM XML: %s", domxml)

self.driver.defineXML(domxml)

def _update_dhcp(self):
Expand Down Expand Up @@ -494,6 +502,7 @@ def nuke(self, dom_name):
nuker.nuke()

def create(self, vmspec):
self.logger.debug("Creating with VMspec %s", vmspec.__dict__)
creator = APIDriverVMCreator(self, vmspec)
creator.create()

Expand Down
1 change: 1 addition & 0 deletions cloudvirt/spec.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ def __init__(self):
self.ip = None
self.gateway = None
self.bridge_pfxlen = None
self.isolated_port = None

# storage
self.vol_pool = None
Expand Down
17 changes: 17 additions & 0 deletions tests/test_config.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import unittest

import yaml
import os

from cloudvirt import config


def get_testfile(name):
return os.path.join(os.path.dirname(__file__), name)

class ParseConfig(unittest.TestCase):
def test_parse_vmspec_yaml(self):
filename = get_testfile("vmspec_config_1.yml")
c = config.ConfigYAML(filename, None, None)
c.run()
self.assertEqual(c.vmspec.isolated_port, False)
13 changes: 13 additions & 0 deletions tests/vmspec_config_1.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
---
vmspec:
dom_name: test_dom
dom_mem: 1512
dom_vcpu: 2
net: test_net
ip: 1.1.1.1
gateway: 2.2.2.2
vol_pool: test_vol
vol_size: 10
base_image: base-img.iso
isolated_port: no
sshpwauth: no