resiliency: takeover: fix missing import.
[slapos.git] / slapos / recipe / addresiliency / takeover.py
1 # -*- coding: utf-8 -*-
2 import logging
3 import time
4 import traceback
5
6 import slapos
7 from slapos.slap.slap import NotFoundError
8
9 log = logging.getLogger(__name__)
10 logging.basicConfig(level=logging.DEBUG)
11
12 def takeover(server_url, key_file, cert_file, computer_guid,
13 partition_id, software_release, namebase,
14 winner_instance_suffix = None):
15 """
16 This function does
17
18 - retrieve the broken computer partition
19 - change its reference to 'broken-...' and its software type to 'frozen'
20 - retrieve the winner computer partition (attached to this process)
21 - change its reference to replace the broken one.
22 later, slapgrid will change its software_type as well.
23
24 Then, after running slapgrid-cp a few times, the winner takes over and
25 a new cp is created to replace it as an importer.
26 """
27
28 slap = slapos.slap.slap()
29 slap.initializeConnection(server_url, key_file, cert_file)
30 current_partition = slap.registerComputerPartition(computer_guid=computer_guid,
31 partition_id=partition_id)
32
33 # partition that will take over.
34 if winner_instance_suffix:
35 winner_instance_name = namebase + winner_instance_suffix
36 # XXX: we hardcode a lot of values here, because request is a settergetter, all at once.
37 cp_winner = current_partition.request(software_release=software_release,
38 software_type='%s-import' % namebase,
39 partition_reference=winner_instance_name)
40 else:
41 # This script is run in the winning partition: use this one as winner
42 cp_winner = current_partition
43 # XXX although we can already rename cp_winner, to change its software type we need to
44 # get hold of the root cp as well
45
46 cp_exporter_ref = namebase + '0' # this is ok. the boss is always number zero.
47
48 # partition to be deactivated
49 cp_broken = cp_winner.request(software_release=software_release,
50 software_type='frozen',
51 state='stopped',
52 partition_reference=cp_exporter_ref)
53
54 broken_new_ref = 'broken-{}'.format(time.strftime("%d-%b_%H:%M:%S", time.gmtime()))
55
56 log.debug("Renaming {}: {}".format(cp_broken.getId(), broken_new_ref))
57
58 cp_broken.rename(new_name=broken_new_ref)
59
60 log.debug("Renaming {}: {}".format(cp_winner.getId(), cp_exporter_ref))
61
62 # update name (and later, software type) for the partition that will take over
63 while True:
64 time.sleep(10)
65 try:
66 cp_winner.rename(new_name=cp_exporter_ref)
67 break
68 except NotFoundError:
69 traceback.print_exc()
70 log.warning('Impossible to rename. Retrying in a few seconds...')
71 log.debug('Renamed.')
72
73 cp_winner.bang(message='partitions have been renamed!')
74 # Note: Root instance will reconfigure itself the winning instance (software_type
75 # and parameters.)
76
77 def run(args):
78 slapos.recipe.addresiliency.takeover.takeover(server_url = args.pop('server_url'),
79 key_file = args.pop('key_file'),
80 cert_file = args.pop('cert_file'),
81 computer_guid = args.pop('computer_id'),
82 partition_id = args.pop('partition_id'),
83 software_release = args.pop('software'),
84 namebase = args.pop('namebase'))
85