242 |
242 |
self._wait_transition(server_id, "ACTIVE", "DELETED")
|
243 |
243 |
|
244 |
244 |
@_check_kamaki
|
245 |
|
def create_server(self, image_id=None, flavor_name=None, ssh_keys=None):
|
|
245 |
def create_server(self, image=None, flavor=None, ssh_keys=None):
|
246 |
246 |
"""Create slave server"""
|
247 |
247 |
self.logger.info("Create a new server..")
|
248 |
248 |
|
... | ... | |
260 |
260 |
% _green(self.build_id))
|
261 |
261 |
|
262 |
262 |
# Find an image to use
|
263 |
|
if image_id is None:
|
264 |
|
image = self._find_image()
|
265 |
|
self.logger.debug("Will use image \"%s\"" % _green(image['name']))
|
266 |
|
image_id = image["id"]
|
267 |
|
self.logger.debug("Image has id %s" % _green(image_id))
|
|
263 |
image_id = self._find_image(image)
|
268 |
264 |
# Find a flavor to use
|
269 |
|
flavor_id = self._find_flavor(flavor_name)
|
|
265 |
flavor_id = self._find_flavor(flavor)
|
|
266 |
|
|
267 |
# Create Server
|
270 |
268 |
server = self.cyclades_client.create_server(
|
271 |
269 |
self.config.get('Deployment', 'server_name'),
|
272 |
270 |
flavor_id,
|
... | ... | |
317 |
315 |
""".format(self.config.get('Global', 'apt_repo'))
|
318 |
316 |
_run(cmd, False)
|
319 |
317 |
|
320 |
|
def _find_flavor(self, flavor_name):
|
321 |
|
"""Given a flavor_name (reg expression) find a flavor id to use"""
|
322 |
|
# Get a list of flavor names from config file
|
323 |
|
flavor_names = self.config.get('Deployment', 'flavor_name').split(",")
|
324 |
|
if flavor_name is not None:
|
|
318 |
def _find_flavor(self, flavor=None):
|
|
319 |
"""Find a suitable flavor to use
|
|
320 |
|
|
321 |
Search by name (reg expression) or by id
|
|
322 |
"""
|
|
323 |
# Get a list of flavors from config file
|
|
324 |
flavors = self.config.get('Deployment', 'flavors').split(",")
|
|
325 |
if flavor is not None:
|
325 |
326 |
# If we have a flavor_name to use, add it to our list
|
326 |
|
flavor_names.insert(0, flavor_name)
|
327 |
|
|
328 |
|
flavors = self.compute_client.list_flavors()
|
329 |
|
for flname in flavor_names:
|
330 |
|
sflname = flname.strip()
|
331 |
|
self.logger.debug("Try to find a flavor with name \"%s\"" % sflname)
|
332 |
|
fls = [f for f in flavors
|
333 |
|
if re.search(sflname, f['name']) is not None]
|
334 |
|
if fls:
|
335 |
|
self.logger.debug("Will use %s with id %s"
|
336 |
|
% (fls[0]['name'], fls[0]['id']))
|
337 |
|
return fls[0]['id']
|
|
327 |
flavors.insert(0, flavor)
|
|
328 |
|
|
329 |
list_flavors = self.compute_client.list_flavors()
|
|
330 |
for flv in flavors:
|
|
331 |
[flv_type, flv_value] = flv.strip().split(':')
|
|
332 |
if flv_type == "name":
|
|
333 |
# Filter flavors by name
|
|
334 |
self.logger.debug(
|
|
335 |
"Trying to find a flavor with name \"%s\"" % flv_value)
|
|
336 |
list_flvs = \
|
|
337 |
[f for f in list_flavors
|
|
338 |
if re.search(flv_value, f['name'], flags=re.I) is not None]
|
|
339 |
elif flv_type == "id":
|
|
340 |
# Filter flavors by id
|
|
341 |
self.logger.debug(
|
|
342 |
"Trying to find a flavor with id \"%s\"" % flv_value)
|
|
343 |
list_flvs = \
|
|
344 |
[f for f in list_flavors
|
|
345 |
if f['id'].lower() == flv_value.lower()]
|
|
346 |
else:
|
|
347 |
self.logger.error("Unrecognized flavor type %s" % flv_type)
|
|
348 |
|
|
349 |
# Check if we found one
|
|
350 |
if list_flvs:
|
|
351 |
self.logger.debug("Will use \"%s\" with id \"%s\""
|
|
352 |
% (list_flvs[0]['name'], list_flvs[0]['id']))
|
|
353 |
return list_flvs[0]['id']
|
338 |
354 |
|
339 |
355 |
self.logger.error("No matching flavor found.. aborting")
|
340 |
356 |
sys.exit(1)
|
341 |
357 |
|
342 |
|
def _find_image(self):
|
|
358 |
def _find_image(self, image=None):
|
343 |
359 |
"""Find a suitable image to use
|
344 |
360 |
|
345 |
|
It has to belong to one of the `DEFAULT_SYSTEM_IMAGES_UUID'
|
346 |
|
users and contain the word given by `image_name' option.
|
|
361 |
In case of search by name, the image has to belong to one
|
|
362 |
of the `DEFAULT_SYSTEM_IMAGES_UUID' users.
|
|
363 |
In case of search by id it only has to exist.
|
347 |
364 |
"""
|
348 |
|
image_name = self.config.get('Deployment', 'image_name').lower()
|
349 |
|
images = self.image_client.list_public(detail=True)['images']
|
350 |
|
# Select images by `system_uuid' user
|
351 |
|
images = [x for x in images
|
352 |
|
if x['user_id'] in DEFAULT_SYSTEM_IMAGES_UUID]
|
353 |
|
# Select images with `image_name' in their names
|
354 |
|
images = [x for x in images
|
355 |
|
if x['name'].lower().find(image_name) != -1]
|
356 |
|
# Let's select the first one
|
357 |
|
return images[0]
|
|
365 |
# Get a list of images from config file
|
|
366 |
images = self.config.get('Deployment', 'images').split(",")
|
|
367 |
if image is not None:
|
|
368 |
# If we have an image from command line, add it to our list
|
|
369 |
images.insert(0, image)
|
|
370 |
|
|
371 |
list_images = self.image_client.list_public(detail=True)['images']
|
|
372 |
for img in images:
|
|
373 |
[img_type, img_value] = img.strip().split(':')
|
|
374 |
if img_type == "name":
|
|
375 |
# Filter images by name
|
|
376 |
self.logger.debug(
|
|
377 |
"Trying to find an image with name \"%s\"" % img_value)
|
|
378 |
list_imgs = \
|
|
379 |
[i for i in list_images
|
|
380 |
if i['user_id'] in DEFAULT_SYSTEM_IMAGES_UUID and
|
|
381 |
re.search(img_value, i['name'], flags=re.I) is not None]
|
|
382 |
elif img_type == "id":
|
|
383 |
# Filter images by id
|
|
384 |
self.logger.debug(
|
|
385 |
"Trying to find an image with id \"%s\"" % img_value)
|
|
386 |
list_imgs = \
|
|
387 |
[i for i in list_images
|
|
388 |
if i['id'].lower() == img_value.lower()]
|
|
389 |
else:
|
|
390 |
self.logger.error("Unrecognized image type %s" % img_type)
|
|
391 |
sys.exit(1)
|
|
392 |
|
|
393 |
# Check if we found one
|
|
394 |
if list_imgs:
|
|
395 |
self.logger.debug("Will use \"%s\" with id \"%s\""
|
|
396 |
% (list_imgs[0]['name'], list_imgs[0]['id']))
|
|
397 |
return list_imgs[0]['id']
|
|
398 |
|
|
399 |
# We didn't found one
|
|
400 |
self.logger.error("No matching image found.. aborting")
|
|
401 |
sys.exit(1)
|
358 |
402 |
|
359 |
403 |
def _get_server_ip_and_port(self, server):
|
360 |
404 |
"""Compute server's IPv4 and ssh port number"""
|
... | ... | |
614 |
658 |
self.logger.info("Deploy Synnefo..")
|
615 |
659 |
if schema is None:
|
616 |
660 |
schema = self.config.get('Global', 'schema')
|
617 |
|
self.logger.debug("Will use %s schema" % schema)
|
|
661 |
self.logger.debug("Will use \"%s\" schema" % schema)
|
618 |
662 |
|
619 |
663 |
schema_dir = os.path.join(self.ci_dir, "schemas/%s" % schema)
|
620 |
664 |
if not (os.path.exists(schema_dir) and os.path.isdir(schema_dir)):
|