]> git.ipfire.org Git - nitsi.git/blob - src/nitsi/machine.py
Sort imports: part 1
[nitsi.git] / src / nitsi / machine.py
1 #!/usr/bin/python3
2
3 import libvirt
4 import logging
5 import os
6 import xml.etree.ElementTree as ET
7
8 from .disk import disk
9 from .serial_connection import serial_connection
10
11 logger = logging.getLogger("nitsi.machine")
12
13 class machine():
14 def __init__(self, libvirt_con, vm_xml_file, snapshot_xml_file, image, root_uid, username, password):
15 self.log = logger.getChild(os.path.basename(vm_xml_file))
16 self.con = libvirt_con
17 try:
18 with open(vm_xml_file) as fobj:
19 self.vm_xml = fobj.read()
20 except FileNotFoundError as error:
21 logger.error("No such file: {}".format(vm_xml_file))
22
23 try:
24 self.name = self.get_name()
25 except BaseException as error:
26 logger.error("Could not get name of the machine: {}".format(vm_xml_file))
27 raise error
28
29 self.log = logger.getChild(self.name)
30 self.log.debug("Name of this machine is {}".format(self.name))
31
32 try:
33 with open(snapshot_xml_file) as fobj:
34 self.snapshot_xml = fobj.read()
35 except FileNotFoundError as error:
36 self.log.error("No such file: {}".format(snapshot_xml_file))
37
38 self.image = image
39
40 if not os.path.isfile(self.image):
41 self.log.error("No such file: {}".format(self.image))
42
43 self.root_uid = root_uid
44 self.disk = disk(image)
45
46 self.username = username
47 self.password = password
48
49 def define(self):
50 self.dom = self.con.defineXML(self.vm_xml)
51 if self.dom == None:
52 self.log.error("Could not define VM")
53 raise BaseException
54
55 def start(self):
56 if self.dom.create() < 0:
57 self.log.error("Could not start VM")
58 raise BaseException
59
60 def shutdown(self):
61 if self.is_running():
62 if self.dom.shutdown() < 0:
63 self.log.error("Could not shutdown VM")
64 raise BaseException
65 else:
66 self.log.error("Domain is not running")
67
68 def undefine(self):
69 self.dom.undefine()
70
71 def create_snapshot(self):
72
73 self.snapshot = self.dom.snapshotCreateXML(self.snapshot_xml)
74
75 if not self.snapshot:
76 self.log.error("Could not create snapshot")
77 raise BaseException
78
79 def revert_snapshot(self):
80 self.dom.revertToSnapshot(self.snapshot)
81 self.snapshot.delete()
82
83 def is_running(self):
84
85 state, reason = self.dom.state()
86
87 if state == libvirt.VIR_DOMAIN_RUNNING:
88 return True
89 else:
90 return False
91
92 def get_serial_device(self):
93
94 if not self.is_running():
95 raise BaseException
96
97 xml_root = ET.fromstring(self.dom.XMLDesc(0))
98
99 elem = xml_root.find("./devices/serial/source")
100 return elem.get("path")
101
102 def get_name(self):
103 xml_root = ET.fromstring(self.vm_xml)
104
105 elem = xml_root.find("./name")
106 return elem.text
107
108 def check_is_booted_up(self):
109 serial_con = serial_connection(self.get_serial_device())
110
111 serial_con.write("\n")
112 # This will block till the domain is booted up
113 serial_con.read(1)
114
115 #serial_con.close()
116
117 def login(self, log_file, log_start_time=None, longest_machine_name=10):
118 try:
119 self.serial_con = serial_connection(self.get_serial_device(),
120 username=self.username,
121 log_file=log_file,
122 log_start_time=log_start_time,
123 name=self.name,
124 longest_machine_name=longest_machine_name)
125 self.serial_con.login(self.password)
126 except BaseException as e:
127 self.log.error("Could not connect to the domain via serial console")
128 self.log.exception(e)
129 raise e
130
131 def cmd(self, cmd):
132 return self.serial_con.command(cmd)
133
134 def copy_in(self, fr, to):
135 try:
136 self.disk.mount(self.root_uid, "/")
137 self.disk.copy_in(fr, to)
138 except BaseException as e:
139 self.log.error(e)
140 finally:
141 self.disk.umount("/")
142 self.disk.close()