no functional change, but a small cleanup on how sfa users are configured
[tests.git] / system / TestSliceSfa.py
1 # Thierry Parmentelat <thierry.parmentelat@inria.fr>
2 # Copyright (C) 2010 INRIA 
3 #
4
5 import time
6 from datetime import datetime, timedelta
7
8 import utils
9 from TestNode import TestNode
10 from TestUser import TestUser
11 from TestBoxQemu import TestBoxQemu
12 from TestSsh import TestSsh
13
14 from Completer import Completer, CompleterTask
15 from TestSlice import CompleterTaskSshSlice
16
17 class TestSliceSfa:
18
19     def __init__ (self, test_auth_sfa, slice_spec):
20         self.test_auth_sfa=test_auth_sfa
21         self.slice_spec=slice_spec
22         # shortcuts
23         self.test_plc=self.test_auth_sfa.test_plc
24
25     def hrn (self): 
26         return self.test_auth_sfa.obj_hrn(self.slice_spec['name'])
27     def sfi_path (self):
28         return self.test_auth_sfa.sfi_path()
29
30     # send back up to the TestAuthSfa
31     def rspec_style (self): return self.test_auth_sfa.rspec_style()
32     def sfi_pi(self,*args,**kwds): return self.test_auth_sfa.sfi_pi(*args, **kwds)
33     def sfi_user(self,*args,**kwds): return self.test_auth_sfa.sfi_user(*args, **kwds)
34
35     def discover_option(self):
36         if self.rspec_style()=='pg': return "-r GENI"
37         else:                        return "-r sfa"
38
39     # those are step names exposed as methods of TestPlc, hence the _sfa
40
41     # needs to be run as pi
42     def sfa_add_slice(self,options):
43         "run sfi add (on Registry)"
44         sfi_command="add"
45         sfi_command += " --type slice"
46         sfi_command += " --xrn %s"%self.hrn()
47         for opt in self.slice_spec['add_options']:
48             sfi_command += " %s"%(opt)
49         return self.test_plc.run_in_guest(self.sfi_pi(sfi_command))==0
50
51     def sfa_renew_slice(self, options):
52         "run sfi renew (on Aggregates)"
53         too_late =  datetime.now() + timedelta(weeks=52)
54         one_month = datetime.now() + timedelta(weeks=4)
55         # we expect this to fail on too long term attemps, but to succeed otherwise
56         overall=True
57         for ( renew_until, expected) in [ (too_late, False), (one_month, True) ] :
58             sfi_command="renew"
59             sfi_command += " %s"%self.hrn()
60             sfi_command += " %s"%renew_until.strftime("%Y-%m-%d")
61             succeeded = self.test_plc.run_in_guest(self.sfi_user(sfi_command))==0
62             if succeeded!=expected:
63                 utils.header ("Expecting success=%s, got %s"%(expected,succeeded))
64                 # however it turns out sfi renew always returns fine....
65                 #overall=False
66             # so for helping manual checks:
67             sfi_command="show -k hrn -k expires %s"%self.hrn()
68             self.test_plc.run_in_guest(self.sfi_user(sfi_command))
69         return overall
70
71     # helper - filename to store a given result
72     def _resname (self,name,ext): return "%s.%s"%(name,ext)
73     def adfile (self): return self._resname("ad","rspec")
74     def reqfile (self): return self._resname("req","rspec")
75     def nodefile (self): return self._resname("nodes","txt")
76     
77     # run as user
78     def sfa_discover(self,options):
79         "discover resources into resouces_in.rspec"
80         return self.test_plc.run_in_guest(self.sfi_user(\
81                 "resources %s -o %s/%s"% (self.discover_option(),self.sfi_path(),self.adfile())))==0
82
83     # run sfi create as a regular user
84     def sfa_create_slice(self,options):
85         "run sfi create (on SM) - 1st time"
86         commands=[
87             "sfiListNodes.py -i %s/%s -o %s/%s"%(self.sfi_path(),self.adfile(),self.sfi_path(),self.nodefile()),
88             "sfiAddSliver.py -i %s/%s -n %s/%s -o %s/%s"%\
89                 (self.sfi_path(),self.adfile(),self.sfi_path(),self.nodefile(),self.sfi_path(),self.reqfile()),
90             self.sfi_user("allocate %s %s"%(self.hrn(),self.reqfile())),
91             self.sfi_user("provision %s"%(self.hrn())),
92             ]
93         for command in commands:
94             if self.test_plc.run_in_guest(command)!=0: return False
95         return True
96
97     def plc_name (self):
98         return "%s_%s"%(self.test_auth_sfa.login_base,self.slice_spec['name'])
99
100     # all local nodes in slice ?
101     def sfa_check_slice_plc (self,options):
102         "check sfa_create_slice at the plcs - all local nodes should be in slice"
103         slice=self.test_plc.apiserver.GetSlices(self.test_plc.auth_root(), self.plc_name())[0]
104         nodes=self.test_plc.apiserver.GetNodes(self.test_plc.auth_root(), {'peer_id':None})
105         result=True
106         for node in nodes: 
107             if node['node_id'] in slice['node_ids']:
108                 utils.header("local node %s found in slice %s"%(node['hostname'],slice['name']))
109             else:
110                 utils.header("ERROR - local node %s NOT FOUND in slice %s"%(node['hostname'],slice['name']))
111                 result=False
112         return result
113
114     # actually the same for now
115     def sfa_update_slice(self,options):
116         "run sfi create (on SM) on existing object"
117         return self.sfa_create_slice(options)
118
119     # run as pi
120     def sfa_delete_slice(self,options):
121         "run sfi delete"
122         self.test_plc.run_in_guest(self.sfi_pi("delete %s"%(self.hrn(),)))
123         return self.test_plc.run_in_guest(self.sfi_pi("remove -t slice %s"%(self.hrn(),)))==0
124
125     def locate_private_key(self):
126         return self.test_plc.locate_private_key_from_key_names ( [ self.slice_spec['key_name'] ] )
127
128     # check the resulting sliver
129     def ssh_slice_sfa(self,options,timeout_minutes=40,silent_minutes=0,period_seconds=15):
130         "tries to ssh-enter the SFA slice"
131         timeout  = timedelta(minutes=timeout_minutes)
132         graceout = timedelta(minutes=silent_minutes)
133         period   = timedelta(seconds=period_seconds)
134         # locate a key
135         private_key=self.locate_private_key()
136         if not private_key :
137             utils.header("WARNING: Cannot find a valid key for slice %s"%self.name())
138             return False
139         command="echo hostname ; hostname; echo id; id; echo uname -a ; uname -a"
140         
141         tasks=[]
142         slicename=self.plc_name()
143         dry_run = getattr(options,'dry_run',False)
144         for nodename in self.slice_spec['nodenames']:
145             (site_spec,node_spec) = self.test_plc.locate_node(nodename)
146             tasks.append( CompleterTaskSshSlice(self.test_plc,node_spec['node_fields']['hostname'],
147                                                 slicename,private_key,command,expected=True,dry_run=dry_run))
148         return Completer (tasks).run (timeout, graceout, period)