]>
git.ipfire.org Git - nitsi.git/blob - test.py
13 def __init__(self
, log_level
):
14 self
.log_level
= log_level
16 def debug(self
, string
):
17 if self
.log_level
>= 4:
18 print("DEBUG: {}".format(string
))
20 def error(self
, string
):
21 print("ERROR: {}".format(string
))
24 def __init__(self
, uri
):
27 self
.connection
= None
29 def get_domain_from_name(self
, name
):
30 dom
= self
.con
.lookupByName(name
)
38 if self
.connection
== None:
40 self
.connection
= libvirt
.open(self
.uri
)
41 except BaseException
as error
:
42 self
.log
.error("Could not connect to: {}".format(self
.uri
))
44 self
.log
.debug("Connected to: {}".format(self
.uri
))
45 return self
.connection
47 return self
.connection
51 class RecipeExeption(Exception):
56 # Should read the test, check if the syntax are valid
57 # and return tuples with the ( host, command ) structure
59 def __init__(self
, path
, circle
=[]):
61 self
.recipe_file
= path
62 self
.path
= os
.path
.dirname(self
.recipe_file
)
63 self
.log
.debug("Path of recipe is: {}".format(self
.recipe_file
))
67 self
.in_recursion
= True
69 self
.in_recursion
= False
72 self
.log
.debug(circle
)
73 self
.log
.debug(self
.circle
)
75 if not os
.path
.isfile(self
.recipe_file
):
76 self
.log
.error("No such file: {}".format(self
.recipe_file
))
79 with
open(self
.recipe_file
) as fobj
:
80 self
.raw_recipe
= fobj
.readlines()
81 except FileNotFoundError
as error
:
82 self
.log
.error("No such file: {}".format(vm_xml_file
))
93 if not self
._machines
:
95 for line
in self
._recipe
:
96 if line
[0] != "all" and line
[0] not in self
._machines
:
97 self
._machines
.append(line
[0])
104 for line
in self
.raw_recipe
:
105 raw_line
= line
.split(":")
106 if len(raw_line
) < 2:
107 self
.log
.error("Error parsing the recipe in line {}".format(i
))
109 cmd
= raw_line
[1].strip()
110 raw_line
= raw_line
[0].strip().split(" ")
111 if len(raw_line
) == 0:
112 self
.log
.error("Failed to parse the recipe in line {}".format(i
))
115 if raw_line
[0].strip() == "":
116 self
.log
.error("Failed to parse the recipe in line {}".format(i
))
119 machine
= raw_line
[0].strip()
121 if len(raw_line
) == 2:
122 extra
= raw_line
[1].strip()
126 # We could get a machine here or a include statement
127 if machine
== "include":
129 path
= os
.path
.normpath(self
.path
+ "/" + path
)
130 path
= path
+ "/recipe"
131 if path
in self
.circle
:
132 self
.log
.error("Detect import loop!")
134 self
.circle
.append(path
)
135 recipe_to_include
= recipe(path
, circle
=self
.circle
)
137 if machine
== "include":
138 self
._recipe
.extend(recipe_to_include
.recipe
)
140 # Support also something like 'alice,bob: echo'
141 machines
= machine
.split(",")
142 for machine
in machines
:
143 self
._recipe
.append((machine
.strip(), extra
.strip(), cmd
.strip()))
146 if not self
.in_recursion
:
148 for line
in self
._recipe
:
150 tmp_recipe
.append(line
)
152 for machine
in self
.machines
:
153 tmp_recipe
.append((machine
.strip(), line
[1], line
[2]))
155 self
._recipe
= tmp_recipe
160 def __init__(self
, path
):
163 self
.path
= os
.path
.abspath(path
)
164 except BaseException
as e
:
165 self
.log
.error("Could not get absolute path")
167 self
.log
.debug(self
.path
)
169 self
.settings_file
= "{}/settings".format(self
.path
)
170 if not os
.path
.isfile(self
.settings_file
):
171 self
.log
.error("No such file: {}".format(self
.settings_file
))
173 self
.recipe_file
= "{}/recipe".format(self
.path
)
174 if not os
.path
.isfile(self
.recipe_file
):
175 self
.log
.error("No such file: {}".format(self
.recipe_file
))
177 def read_settings(self
):
178 self
.config
= configparser
.ConfigParser()
179 self
.config
.read(self
.settings_file
)
180 self
.name
= self
.config
["DEFAULT"]["Name"]
181 self
.description
= self
.config
["DEFAULT"]["Description"]
182 self
.copy_to
= self
.config
["DEFAULT"]["Copy_to"]
183 self
.copy_from
= self
.config
["DEFAULT"]["Copy_from"]
184 self
.copy_from
= self
.copy_from
.split(",")
187 for file in self
.copy_from
:
189 file = os
.path
.normpath(self
.path
+ "/" + file)
194 self
.virtual_environ_name
= self
.config
["VIRTUAL_ENVIRONMENT"]["Name"]
195 self
.virtual_environ_path
= self
.config
["VIRTUAL_ENVIRONMENT"]["Path"]
196 self
.virtual_environ_path
= os
.path
.normpath(self
.path
+ "/" + self
.virtual_environ_path
)
198 def virtual_environ_setup(self
):
199 self
.virtual_environ
= virtual_environ(self
.virtual_environ_path
)
201 self
.virtual_networks
= self
.virtual_environ
.get_networks()
203 self
.virtual_machines
= self
.virtual_environ
.get_machines()
205 def virtual_environ_start(self
):
206 for name
in self
.virtual_environ
.network_names
:
207 self
.virtual_networks
[name
].define()
208 self
.virtual_networks
[name
].start()
210 for name
in self
.virtual_environ
.machine_names
:
211 self
.virtual_machines
[name
].define()
212 self
.virtual_machines
[name
].create_snapshot()
213 self
.virtual_machines
[name
].copy_in(self
.copy_from
, self
.copy_to
)
214 self
.virtual_machines
[name
].start()
216 self
.log
.debug("Try to login on all machines")
217 for name
in self
.virtual_environ
.machine_names
:
218 self
.virtual_machines
[name
].login()
220 def load_recipe(self
):
222 self
.recipe
= recipe(self
.recipe_file
)
223 except BaseException
:
224 self
.log
.error("Failed to load recipe")
227 def run_recipe(self
):
228 for line
in self
.recipe
.recipe
:
229 return_value
= self
.virtual_machines
[line
[0]].cmd(line
[2])
230 self
.log
.debug("Return value is: {}".format(return_value
))
231 if return_value
!= "0" and line
[1] == "":
232 self
.log
.error("Failed to execute command '{}' on {}, return code: {}".format(line
[2],line
[0], return_value
))
234 elif return_value
== "0" and line
[1] == "!":
235 self
.log
.error("Succeded to execute command '{}' on {}, return code: {}".format(line
[2],line
[0],return_value
))
238 self
.log
.debug("Command '{}' on {} returned with: {}".format(line
[2],line
[0],return_value
))
240 def virtual_environ_stop(self
):
241 for name
in self
.virtual_environ
.machine_names
:
242 self
.virtual_machines
[name
].shutdown()
243 self
.virtual_machines
[name
].revert_snapshot()
244 self
.virtual_machines
[name
].undefine()
246 for name
in self
.virtual_environ
.network_names
:
247 self
.virtual_networks
[name
].undefine()
250 if __name__
== "__main__":
253 parser
= argparse
.ArgumentParser()
255 parser
.add_argument("-d", "--directory", dest
="dir")
257 args
= parser
.parse_args()
259 currenttest
= test(args
.dir)
260 currenttest
.read_settings()
261 currenttest
.virtual_environ_setup()
262 currenttest
.load_recipe()
264 currenttest
.virtual_environ_start()
265 currenttest
.run_recipe()
266 except BaseException
as e
:
269 currenttest
.virtual_environ_stop()