3 # sfi -- slice-based facility interface
13 from lxml import etree
14 from StringIO import StringIO
15 from types import StringTypes, ListType
16 from optparse import OptionParser
17 from sfa.trust.certificate import Keypair, Certificate
18 from sfa.trust.credential import Credential
19 from sfa.util.sfaticket import SfaTicket
20 from sfa.util.record import *
21 from sfa.util.namespace import *
22 from sfa.util.xmlrpcprotocol import ServerException
23 import sfa.util.xmlrpcprotocol as xmlrpcprotocol
24 from sfa.util.config import Config
30 # utility methods here
32 def display_rspec(rspec, format='rspec'):
34 tree = etree.parse(StringIO(rspec))
36 result = root.xpath("./network/site/node/hostname/text()")
37 elif format in ['ip']:
38 # The IP address is not yet part of the new RSpec
39 # so this doesn't do anything yet.
40 tree = etree.parse(StringIO(rspec))
42 result = root.xpath("./network/site/node/ipv4/text()")
49 def display_list(results):
50 for result in results:
54 def display_records(recordList, dump=False):
55 ''' Print all fields in the record'''
56 for record in recordList:
57 display_record(record, dump)
59 def display_record(record, dump=False):
63 info = record.getdict()
64 print "%s (%s)" % (info['hrn'], info['type'])
68 def filter_records(type, records):
70 for record in records:
71 if (record['type'] == type) or (type == "all"):
72 filtered_records.append(record)
73 return filtered_records
77 def save_rspec_to_file(rspec, filename):
78 if not filename.endswith(".rspec"):
79 filename = filename + ".rspec"
81 f = open(filename, 'w')
86 def save_records_to_file(filename, recordList):
88 for record in recordList:
90 save_record_to_file(filename + "." + str(index), record)
92 save_record_to_file(filename, record)
95 def save_record_to_file(filename, record):
96 if record['type'] in ['user']:
97 record = UserRecord(dict=record)
98 elif record['type'] in ['slice']:
99 record = SliceRecord(dict=record)
100 elif record['type'] in ['node']:
101 record = NodeRecord(dict=record)
102 elif record['type'] in ['authority', 'ma', 'sa']:
103 record = AuthorityRecord(dict=record)
105 record = SfaRecord(dict=record)
106 str = record.save_to_string()
107 file(filename, "w").write(str)
112 def load_record_from_file(filename):
113 str = file(filename, "r").read()
114 record = SfaRecord(string=str)
129 def create_cmd_parser(self, command, additional_cmdargs=None):
130 cmdargs = {"gid": "",
136 "aggregates": "[name]",
137 "registries": "[name]",
139 "resources": "[name]",
140 "create": "name rspec",
141 "get_trusted_certs": "cred",
142 "get_ticket": "name rspec",
143 "redeem_ticket": "ticket",
149 "GetVersion": "name",
150 "ListResources": "name",
151 "CreateSliver": "name",
152 "get_geni_aggregates": "name",
153 "DeleteSliver": "name",
154 "SliverStatus": "name",
155 "RenewSliver": "name",
159 if additional_cmdargs:
160 cmdargs.update(additional_cmdargs)
162 if command not in cmdargs:
163 print "Invalid command\n"
165 for key in cmdargs.keys():
170 parser = OptionParser(usage="sfi [sfi_options] %s [options] %s" \
171 % (command, cmdargs[command]))
173 if command in ("resources"):
174 parser.add_option("-f", "--format", dest="format", type="choice",
175 help="display format ([xml]|dns|ip)", default="xml",
176 choices=("xml", "dns", "ip"))
178 if command in ("resources", "slices", "create", "delete", "start", "stop", "get_ticket"):
179 parser.add_option("-a", "--aggregate", dest="aggregate",
180 default=None, help="aggregate host")
181 parser.add_option("-p", "--port", dest="port",
182 default=AGGREGATE_PORT, help="aggregate port")
184 if command in ("start", "stop", "reset", "delete", "slices"):
185 parser.add_option("-c", "--component", dest="component", default=None,
186 help="component hrn")
188 if command in ("list", "show", "remove"):
189 parser.add_option("-t", "--type", dest="type", type="choice",
190 help="type filter ([all]|user|slice|sa|ma|node|aggregate)",
191 choices=("all", "user", "slice", "sa", "ma", "node", "aggregate"),
194 if command in ("resources", "show", "list"):
195 parser.add_option("-o", "--output", dest="file",
196 help="output XML to file", metavar="FILE", default=None)
198 if command in ("show", "list"):
199 parser.add_option("-f", "--format", dest="format", type="choice",
200 help="display format ([text]|xml)", default="text",
201 choices=("text", "xml"))
203 if command in ("delegate"):
204 parser.add_option("-u", "--user",
205 action="store_true", dest="delegate_user", default=False,
206 help="delegate user credential")
207 parser.add_option("-s", "--slice", dest="delegate_slice",
208 help="delegate slice credential", metavar="HRN", default=None)
213 def create_parser(self):
215 # Generate command line parser
216 parser = OptionParser(usage="sfi [options] command [command_options] [command_args]",
217 description="Commands: gid,list,show,remove,add,update,nodes,slices,resources,create,delete,start,stop,reset")
218 parser.add_option("-g", "--geni_am", dest="geni_am",
219 help="geni am", metavar="URL", default=None)
220 parser.add_option("-r", "--registry", dest="registry",
221 help="root registry", metavar="URL", default=None)
222 parser.add_option("-s", "--slicemgr", dest="sm",
223 help="slice manager", metavar="URL", default=None)
224 default_sfi_dir = os.path.expanduser("~/.sfi/")
225 parser.add_option("-d", "--dir", dest="sfi_dir",
226 help="config & working directory - default is " + default_sfi_dir,
227 metavar="PATH", default=default_sfi_dir)
228 parser.add_option("-u", "--user", dest="user",
229 help="user name", metavar="HRN", default=None)
230 parser.add_option("-a", "--auth", dest="auth",
231 help="authority name", metavar="HRN", default=None)
232 parser.add_option("-v", "--verbose",
233 action="store_true", dest="verbose", default=False,
235 parser.add_option("-D", "--debug",
236 action="store_true", dest="debug", default=False,
237 help="Debug (xml-rpc) protocol messages")
238 parser.add_option("-p", "--protocol",
239 dest="protocol", default="xmlrpc",
240 help="RPC protocol (xmlrpc or soap)")
241 parser.add_option("-k", "--hashrequest",
242 action="store_true", dest="hashrequest", default=False,
243 help="Create a hash of the request that will be authenticated on the server")
244 parser.disable_interspersed_args()
250 # Establish Connection to SliceMgr and Registry Servers
252 def set_servers(self):
253 config_file = self.options.sfi_dir + os.sep + "sfi_config"
255 config = Config (config_file)
257 print "Failed to read configuration file", config_file
258 print "Make sure to remove the export clauses and to add quotes"
259 if not self.options.verbose:
260 print "Re-run with -v for more details"
262 traceback.print_exc()
267 if (self.options.sm is not None):
268 sm_url = self.options.sm
269 elif hasattr(config, "SFI_SM"):
270 sm_url = config.SFI_SM
272 print "You need to set e.g. SFI_SM='http://your.slicemanager.url:12347/' in %s" % config_file
276 if (self.options.registry is not None):
277 reg_url = self.options.registry
278 elif hasattr(config, "SFI_REGISTRY"):
279 reg_url = config.SFI_REGISTRY
281 print "You need to set e.g. SFI_REGISTRY='http://your.registry.url:12345/' in %s" % config_file
285 if (self.options.geni_am is not None):
286 geni_am_url = self.options.geni_am
287 elif hasattr(config, "SFI_GENI_AM"):
288 geni_am_url = config.SFI_GENI_AM
291 if (self.options.user is not None):
292 self.user = self.options.user
293 elif hasattr(config, "SFI_USER"):
294 self.user = config.SFI_USER
296 print "You need to set e.g. SFI_USER='plc.princeton.username' in %s" % config_file
300 if (self.options.auth is not None):
301 self.authority = self.options.auth
302 elif hasattr(config, "SFI_AUTH"):
303 self.authority = config.SFI_AUTH
305 print "You need to set e.g. SFI_AUTH='plc.princeton' in %s" % config_file
311 if self.options.verbose :
312 print "Contacting Slice Manager at:", sm_url
313 print "Contacting Registry at:", reg_url
315 # Get key and certificate
316 key_file = self.get_key_file()
317 cert_file = self.get_cert_file(key_file)
318 self.key = Keypair(filename=key_file)
319 self.key_file = key_file
320 self.cert_file = cert_file
321 self.cert = Certificate(filename=cert_file)
322 # Establish connection to server(s)
323 self.registry = xmlrpcprotocol.get_server(reg_url, key_file, cert_file, self.options.debug)
324 self.slicemgr = xmlrpcprotocol.get_server(sm_url, key_file, cert_file, self.options.debug)
325 self.geni_am = xmlrpcprotocol.get_server(geni_am_url, key_file, cert_file, self.options.debug)
330 # Get various credential and spec files
332 # Establishes limiting conventions
333 # - conflates MAs and SAs
334 # - assumes last token in slice name is unique
336 # Bootstraps credentials
337 # - bootstrap user credential from self-signed certificate
338 # - bootstrap authority credential from user credential
339 # - bootstrap slice credential from user credential
343 def get_key_file(self):
344 file = os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".pkey")
345 #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".pkey")
346 if (os.path.isfile(file)):
349 print "Key file", file, "does not exist"
353 def get_cert_file(self, key_file):
355 #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".cert")
356 file = os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".cert")
357 if (os.path.isfile(file)):
360 k = Keypair(filename=key_file)
361 cert = Certificate(subject=self.user)
363 cert.set_issuer(k, self.user)
365 if self.options.verbose :
366 print "Writing self-signed certificate to", file
367 cert.save_to_file(file)
371 #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".gid")
372 file = os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".gid")
373 if (os.path.isfile(file)):
374 gid = GID(filename=file)
377 cert_str = self.cert.save_to_string(save_parents=True)
378 gid_str = self.registry.get_gid(cert_str, self.user, "user")
379 gid = GID(string=gid_str)
380 if self.options.verbose:
381 print "Writing user gid to", file
382 gid.save_to_file(file, save_parents=True)
385 def get_cached_credential(self, file):
387 Return a cached credential only if it hasn't expired.
389 if (os.path.isfile(file)):
390 credential = Credential(filename=file)
391 # make sure it isnt expired
392 if not credential.get_lifetime or \
393 datetime.datetime.today() < credential.get_lifetime():
397 def get_user_cred(self):
398 #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".cred")
399 file = os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".cred")
400 return self.get_cred(file, 'user', self.user)
402 def get_auth_cred(self):
403 if not self.authority:
404 print "no authority specified. Use -a or set SF_AUTH"
406 file = os.path.join(self.options.sfi_dir, get_leaf("authority") + ".cred")
407 return self.get_cred(file, 'authority', name)
409 def get_slice_cred(self, name):
410 file = os.path.join(self.options.sfi_dir, "slice_" + get_leaf(name) + ".cred")
411 return self.get_cred(file, 'slice', name)
413 def get_cred(self, file, type, hrn):
414 # attempt to load a cached credential
415 cred = self.get_cached_credential(file)
418 cert_string = self.cert.save_to_string(save_parents=True)
419 user_name = self.user.replace(self.authority + ".", '')
420 if user_name.count(".") > 0:
421 user_name = user_name.replace(".", '_')
422 self.user = self.authority + "." + user_name
423 cred_str = self.registry.get_self_credential(cert_string, "user", hrn)
425 # bootstrap slice credential from user credential
426 user_cred = self.get_user_cred().save_to_string(save_parents=True)
427 cred_str = self.registry.get_credential(user_cred, type, hrn)
430 print "Failed to get %s credential" % (type)
433 cred = Credential(string=cred_str)
434 cred.save_to_file(file, save_parents=True)
435 if self.options.verbose:
436 print "Writing %s credential to %s" %(type, file)
440 def delegate_cred(self, cred, hrn, type='authority'):
441 # the gid and hrn of the object we are delegating
442 user_cred = Credential(string=cred)
443 object_gid = user_cred.get_gid_object()
444 object_hrn = object_gid.get_hrn()
445 #cred.set_delegate(True)
446 #if not cred.get_delegate():
447 # raise Exception, "Error: Object credential %(object_hrn)s does not have delegate bit set" % locals()
450 records = self.registry.resolve(cred, hrn)
451 records = filter_records(type, records)
454 raise Exception, "Error: Didn't find a %(type)s record for %(hrn)s" % locals()
456 # the gid of the user who will be delegated too
457 record = SfaRecord(dict=records[0])
458 delegee_gid = record.get_gid_object()
459 delegee_hrn = delegee_gid.get_hrn()
461 # the key and hrn of the user who will be delegating
462 user_key = Keypair(filename=self.get_key_file())
463 user_hrn = user_cred.get_gid_caller().get_hrn()
465 dcred = Credential(subject=object_hrn + " delegated to " + delegee_hrn)
466 dcred.set_gid_caller(delegee_gid)
467 dcred.set_gid_object(object_gid)
468 dcred.set_privileges(user_cred.get_privileges())
469 dcred.get_privileges().delegate_all_privileges(True)
472 # Save the issuer's gid to a file
473 fname = self.options.sfi_dir + os.sep + "gid_%d" % random.randint(0, 999999999)
475 f.write(user_cred.get_gid_caller().save_to_string())
477 dcred.set_issuer_keys(self.get_key_file(), fname)
480 dcred.set_parent(user_cred)
484 return dcred.save_to_string(save_parents=True)
486 def get_rspec_file(self, rspec):
487 if (os.path.isabs(rspec)):
490 file = os.path.join(self.options.sfi_dir, rspec)
491 if (os.path.isfile(file)):
494 print "No such rspec file", rspec
497 def get_record_file(self, record):
498 if (os.path.isabs(record)):
501 file = os.path.join(self.options.sfi_dir, record)
502 if (os.path.isfile(file)):
505 print "No such registry record file", record
508 def load_publickey_string(self, fn):
510 key_string = f.read()
512 # if the filename is a private key file, then extract the public key
513 if "PRIVATE KEY" in key_string:
514 outfn = tempfile.mktemp()
515 cmd = "openssl rsa -in " + fn + " -pubout -outform PEM -out " + outfn
518 key_string = f.read()
523 def get_component_server_from_hrn(self, hrn):
524 # direct connection to the nodes component manager interface
525 user_cred = self.get_user_cred().save_to_string(save_parents=True)
526 records = self.registry.resolve(user_cred, hrn)
527 records = filter_records('node', records)
529 print "No such component:", opts.component
532 return self.get_server(record['hostname'], CM_PORT, self.key_file, \
533 self.cert_file, self.options.debug)
535 def get_server(self, host, port, keyfile, certfile, debug):
537 Return an instnace of an xmlrpc server connection
539 url = "http://%s:%s" % (host, port)
540 return xmlrpcprotocol.get_server(url, keyfile, certfile, debug)
542 def get_server_from_opts(self, opts):
544 Return instance of an xmlrpc connection to a slice manager, aggregate
545 or component server depending on the specified opts
547 server = self.slicemgr
548 # direct connection to an aggregate
550 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
551 self.cert_file, self.options.debug)
552 # direct connection to the nodes component manager interface
554 server = self.get_component_server_from_hrn(opts.component)
557 #==========================================================================
558 # Following functions implement the commands
560 # Registry-related commands
561 #==========================================================================
563 def dispatch(self, command, cmd_opts, cmd_args):
564 getattr(self, command)(cmd_opts, cmd_args)
566 def gid(self, opts, args):
568 print "GID: %s" % (gid.save_to_string(save_parents=True))
571 # list entires in named authority registry
572 def list(self, opts, args):
573 user_cred = self.get_user_cred().save_to_string(save_parents=True)
576 list = self.registry.list(user_cred, hrn)
578 raise Exception, "Not enough parameters for the 'list' command"
580 # filter on person, slice, site, node, etc.
581 # THis really should be in the self.filter_records funct def comment...
582 list = filter_records(opts.type, list)
584 print "%s (%s)" % (record['hrn'], record['type'])
587 if not file.startswith(os.sep):
588 file = os.path.join(self.options.sfi_dir, file)
589 save_records_to_file(file, list)
592 # show named registry record
593 def show(self, opts, args):
594 user_cred = self.get_user_cred().save_to_string(save_parents=True)
596 records = self.registry.resolve(user_cred, hrn)
597 records = filter_records(opts.type, records)
599 print "No record of type", opts.type
600 for record in records:
601 if record['type'] in ['user']:
602 record = UserRecord(dict=record)
603 elif record['type'] in ['slice']:
604 record = SliceRecord(dict=record)
605 elif record['type'] in ['node']:
606 record = NodeRecord(dict=record)
607 elif record['type'] in ['authority', 'ma', 'sa']:
608 record = AuthorityRecord(dict=record)
610 record = SfaRecord(dict=record)
611 if (opts.format == "text"):
614 print record.save_to_string()
618 if not file.startswith(os.sep):
619 file = os.path.join(self.options.sfi_dir, file)
620 save_records_to_file(file, records)
623 def delegate(self, opts, args):
624 user_cred = self.get_user_cred()
625 if opts.delegate_user:
626 object_cred = user_cred
627 elif opts.delegate_slice:
628 object_cred = self.get_slice_cred(opts.delegate_slice)
630 print "Must specify either --user or --slice <hrn>"
633 # the gid and hrn of the object we are delegating
634 object_gid = object_cred.get_gid_object()
635 object_hrn = object_gid.get_hrn()
637 if not object_cred.get_privileges().get_all_delegate():
638 print "Error: Object credential", object_hrn, "does not have delegate bit set"
641 records = self.registry.resolve(user_cred.save_to_string(save_parents=True), args[0])
642 records = filter_records("user", records)
645 print "Error: Didn't find a user record for", args[0]
648 # the gid of the user who will be delegated to
649 delegee_gid = GID(string=records[0]['gid'])
650 delegee_hrn = delegee_gid.get_hrn()
652 # the key and hrn of the user who will be delegating
653 user_key = Keypair(filename=self.get_key_file())
654 user_hrn = user_cred.get_gid_caller().get_hrn()
655 subject_string = "%s delegated to %s" % (object_hrn, delegee_hrn)
656 dcred = Credential(subject=subject_string)
657 dcred.set_gid_caller(delegee_gid)
658 dcred.set_gid_object(object_gid)
659 privs = object_cred.get_privileges()
660 dcred.set_privileges(object_cred.get_privileges())
661 dcred.get_privileges().delegate_all_privileges(True)
662 dcred.set_pubkey(object_gid.get_pubkey())
663 dcred.set_issuer(user_key, user_hrn)
664 dcred.set_parent(object_cred)
668 if opts.delegate_user:
669 dest_fn = os.path.join(self.options.sfi_dir, get_leaf(delegee_hrn) + "_"
670 + get_leaf(object_hrn) + ".cred")
671 elif opts.delegate_slice:
672 dest_fn = os.path_join(self.options.sfi_dir, get_leaf(delegee_hrn) + "_slice_"
673 + get_leaf(object_hrn) + ".cred")
675 dcred.save_to_file(dest_fn, save_parents=True)
677 print "delegated credential for", object_hrn, "to", delegee_hrn, "and wrote to", dest_fn
679 # removed named registry record
680 # - have to first retrieve the record to be removed
681 def remove(self, opts, args):
682 auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
687 return self.registry.remove(auth_cred, type, hrn)
689 # add named registry record
690 def add(self, opts, args):
691 auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
692 record_filepath = args[0]
693 rec_file = self.get_record_file(record_filepath)
694 record = load_record_from_file(rec_file).as_dict()
695 return self.registry.register(auth_cred, record)
697 # update named registry entry
698 def update(self, opts, args):
699 user_cred = self.get_user_cred()
700 rec_file = self.get_record_file(args[0])
701 record = load_record_from_file(rec_file)
702 if record['type'] == "user":
703 if record.get_name() == user_cred.get_gid_object().get_hrn():
704 cred = user_cred.save_to_string(save_parents=True)
706 cred = self.get_auth_cred().save_to_string(save_parents=True)
707 elif record['type'] in ["slice"]:
709 cred = self.get_slice_cred(record.get_name()).save_to_string(save_parents=True)
710 except ServerException, e:
711 # XXX smbaker -- once we have better error return codes, update this
712 # to do something better than a string compare
713 if "Permission error" in e.args[0]:
714 cred = self.get_auth_cred().save_to_string(save_parents=True)
717 elif record.get_type() in ["authority"]:
718 cred = self.get_auth_cred().save_to_string(save_parents=True)
719 elif record.get_type() == 'node':
720 cred = self.get_auth_cred().save_to_string(save_parents=True)
722 raise "unknown record type" + record.get_type()
723 record = record.as_dict()
724 return self.registry.update(cred, record)
726 def get_trusted_certs(self, opts, args):
728 return the trusted certs at this interface
730 trusted_certs = self.registry.get_trusted_certs()
731 for trusted_cert in trusted_certs:
732 cert = Certificate(string=trusted_cert)
733 print cert.get_subject()
736 def aggregates(self, opts, args):
738 return a list of details about known aggregates
740 user_cred = self.get_user_cred().save_to_string(save_parents=True)
745 result = self.registry.get_aggregates(user_cred, hrn)
749 def get_geni_aggregates(self, opts, args):
751 return a list of details about known aggregates
753 user_cred = self.get_user_cred().save_to_string(save_parents=True)
758 result = self.registry.get_geni_aggregates(user_cred, hrn)
763 def registries(self, opts, args):
765 return a list of details about known registries
767 user_cred = self.get_user_cred().save_to_string(save_parents=True)
771 result = self.registry.get_registries(user_cred, hrn)
776 # ==================================================================
777 # Slice-related commands
778 # ==================================================================
781 # list instantiated slices
782 def slices(self, opts, args):
784 list instantiated slices
786 user_cred = self.get_user_cred().save_to_string(save_parents=True)
787 server = self.slicemgr
789 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
790 self.cert_file, self.options.debug)
791 # direct connection to the nodes component manager interface
793 server = self.get_component_server_from_hrn(opts.component)
794 results = server.get_slices(user_cred)
795 display_list(results)
798 # show rspec for named slice
799 def resources(self, opts, args):
800 user_cred = self.get_user_cred().save_to_string(save_parents=True)
801 server = self.slicemgr
803 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
804 self.cert_file, self.options.debug)
806 cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
812 result = server.get_resources(cred, hrn)
815 display_rspec(result, format)
816 if (opts.file is not None):
818 if not file.startswith(os.sep):
819 file = os.path.join(self.options.sfi_dir, file)
820 save_rspec_to_file(result, file)
823 # created named slice with given rspec
824 def create(self, opts, args):
826 user_cred = self.get_user_cred()
827 slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
828 rspec_file = self.get_rspec_file(args[1])
829 rspec = open(rspec_file).read()
830 server = self.slicemgr
833 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
834 self.cert_file, self.options.debug)
836 return server.create_slice(slice_cred, slice_hrn, rspec)
838 # get a ticket for the specified slice
839 def get_ticket(self, opts, args):
840 slice_hrn, rspec_path = args[0], args[1]
841 user_cred = self.get_user_cred()
842 slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
843 rspec_file = self.get_rspec_file(rspec_path)
844 rspec = open(rspec_file).read()
845 server = self.slicemgr
847 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
848 self.cert_file, self.options.debug)
849 ticket_string = server.get_ticket(slice_cred, slice_hrn, rspec)
850 file = os.path.join(self.options.sfi_dir, get_leaf(slice_hrn) + ".ticket")
851 print "writing ticket to ", file
852 ticket = SfaTicket(string=ticket_string)
853 ticket.save_to_file(filename=file, save_parents=True)
855 def redeem_ticket(self, opts, args):
856 ticket_file = args[0]
858 # get slice hrn from the ticket
859 # use this to get the right slice credential
860 ticket = SfaTicket(filename=ticket_file)
862 slice_hrn = ticket.gidObject.get_hrn()
863 #slice_hrn = ticket.attributes['slivers'][0]['hrn']
864 user_cred = self.get_user_cred()
865 slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
867 # get a list of node hostnames from the RSpec
868 tree = etree.parse(StringIO(ticket.rspec))
869 root = tree.getroot()
870 hostnames = root.xpath("./network/site/node/hostname/text()")
872 # create an xmlrpc connection to the component manager at each of these
873 # components and gall redeem_ticket
875 for hostname in hostnames:
877 print "Calling redeem_ticket at %(hostname)s " % locals(),
878 server = self.get_server(hostname, CM_PORT, self.key_file, \
879 self.cert_file, self.options.debug)
880 server.redeem_ticket(slice_cred, ticket.save_to_string(save_parents=True))
882 except socket.gaierror:
884 print "Componet Manager not accepting requests"
886 print "Failed:", e.message
890 def delete(self, opts, args):
892 server = self.slicemgr
894 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
895 self.cert_file, self.options.debug)
896 # direct connection to the nodes component manager interface
898 server = self.get_component_server_from_hrn(opts.component)
899 slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
900 return server.delete_slice(slice_cred, slice_hrn)
903 def start(self, opts, args):
905 server = self.slicemgr
906 # direct connection to an aggregagte
908 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
909 self.cert_file, self.options.debug)
911 server = self.get_component_server_from_hrn(opts.component)
912 slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
913 return server.start_slice(slice_cred, slice_hrn)
916 def stop(self, opts, args):
918 server = self.slicemgr
919 # direct connection to an aggregate
921 server = self.get_server(opts.aggregate, opts.port, self.key_file, \
922 self.cert_file, self.options.debug)
923 # direct connection to the nodes component manager interface
925 server = self.get_component_server_from_hrn(opts.component)
926 slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
927 return server.stop_slice(slice_cred, slice_hrn)
930 def reset(self, opts, args):
932 server = self.slicemgr
933 # direct connection to the nodes component manager interface
935 server = self.get_component_server_from_hrn(opts.component)
936 slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
937 return server.reset_slice(slice_cred, slice_hrn)
940 # =====================================================================
941 # GENI AM related calls
942 # =====================================================================
944 def GetVersion(self, opts, args):
945 server = self.geni_am
946 #server = self.get_server_from_opts(opts)
947 print server.GetVersion()
949 def ListResources(self, opts, args):
950 user_cred = self.get_user_cred().save_to_string(save_parents=True)
951 server = self.geni_am
952 call_options = {'geni_compressed': True}
957 cred = self.get_slice_cred(xrn).save_to_string(save_parents=True)
960 call_options['geni_slice_urn'] = xrn
962 rspec = server.ListResources([cred], call_options)
963 rspec = zlib.decompress(rspec.decode('base64'))
966 def CreateSliver(self, opts, args):
968 slice_cred = self.get_slice_cred(slice_xrn).save_to_string(save_parents=True)
969 rspec_file = self.get_rspec_file(args[1])
970 rspec = open(rspec_file).read()
971 server = self.geni_am
972 return server.CreateSliver(slice_xrn, [slice_cred], rspec, [])
974 def DeleteSliver(self, opts, args):
976 slice_cred = self.get_slice_cred(slice_xrn).save_to_string(save_parents=True)
977 server = self.geni_am
978 return server.DeleteSliver(slice_xrn, [slice_cred])
980 def SliverStatus(self, opts, args):
982 slice_cred = self.get_slice_cred(slice_xrn).save_to_string(save_parents=True)
983 server = self.geni_am
984 print server.SliverStatus(slice_xrn, [slice_cred])
986 def RenewSliver(self, opts, args):
988 slice_cred = self.get_slice_cred(slice_xrn).save_to_string(save_parents=True)
990 server = self.geni_am
991 return server.RenewSliver(slice_xrn, [slice_cred], time)
993 def Shutdown(self, opts, args):
995 slice_cred = self.get_slice_cred(slice_xrn).save_to_string(save_parents=True)
996 server = self.geni_am
997 return server.Shutdown(slice_xrn, [slice_cred])
1000 # Main: parse arguments and dispatch to command
1003 parser = self.create_parser()
1004 (options, args) = parser.parse_args()
1005 self.options = options
1007 if options.hashrequest:
1008 self.hashrequest = True
1011 print "No command given. Use -h for help."
1015 (cmd_opts, cmd_args) = self.create_cmd_parser(command).parse_args(args[1:])
1016 if self.options.verbose :
1017 print "Registry %s, sm %s, dir %s, user %s, auth %s" % (options.registry, options.sm,
1018 options.sfi_dir, options.user,
1020 print "Command %s" % command
1021 if command in ("resources"):
1022 print "resources cmd_opts %s" % cmd_opts.format
1023 elif command in ("list", "show", "remove"):
1024 print "cmd_opts.type %s" % cmd_opts.type
1025 print "cmd_args %s" % cmd_args
1030 self.dispatch(command, cmd_opts, cmd_args)
1033 print "Command not found:", command
1038 if __name__ == "__main__":