1 ### $Id: slices.py 15842 2009-11-22 09:56:13Z anil $
2 ### $URL: https://svn.planet-lab.org/svn/sfa/trunk/sfa/plc/slices.py $
9 from types import StringTypes
10 from sfa.util.namespace import *
11 from sfa.util.rspec import *
12 from sfa.util.specdict import *
13 from sfa.util.faults import *
14 from sfa.util.record import SfaRecord
15 from sfa.util.policy import Policy
16 from sfa.util.record import *
17 from sfa.util.sfaticket import SfaTicket
18 from sfa.util.debug import log
19 from sfa.plc.slices import Slices
20 import sfa.plc.peers as peers
21 from sfa.plc.network import *
22 from sfa.plc.api import SfaAPI
23 from sfa.plc.slices import *
25 def delete_slice(api, xrn):
26 hrn, type = urn_to_hrn(xrn)
27 slicename = hrn_to_pl_slicename(hrn)
28 slices = api.plshell.GetSlices(api.plauth, {'name': slicename})
33 # determine if this is a peer slice
34 peer = peers.get_peer(api, hrn)
36 api.plshell.UnBindObjectFromPeer(api.plauth, 'slice', slice['slice_id'], peer)
37 api.plshell.DeleteSliceFromNodes(api.plauth, slicename, slice['node_ids'])
39 api.plshell.BindObjectToPeer(api.plauth, 'slice', slice['slice_id'], peer, slice['peer_slice_id'])
42 def __get_hostnames(nodes):
45 hostnames.append(node.hostname)
48 def create_slice(api, xrn, xml, reg_objects=None):
50 Verify HRN and initialize the slice record in PLC if necessary.
53 hrn, type = urn_to_hrn(xrn)
56 peer = slices.get_peer(hrn)
57 sfa_peer = slices.get_sfa_peer(hrn)
58 registry = api.registries[api.hrn]
59 credential = api.getCredential()
60 site_id, remote_site_id = slices.verify_site(registry, credential, hrn,
61 peer, sfa_peer, reg_objects)
63 slice = slices.verify_slice(registry, credential, hrn, site_id,
64 remote_site_id, peer, sfa_peer, reg_objects)
66 network = Network(api)
68 slice = network.get_slice(api, hrn)
69 current = __get_hostnames(slice.get_nodes())
71 network.addRSpec(xml, api.config.SFA_AGGREGATE_RSPEC_SCHEMA)
72 request = __get_hostnames(network.nodesWithSlivers())
74 # remove nodes not in rspec
75 deleted_nodes = list(set(current).difference(request))
77 # add nodes from rspec
78 added_nodes = list(set(request).difference(current))
83 api.plshell.UnBindObjectFromPeer(api.plauth, 'slice', slice.id, peer)
85 api.plshell.AddSliceToNodes(api.plauth, slice.name, added_nodes)
86 api.plshell.DeleteSliceFromNodes(api.plauth, slice.name, deleted_nodes)
88 network.updateSliceTags()
91 api.plshell.BindObjectToPeer(api.plauth, 'slice', slice.id, peer,
94 # print network.toxml()
99 def get_ticket(api, xrn, rspec, origin_hrn=None, reg_objects=None):
101 slice_hrn, type = urn_to_hrn(xrn)
103 peer = slices.get_peer(slice_hrn)
104 sfa_peer = slices.get_sfa_peer(slice_hrn)
106 # get the slice record
107 registry = api.registries[api.hrn]
108 credential = api.getCredential()
109 records = registry.resolve(credential, xrn)
111 # similar to create_slice, we must verify that the required records exist
112 # at this aggregate before we can issue a ticket
113 site_id, remote_site_id = slices.verify_site(registry, credential, slice_hrn,
114 peer, sfa_peer, reg_objects)
115 slice = slices.verify_slice(registry, credential, slice_hrn, site_id,
116 remote_site_id, peer, sfa_peer, reg_objects)
118 # make sure we get a local slice record
120 for tmp_record in records:
121 if tmp_record['type'] == 'slice' and \
122 not tmp_record['peer_authority']:
123 record = SliceRecord(dict=tmp_record)
125 raise RecordNotFound(slice_hrn)
128 slivers = Slices(api).get_slivers(slice_hrn)
130 raise SliverDoesNotExist(slice_hrn)
135 'timestamp': int(time.time()),
136 'initscripts': initscripts,
141 object_gid = record.get_gid_object()
142 new_ticket = SfaTicket(subject = object_gid.get_subject())
143 new_ticket.set_gid_caller(api.auth.client_gid)
144 new_ticket.set_gid_object(object_gid)
145 new_ticket.set_issuer(key=api.key, subject=api.hrn)
146 new_ticket.set_pubkey(object_gid.get_pubkey())
147 new_ticket.set_attributes(data)
148 new_ticket.set_rspec(rspec)
149 #new_ticket.set_parent(api.auth.hierarchy.get_auth_ticket(auth_hrn))
153 return new_ticket.save_to_string(save_parents=True)
155 def start_slice(api, xrn):
156 hrn, type = urn_to_hrn(xrn)
157 slicename = hrn_to_pl_slicename(hrn)
158 slices = api.plshell.GetSlices(api.plauth, {'name': slicename}, ['slice_id'])
160 raise RecordNotFound(hrn)
162 attributes = api.plshell.GetSliceTags(api.plauth, {'slice_id': slice_id, 'name': 'enabled'}, ['slice_attribute_id'])
163 attribute_id = attributes[0]['slice_attribute_id']
164 api.plshell.UpdateSliceTag(api.plauth, attribute_id, "1" )
168 def stop_slice(api, xrn):
169 hrn, type = urn_to_hrn(xrn)
170 slicename = hrn_to_pl_slicename(hrn)
171 slices = api.plshell.GetSlices(api.plauth, {'name': slicename}, ['slice_id'])
173 raise RecordNotFound(hrn)
174 slice_id = slices[0]['slice_id']
175 attributes = api.plshell.GetSliceTags(api.plauth, {'slice_id': slice_id, 'name': 'enabled'}, ['slice_attribute_id'])
176 attribute_id = attributes[0]['slice_attribute_id']
177 api.plshell.UpdateSliceTag(api.plauth, attribute_id, "0")
180 def reset_slice(api, xrn):
181 # XX not implemented at this interface
185 # look in cache first
187 slices = api.cache.get('slices')
192 slices = api.plshell.GetSlices(api.plauth, {'peer_id': None}, ['name'])
193 slice_hrns = [slicename_to_hrn(api.hrn, slice['name']) for slice in slices]
194 slice_urns = [hrn_to_urn(slice_hrn, 'slice') for slice_hrn in slice_hrns]
198 api.cache.add('slices', slice_urns)
202 def get_rspec(api, xrn=None, origin_hrn=None):
203 # look in cache first
204 if api.cache and not xrn:
205 rspec = api.cache.get('nodes')
209 hrn, type = urn_to_hrn(xrn)
210 network = Network(api)
212 if network.get_slice(api, hrn):
215 rspec = network.toxml()
218 if api.cache and not xrn:
219 api.cache.add('nodes', rspec)
224 Returns the request context required by sfatables. At some point, this
225 mechanism should be changed to refer to "contexts", which is the
226 information that sfatables is requesting. But for now, we just return
227 the basic information needed in a dict.
229 def fetch_context(slice_xrn, user_xrn, contexts):
230 slice_hrn, type = urn_to_hrn(slice_xrn)
231 user_hrn, type = urn_to_hrn(user_xrn)
232 base_context = {'sfa':{'user':{'hrn':user_hrn}, 'slice':{'hrn':slice_hrn}}}
238 rspec = get_rspec(api, "plc.princeton.sapan", None)
239 #rspec = get_rspec(api, "plc.princeton.coblitz", None)
240 #rspec = get_rspec(api, "plc.pl.sirius", None)
243 f = open(sys.argv[1])
246 create_slice(api, "plc.princeton.sapan", xml)
248 if __name__ == "__main__":