removed another bunch of references to geni
[sfa.git] / sfa / client / sfi.py
index b3dbf35..b1a4379 100755 (executable)
 # sfi -- slice-based facility interface
 
 import sys
 # sfi -- slice-based facility interface
 
 import sys
+sys.path.append('.')
 import os, os.path
 import tempfile
 import traceback
 import os, os.path
 import tempfile
 import traceback
+import socket
 from types import StringTypes, ListType
 from optparse import OptionParser
 from types import StringTypes, ListType
 from optparse import OptionParser
-
 from sfa.trust.certificate import Keypair, Certificate
 from sfa.trust.credential import Credential
 from sfa.trust.certificate import Keypair, Certificate
 from sfa.trust.credential import Credential
-from sfa.util.geniclient import GeniClient
+from sfa.util.sfaticket import SfaTicket
 from sfa.util.record import *
 from sfa.util.record import *
+from sfa.util.namespace import *
 from sfa.util.rspec import RSpec
 from sfa.util.xmlrpcprotocol import ServerException
 import sfa.util.xmlrpcprotocol as xmlrpcprotocol
 from sfa.util.config import Config
 
 from sfa.util.rspec import RSpec
 from sfa.util.xmlrpcprotocol import ServerException
 import sfa.util.xmlrpcprotocol as xmlrpcprotocol
 from sfa.util.config import Config
 
+# utility methods here
+# display methods
+def display_rspec(rspec, format = 'rspec'):
+    if format in ['dns']:
+        spec = RSpec()
+        spec.parseString(rspec)
+        hostnames = []
+        nodespecs = spec.getDictsByTagName('NodeSpec')
+        for nodespec in nodespecs:
+            if nodespec.has_key('name') and nodespec['name']:
+                if isinstance(nodespec['name'], ListType):
+                    hostnames.extend(nodespec['name'])
+                elif isinstance(nodespec['name'], StringTypes):
+                     hostnames.append(nodespec['name'])
+        result = hostnames
+    elif format in ['ip']:
+        spec = RSpec()
+        spec.parseString(rspec)
+        ips = []
+        ifspecs = spec.getDictsByTagName('IfSpec')
+        for ifspec in ifspecs:
+            if ifspec.has_key('addr') and ifspec['addr']:
+                ips.append(ifspec['addr'])
+        result = ips
+    else:
+        result = rspec
+
+    print result
+    return
+
+def display_list(results):
+    for result in results:
+        print result
+
+
+def display_records(recordList, dump = False):
+    ''' Print all fields in the record'''
+    for record in recordList:
+        display_record(record, dump)
+
+def display_record(record, dump = False):
+    if dump:
+        record.dump()
+    else:
+        info = record.getdict()
+        print "%s (%s)" % (info['hrn'], info['type'])
+    return
+
+
+def filter_records(type, records):
+    filtered_records = []
+    for record in records:
+        if (record['type'] == type) or (type == "all"):
+            filtered_records.append(record)
+    return filtered_records
+
+
+# save methods
+def save_rspec_to_file(rspec, filename):
+    if not filename.endswith(".rspec"):
+        filename = filename + ".rspec"
+
+    f = open(filename, 'w')
+    f.write(rspec)
+    f.close()
+    return
+
+def save_records_to_file(filename, recordList):
+    index = 0
+    for record in recordList:
+        if index>0:
+            save_record_to_file(filename + "." + str(index), record)
+        else:
+            save_record_to_file(filename, record)
+        index = index + 1
+
+def save_record_to_file(filename, record):
+    if record['type'] in ['user']:
+        record = UserRecord(dict = record)
+    elif record['type'] in ['slice']:
+        record = SliceRecord(dict = record)
+    elif record['type'] in ['node']:
+        record = NodeRecord(dict = record)
+    elif record['type'] in ['authority', 'ma', 'sa']:
+        record = AuthorityRecord(dict = record)
+    else:
+        record = SfaRecord(dict = record)
+    str = record.save_to_string()
+    file(filename, "w").write(str)
+    return
+
+
+# load methods
+def load_record_from_file(filename):
+    str = file(filename, "r").read()
+    record = SfaRecord(string=str)
+    return record
+
+
+
 class Sfi:
     
     slicemgr = None
 class Sfi:
     
     slicemgr = None
@@ -25,7 +127,114 @@ class Sfi:
     user = None
     authority = None
     options = None
     user = None
     authority = None
     options = None
-    
+    hashrequest = False
+   
+    def create_cmd_parser(self,command, additional_cmdargs = None):
+        cmdargs = {"gid": "",
+                  "list": "name",
+                  "show": "name",
+                  "remove": "name",
+                  "add": "record",
+                  "update": "record",
+                  "aggregates": "[name]",
+                  "registries": "[name]",
+                  "slices": "",
+                  "resources": "[name]",
+                  "create": "name rspec",
+                  "get_trusted_certs": "cred",
+                  "get_ticket": "name rspec",
+                  "redeem_ticket": "ticket",  
+                  "delete": "name",
+                  "reset": "name",
+                  "start": "name",
+                  "stop": "name",
+                  "delegate": "name"
+                 }
+
+        if additional_cmdargs:
+            cmdargs.update(additional_cmdargs)
+
+        if command not in cmdargs:
+            print "Invalid command\n"
+            print "Commands: ",
+            for key in cmdargs.keys():
+                print key+",",
+            print ""
+            sys.exit(2)
+
+        parser = OptionParser(usage="sfi [sfi_options] %s [options] %s" \
+                                     % (command, cmdargs[command]))
+
+        if command in ("resources"):
+            parser.add_option("-f", "--format", dest="format",type="choice",
+                             help="display format ([xml]|dns|ip)",default="xml",
+                             choices=("xml","dns","ip"))
+            parser.add_option("-a", "--aggregate", dest="aggregate",
+                             default=None, help="aggregate hrn")
+
+        if command in ("create", "get_ticket"):
+            parser.add_option("-a", "--aggregate", dest="aggregate",default=None,
+                             help="aggregate hrn")
+
+        if command in ("start", "stop", "reset", "delete", "slices"):
+            parser.add_option("-c", "--component", dest="component",default=None,
+                             help="component hrn")
+            
+        if command in ("list", "show", "remove"):
+            parser.add_option("-t", "--type", dest="type",type="choice",
+                            help="type filter ([all]|user|slice|sa|ma|node|aggregate)",
+                            choices=("all","user","slice","sa","ma","node","aggregate"),
+                            default="all")
+
+        if command in ("resources", "show", "list"):
+           parser.add_option("-o", "--output", dest="file",
+                            help="output XML to file", metavar="FILE", default=None)
+        
+        if command in ("show", "list"):
+           parser.add_option("-f", "--format", dest="format", type="choice",
+                             help="display format ([text]|xml)",default="text",
+                             choices=("text","xml"))
+
+        if command in ("delegate"):
+           parser.add_option("-u", "--user",
+                            action="store_true", dest="delegate_user", default=False,
+                            help="delegate user credential")
+           parser.add_option("-s", "--slice", dest="delegate_slice",
+                            help="delegate slice credential", metavar="HRN", default=None)
+        return parser
+
+        
+    def create_parser(self):
+
+        # Generate command line parser
+        parser = OptionParser(usage="sfi [options] command [command_options] [command_args]",
+                             description="Commands: gid,list,show,remove,add,update,nodes,slices,resources,create,delete,start,stop,reset")
+        parser.add_option("-r", "--registry", dest="registry",
+                         help="root registry", metavar="URL", default=None)
+        parser.add_option("-s", "--slicemgr", dest="sm",
+                         help="slice manager", metavar="URL", default=None)
+        default_sfi_dir=os.path.expanduser("~/.sfi/")
+        parser.add_option("-d", "--dir", dest="sfi_dir",
+                         help="config & working directory - default is " + default_sfi_dir,
+                         metavar="PATH", default = default_sfi_dir)
+        parser.add_option("-u", "--user", dest="user",
+                         help="user name", metavar="HRN", default=None)
+        parser.add_option("-a", "--auth", dest="auth",
+                         help="authority name", metavar="HRN", default=None)
+        parser.add_option("-v", "--verbose",
+                         action="store_true", dest="verbose", default=False,
+                         help="verbose mode")
+        parser.add_option("-p", "--protocol",
+                         dest="protocol", default="xmlrpc",
+                         help="RPC protocol (xmlrpc or soap)")
+        parser.add_option("-k", "--hashrequest",
+                         action="store_true", dest="hashrequest", default=False,
+                         help="Create a hash of the request that will be authenticated on the server")
+        parser.disable_interspersed_args()
+
+        return parser
+        
     #
     # Establish Connection to SliceMgr and Registry Servers
     #
     #
     # Establish Connection to SliceMgr and Registry Servers
     #
@@ -94,8 +303,6 @@ class Sfi:
        self.cert_file = cert_file
        self.cert = Certificate(filename=cert_file) 
        # Establish connection to server(s)
        self.cert_file = cert_file
        self.cert = Certificate(filename=cert_file) 
        # Establish connection to server(s)
-       #self.slicemgr = GeniClient(sm_url, key_file, cert_file, self.options.protocol)
-       #self.registry = GeniClient(reg_url, key_file, cert_file, self.options.protocol)
        self.registry = xmlrpcprotocol.get_server(reg_url, key_file, cert_file)  
        self.slicemgr = xmlrpcprotocol.get_server(sm_url, key_file, cert_file)  
        return
        self.registry = xmlrpcprotocol.get_server(reg_url, key_file, cert_file)  
        self.slicemgr = xmlrpcprotocol.get_server(sm_url, key_file, cert_file)  
        return
@@ -113,12 +320,10 @@ class Sfi:
     #   - bootstrap slice credential from user credential
     #
     
     #   - bootstrap slice credential from user credential
     #
     
-    def get_leaf(self,name):
-       parts = name.split(".")
-       return parts[-1]
     
     def get_key_file(self):
     
     def get_key_file(self):
-       file = os.path.join(self.options.sfi_dir, self.get_leaf(self.user) + ".pkey")
+       file=os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".pkey")
+       #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".pkey")
        if (os.path.isfile(file)):
           return file
        else:
        if (os.path.isfile(file)):
           return file
        else:
@@ -128,7 +333,8 @@ class Sfi:
     
     def get_cert_file(self,key_file):
     
     
     def get_cert_file(self,key_file):
     
-       file = os.path.join(self.options.sfi_dir, self.get_leaf(self.user) + ".cert")
+       #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".cert")
+       file=os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".cert")
        if (os.path.isfile(file)):
           return file
        else:
        if (os.path.isfile(file)):
           return file
        else:
@@ -143,14 +349,14 @@ class Sfi:
           return file
    
     def get_gid(self):
           return file
    
     def get_gid(self):
-        file = os.path.join(self.options.sfi_dir, self.get_leaf(self.user) + ".gid")
+        #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".gid")
+        file=os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".gid")
         if (os.path.isfile(file)):
             gid = GID(filename=file)
             return gid
         else:
             cert_str = self.cert.save_to_string(save_parents=True)
         if (os.path.isfile(file)):
             gid = GID(filename=file)
             return gid
         else:
             cert_str = self.cert.save_to_string(save_parents=True)
-            request_hash = self.key.compute_hash([cert_str, self.user, "user"])
-            gid_str = self.registry.get_gid(cert_str, self.user, "user", request_hash)
+            gid_str = self.registry.get_gid(cert_str, self.user, "user")
             gid = GID(string=gid_str)
             if self.options.verbose:
                 print "Writing user gid to", file
             gid = GID(string=gid_str)
             if self.options.verbose:
                 print "Writing user gid to", file
@@ -158,7 +364,8 @@ class Sfi:
             return gid       
  
     def get_user_cred(self):
             return gid       
  
     def get_user_cred(self):
-        file = os.path.join(self.options.sfi_dir, self.get_leaf(self.user) + ".cred")
+        #file = os.path.join(self.options.sfi_dir, get_leaf(self.user) + ".cred")
+        file=os.path.join(self.options.sfi_dir, self.user.replace(self.authority + '.', '') + ".cred")
         if (os.path.isfile(file)):
             user_cred = Credential(filename=file)
             return user_cred
         if (os.path.isfile(file)):
             user_cred = Credential(filename=file)
             return user_cred
@@ -166,6 +373,11 @@ class Sfi:
             # bootstrap user credential
             cert_string = self.cert.save_to_string(save_parents=True)
             request_hash = self.key.compute_hash([cert_string, "user", self.user])
             # bootstrap user credential
             cert_string = self.cert.save_to_string(save_parents=True)
             request_hash = self.key.compute_hash([cert_string, "user", self.user])
+            user_name=self.user.replace(self.authority+".", '')
+            if user_name.count(".") > 0:
+                user_name = user_name.replace(".", '_')
+                self.user=self.authority + "." + user_name
+
             user_cred = self.registry.get_self_credential(cert_string, "user", self.user, request_hash)
             if user_cred:
                cred = Credential(string=user_cred)
             user_cred = self.registry.get_self_credential(cert_string, "user", self.user, request_hash)
             if user_cred:
                cred = Credential(string=user_cred)
@@ -176,88 +388,87 @@ class Sfi:
             else:
                print "Failed to get user credential"
                sys.exit(-1)
             else:
                print "Failed to get user credential"
                sys.exit(-1)
-    
+  
     def get_auth_cred(self):
     def get_auth_cred(self):
+        if not self.authority:
+            print "no authority specified. Use -a or set SF_AUTH"
+            sys.exit(-1)
     
     
-       if not self.authority:
-          print "no authority specified. Use -a or set SF_AUTH"
-          sys.exit(-1)
-    
-       file = os.path.join(self.options.sfi_dir, self.get_leaf("authority") +".cred")
-       if (os.path.isfile(file)):
-          auth_cred = Credential(filename=file)
-          return auth_cred
-       else:
-          # bootstrap authority credential from user credential
-          user_cred = self.get_user_cred().save_to_string(save_parents=True)
-          request_hash = self.key.compute_hash([user_cred, "authority", self.authority])
-          auth_cred = self.registry.get_credential(user_cred, "authority", self.authority, request_hash)
-          if auth_cred:
-             cred = Credential(string=auth_cred)
-             cred.save_to_file(file, save_parents=True)
-             if self.options.verbose:
-                print "Writing authority credential to", file
-             return cred
-          else:
-             print "Failed to get authority credential"
-             sys.exit(-1)
+        file = os.path.join(self.options.sfi_dir, get_leaf("authority") +".cred")
+        if (os.path.isfile(file)):
+            auth_cred = Credential(filename=file)
+            return auth_cred
+        else:
+            # bootstrap authority credential from user credential
+            user_cred = self.get_user_cred().save_to_string(save_parents=True)
+            auth_cred = self.registry.get_credential(user_cred, "authority", self.authority)
+            if auth_cred:
+                cred = Credential(string=auth_cred)
+                cred.save_to_file(file, save_parents=True)
+                if self.options.verbose:
+                    print "Writing authority credential to", file
+                return cred
+            else:
+                print "Failed to get authority credential"
+                sys.exit(-1)
     
     def get_slice_cred(self,name):
     
     def get_slice_cred(self,name):
-       file = os.path.join(self.options.sfi_dir, "slice_" + self.get_leaf(name) + ".cred")
-       if (os.path.isfile(file)):
-          slice_cred = Credential(filename=file)
-          return slice_cred
-       else:
-          # bootstrap slice credential from user credential
-          user_cred = self.get_user_cred().save_to_string(save_parents=True)
-          arg_list = [user_cred, "slice", name]
-          request_hash = self.key.compute_hash(arg_list)  
-          slice_cred_str = self.registry.get_credential(user_cred, "slice", name, request_hash)
-          if slice_cred:
-             slice_cred = Credential(string=slice_cred_str)
-             slice_cred.save_to_file(file, save_parents=True)
-             if self.options.verbose:
-                print "Writing slice credential to", file
-             return slice_cred
-          else:
-             print "Failed to get slice credential"
-             sys.exit(-1)
+        file = os.path.join(self.options.sfi_dir, "slice_" + get_leaf(name) + ".cred")
+        if (os.path.isfile(file)):
+            slice_cred = Credential(filename=file)
+            return slice_cred
+        else:
+            # bootstrap slice credential from user credential
+            user_cred = self.get_user_cred().save_to_string(save_parents=True)
+            arg_list = [user_cred, "slice", name]
+            slice_cred_str = self.registry.get_credential(user_cred, "slice", name)
+            if slice_cred_str:
+                slice_cred = Credential(string=slice_cred_str)
+                slice_cred.save_to_file(file, save_parents=True)
+                if self.options.verbose:
+                    print "Writing slice credential to", file
+                return slice_cred
+            else:
+                print "Failed to get slice credential"
+                sys.exit(-1)
     
     def delegate_cred(self,cred, hrn, type = 'authority'):
         # the gid and hrn of the object we are delegating
     
     def delegate_cred(self,cred, hrn, type = 'authority'):
         # the gid and hrn of the object we are delegating
-        object_gid = cred.get_gid_object()
+        user_cred = Credential(string=cred)
+        object_gid = user_cred.get_gid_object()
         object_hrn = object_gid.get_hrn()
         object_hrn = object_gid.get_hrn()
-        cred.set_delegate(True)
-        if not cred.get_delegate():
-            raise Exception, "Error: Object credential %(object_hrn)s does not have delegate bit set" % locals()
+        #cred.set_delegate(True)
+        #if not cred.get_delegate():
+        #    raise Exception, "Error: Object credential %(object_hrn)s does not have delegate bit set" % locals()
            
     
         records = self.registry.resolve(cred, hrn)
            
     
         records = self.registry.resolve(cred, hrn)
-        records = self.filter_records(type, records)
+        records = filter_records(type, records)
         
         if not records:
             raise Exception, "Error: Didn't find a %(type)s record for %(hrn)s" % locals()
     
         # the gid of the user who will be delegated too
         
         if not records:
             raise Exception, "Error: Didn't find a %(type)s record for %(hrn)s" % locals()
     
         # the gid of the user who will be delegated too
-        delegee_gid = records[0].get_gid_object()
+        record = SfaRecord(dict=records[0])
+        delegee_gid = record.get_gid_object()
         delegee_hrn = delegee_gid.get_hrn()
         
         # the key and hrn of the user who will be delegating
         user_key = Keypair(filename = self.get_key_file())
         delegee_hrn = delegee_gid.get_hrn()
         
         # the key and hrn of the user who will be delegating
         user_key = Keypair(filename = self.get_key_file())
-        user_hrn = cred.get_gid_caller().get_hrn()
+        user_hrn = user_cred.get_gid_caller().get_hrn()
     
         dcred = Credential(subject=object_hrn + " delegated to " + delegee_hrn)
         dcred.set_gid_caller(delegee_gid)
         dcred.set_gid_object(object_gid)
     
         dcred = Credential(subject=object_hrn + " delegated to " + delegee_hrn)
         dcred.set_gid_caller(delegee_gid)
         dcred.set_gid_object(object_gid)
-        dcred.set_privileges(cred.get_privileges())
+        dcred.set_privileges(user_cred.get_privileges())
         dcred.set_delegate(True)
         dcred.set_pubkey(object_gid.get_pubkey())
         dcred.set_issuer(user_key, user_hrn)
         dcred.set_delegate(True)
         dcred.set_pubkey(object_gid.get_pubkey())
         dcred.set_issuer(user_key, user_hrn)
-        dcred.set_parent(cred)
+        dcred.set_parent(user_cred)
         dcred.encode()
         dcred.sign()
     
         dcred.encode()
         dcred.sign()
     
-        return dcred
+        return dcred.save_to_string(save_parents=True)
     
     def get_rspec_file(self,rspec):
        if (os.path.isabs(rspec)):
     
     def get_rspec_file(self,rspec):
        if (os.path.isabs(rspec)):
@@ -295,164 +506,84 @@ class Sfi:
            os.remove(outfn)
     
        return key_string
            os.remove(outfn)
     
        return key_string
-    #
-    # Generate sub-command parser
-    #
-    def create_cmd_parser(self,command, additional_cmdargs = None):
-       cmdargs = {"gid": "",
-                  "list": "name",
-                  "show": "name",
-                  "remove": "name",
-                  "add": "record",
-                  "update": "record",
-                  "aggregates": "[name]",
-                  "registries": "[name]",   
-                  "slices": "",
-                  "resources": "[name]",
-                  "create": "name rspec",
-                  "delete": "name",
-                  "reset": "name",
-                  "start": "name",
-                  "stop": "name",
-                  "delegate": "name"
-                 }
-    
-       if additional_cmdargs:
-          cmdargs.update(additional_cmdargs)
-    
-       if command not in cmdargs:
-          print "Invalid command\n"
-          print "Commands: ",
-          for key in cmdargs.keys():
-              print key+",",
-          print ""
-          sys.exit(2)
-    
-       parser = OptionParser(usage="sfi [sfi_options] %s [options] %s" \
-          % (command, cmdargs[command]))
-
-       if command in ("resources"):
-           parser.add_option("-f", "--format", dest="format",type="choice",
-                             help="display format ([xml]|dns|ip)",default="xml",
-                             choices=("xml","dns","ip"))
-           parser.add_option("-a", "--aggregate", dest="aggregate",
-                             default=None, help="aggregate hrn")  
-    
-       if command in ("create"):
-           parser.add_option("-a", "--aggregate", dest="aggregate",default=None,
-                             help="aggregate hrn") 
-       if command in ("list", "show", "remove"):
-          parser.add_option("-t", "--type", dest="type",type="choice",
-                            help="type filter ([all]|user|slice|sa|ma|node|aggregate)",
-                            choices=("all","user","slice","sa","ma","node","aggregate"),
-                            default="all")
-
-       if command in ("resources", "show", "list"):
-          parser.add_option("-o", "--output", dest="file",
-                            help="output XML to file", metavar="FILE", default=None)
-
-       if command in ("show", "list"):
-           parser.add_option("-f", "--format", dest="format", type="choice", 
-                             help="display format ([text]|xml)",default="text", 
-                             choices=("text","xml")) 
 
 
-       if command in ("delegate"):
-          parser.add_option("-u", "--user",
-                            action="store_true", dest="delegate_user", default=False,
-                            help="delegate user credential")
-          parser.add_option("-s", "--slice", dest="delegate_slice",
-                            help="delegate slice credential", metavar="HRN", default=None)
-       return parser
-    
-    def create_parser(self):
-
-       # Generate command line parser
-       parser = OptionParser(usage="sfi [options] command [command_options] [command_args]",
-                             description="Commands: gid,list,show,remove,add,update,nodes,slices,resources,create,delete,start,stop,reset")
-       parser.add_option("-r", "--registry", dest="registry",
-                         help="root registry", metavar="URL", default=None)
-       parser.add_option("-s", "--slicemgr", dest="sm",
-                         help="slice manager", metavar="URL", default=None)
-       default_sfi_dir=os.path.expanduser("~/.sfi/")
-       parser.add_option("-d", "--dir", dest="sfi_dir",
-                         help="config & working directory - default is " + default_sfi_dir,
-                         metavar="PATH", default = default_sfi_dir)
-       parser.add_option("-u", "--user", dest="user",
-                         help="user name", metavar="HRN", default=None)
-       parser.add_option("-a", "--auth", dest="auth",
-                         help="authority name", metavar="HRN", default=None)
-       parser.add_option("-v", "--verbose",
-                         action="store_true", dest="verbose", default=False,
-                         help="verbose mode")
-       parser.add_option("-p", "--protocol",
-                         dest="protocol", default="xmlrpc",
-                         help="RPC protocol (xmlrpc or soap)")
-       parser.disable_interspersed_args()
-    
-       return parser
-    
-    def dispatch(self,command, cmd_opts, cmd_args):
-       getattr(self,command)(cmd_opts, cmd_args)
+    def get_component_server_from_hrn(self, hrn):
+        # direct connection to the nodes component manager interface
+        user_cred = self.get_user_cred().save_to_string(save_parents=True)
+        records = self.registry.resolve(user_cred, hrn)
+        records = filter_records('node', records)
+        if not records:
+            print "No such component:", opts.component
+        record = records[0]
+        cm_port = "12346"
+        url = "https://%s:%s" % (record['hostname'], cm_port)
+        return xmlrpcprotocol.get_server(url, self.key_file, self.cert_file)
     
     #
     # Following functions implement the commands
     #
     # Registry-related commands
     #
     
     #
     # Following functions implement the commands
     #
     # Registry-related commands
     #
-   
+  
+    def dispatch(self,command, cmd_opts, cmd_args):
+        getattr(self,command)(cmd_opts, cmd_args)
     def gid(self, opts, args):
     def gid(self, opts, args):
-       gid = self.get_gid()
-       print "GID: %s" % (gid.save_to_string(save_parents=True))
-       return   
+        gid = self.get_gid()
+        print "GID: %s" % (gid.save_to_string(save_parents=True))
+        return   
  
     # list entires in named authority registry
     def list(self,opts, args):
  
     # list entires in named authority registry
     def list(self,opts, args):
-       user_cred = self.get_user_cred().save_to_string(save_parents=True)
-       hrn = args[0]
-       request_hash = self.key.compute_hash([user_cred, hrn])    
-       try:
-          list = self.registry.list(user_cred, hrn, request_hash)
-       except IndexError:
-          raise Exception, "Not enough parameters for the 'list' command"
+        user_cred = self.get_user_cred().save_to_string(save_parents=True)
+        hrn = args[0]
+        try:
+            list = self.registry.list(user_cred, hrn)
+        except IndexError:
+            raise Exception, "Not enough parameters for the 'list' command"
           
           
-       # filter on person, slice, site, node, etc.  
-       # THis really should be in the self.filter_records funct def comment...
-       list = self.filter_records(opts.type, list)
-       for record in list:
-           print "%s (%s)" % (record['hrn'], record['type'])     
-       if opts.file:
-           self.save_records_to_file(opts.file, list)
-       return
+        # filter on person, slice, site, node, etc.  
+        # THis really should be in the self.filter_records funct def comment...
+        list = filter_records(opts.type, list)
+        for record in list:
+            print "%s (%s)" % (record['hrn'], record['type'])     
+        if opts.file:
+            file = opts.file
+            if not file.startswith(os.sep):
+                file = os.path.join(self.options.sfi_dir, file)
+            save_records_to_file(file, list)
+        return
     
     # show named registry record
     def show(self,opts, args):
     
     # show named registry record
     def show(self,opts, args):
-       user_cred = self.get_user_cred().save_to_string(save_parents=True)
-       hrn = args[0]
-       request_hash = self.key.compute_hash([user_cred, hrn])    
-       records = self.registry.resolve(user_cred, hrn, request_hash)
-       records = self.filter_records(opts.type, records)
-       if not records:
-          print "No record of type", opts.type
-       for record in records:
-           if record['type'] in ['user']:
-               record = UserRecord(dict = record)
-           elif record['type'] in ['slice']:
-               record = SliceRecord(dict = record)
-           elif record['type'] in ['node']:
-               record = NodeRecord(dict = record)
-           elif record['type'] in ['authority', 'ma', 'sa']:
-               record = AuthorityRecord(dict = record)
-           else:
-               record = GeniRecord(dict = record)
-           if (opts.format=="text"): 
-               record.dump()  
-           else: 
-               print record.save_to_string() 
+        user_cred = self.get_user_cred().save_to_string(save_parents=True)
+        hrn = args[0]
+        records = self.registry.resolve(user_cred, hrn)
+        records = filter_records(opts.type, records)
+        if not records:
+            print "No record of type", opts.type
+        for record in records:
+            if record['type'] in ['user']:
+                record = UserRecord(dict = record)
+            elif record['type'] in ['slice']:
+                record = SliceRecord(dict = record)
+            elif record['type'] in ['node']:
+                record = NodeRecord(dict = record)
+            elif record['type'] in ['authority', 'ma', 'sa']:
+                record = AuthorityRecord(dict = record)
+            else:
+                record = SfaRecord(dict = record)
+            if (opts.format=="text"): 
+                record.dump()  
+            else:
+                print record.save_to_string() 
        
        
-       if opts.file:
-           self.save_records_to_file(opts.file, records)
-       return
+        if opts.file:
+            file = opts.file
+            if not file.startswith(os.sep):
+                file = os.path.join(self.options.sfi_dir, file)
+            save_records_to_file(file, records)
+        return
     
     def delegate(self,opts, args):
        user_cred = self.get_user_cred()
     
     def delegate(self,opts, args):
        user_cred = self.get_user_cred()
@@ -473,7 +604,7 @@ class Sfi:
            return
     
        records = self.registry.resolve(user_cred, args[0])
            return
     
        records = self.registry.resolve(user_cred, args[0])
-       records = self.filter_records("user", records)
+       records = filter_records("user", records)
     
        if not records:
            print "Error: Didn't find a user record for", args[0]
     
        if not records:
            print "Error: Didn't find a user record for", args[0]
@@ -499,11 +630,11 @@ class Sfi:
        dcred.sign()
     
        if opts.delegate_user:
        dcred.sign()
     
        if opts.delegate_user:
-           dest_fn = os.path.join(self.options.sfi_dir, self.get_leaf(delegee_hrn) + "_" 
-                                  + self.get_leaf(object_hrn) + ".cred")
+           dest_fn = os.path.join(self.options.sfi_dir, get_leaf(delegee_hrn) + "_" 
+                                  + get_leaf(object_hrn) + ".cred")
        elif opts.delegate_slice:
        elif opts.delegate_slice:
-           dest_fn = os.path_join(self.options.sfi_dir, self.get_leaf(delegee_hrn) + "_slice_" 
-                                  + self.get_leaf(object_hrn) + ".cred")
+           dest_fn = os.path_join(self.options.sfi_dir, get_leaf(delegee_hrn) + "_slice_" 
+                                  + get_leaf(object_hrn) + ".cred")
     
        dcred.save_to_file(dest_fn, save_parents = True)
     
     
        dcred.save_to_file(dest_fn, save_parents = True)
     
@@ -512,78 +643,84 @@ class Sfi:
     # removed named registry record
     #   - have to first retrieve the record to be removed
     def remove(self,opts, args):
     # removed named registry record
     #   - have to first retrieve the record to be removed
     def remove(self,opts, args):
-       auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
-       hrn = args[0]
-       type = opts.type 
-       if type in ['all']:
-           type = '*'
-       arg_list = [auth_cred, type, hrn]
-       request_hash = self.key.compute_hash(arg_list)                   
-       return self.registry.remove(auth_cred, type, hrn, request_hash)
+        auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
+        hrn = args[0]
+        type = opts.type 
+        if type in ['all']:
+            type = '*'
+        return self.registry.remove(auth_cred, type, hrn)
     
     # add named registry record
     def add(self,opts, args):
     
     # add named registry record
     def add(self,opts, args):
-       auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
-       record_filepath = args[0]
-       rec_file = self.get_record_file(record_filepath)
-       record = self.load_record_from_file(rec_file).as_dict()
-       arg_list = [auth_cred]
-       request_hash = self.key.compute_hash(arg_list)
-       return self.registry.register(auth_cred, record, request_hash)
+        auth_cred = self.get_auth_cred().save_to_string(save_parents=True)
+        record_filepath = args[0]
+        rec_file = self.get_record_file(record_filepath)
+        record = load_record_from_file(rec_file).as_dict()
+        return self.registry.register(auth_cred, record)
     
     # update named registry entry
     def update(self,opts, args):
     
     # update named registry entry
     def update(self,opts, args):
-       user_cred = self.get_user_cred()
-       rec_file = self.get_record_file(args[0])
-       record = self.load_record_from_file(rec_file)
-       if record['type'] == "user":
-           if record.get_name() == user_cred.get_gid_object().get_hrn():
-              cred = user_cred.save_to_string(save_parents=True)
-           else:
-              cred = self.get_auth_cred().save_to_string(save_parents=True)
-       elif record['type'] in ["slice"]:
-           try:
-               cred = self.get_slice_cred(record.get_name()).save_to_string(save_parents=True)
-           except ServerException, e:
+        user_cred = self.get_user_cred()
+        rec_file = self.get_record_file(args[0])
+        record = load_record_from_file(rec_file)
+        if record['type'] == "user":
+            if record.get_name() == user_cred.get_gid_object().get_hrn():
+                cred = user_cred.save_to_string(save_parents=True)
+            else:
+                cred = self.get_auth_cred().save_to_string(save_parents=True)
+        elif record['type'] in ["slice"]:
+            try:
+                cred = self.get_slice_cred(record.get_name()).save_to_string(save_parents=True)
+            except ServerException, e:
                # XXX smbaker -- once we have better error return codes, update this
                # to do something better than a string compare
                if "Permission error" in e.args[0]:
                    cred = self.get_auth_cred().save_to_string(save_parents=True)
                else:
                    raise
                # XXX smbaker -- once we have better error return codes, update this
                # to do something better than a string compare
                if "Permission error" in e.args[0]:
                    cred = self.get_auth_cred().save_to_string(save_parents=True)
                else:
                    raise
-       elif record.get_type() in ["authority"]:
-           cred = self.get_auth_cred().save_to_string(save_parents=True)
-       elif record.get_type() == 'node':
-           cred = self.get_auth_cred().save_to_string(save_parents=True)
-       else:
-           raise "unknown record type" + record.get_type()
-       record = record.as_dict()
-       arg_list = [cred]  
-       request_hash = self.key.compute_hash(arg_list)
-       return self.registry.update(cred, record, request_hash)
-   
-    
+        elif record.get_type() in ["authority"]:
+            cred = self.get_auth_cred().save_to_string(save_parents=True)
+        elif record.get_type() == 'node':
+            cred = self.get_auth_cred().save_to_string(save_parents=True)
+        else:
+            raise "unknown record type" + record.get_type()
+        record = record.as_dict()
+        return self.registry.update(cred, record)
+  
+    def get_trusted_certs(self, opts, args):
+        """
+        return the trusted certs at this interface 
+        """ 
+        trusted_certs = self.registry.get_trusted_certs()
+        for trusted_cert in trusted_certs:
+            cert = Certificate(string=trusted_cert)
+            print cert.get_subject()
+        return 
+
     def aggregates(self, opts, args):
     def aggregates(self, opts, args):
+        """
+        return a list of details about known aggregates
+        """
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
         hrn = None
         if args: 
             hrn = args[0]
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
         hrn = None
         if args: 
             hrn = args[0]
-        arg_list = [user_cred, hrn]  
-        request_hash = self.key.compute_hash(arg_list)
-        result = self.registry.get_aggregates(user_cred, hrn, request_hash)
-        self.display_list(result)
+        result = self.registry.get_aggregates(user_cred, hrn)
+        display_list(result)
         return 
 
     def registries(self, opts, args):
         return 
 
     def registries(self, opts, args):
+        """
+        return a list of details about known registries
+        """
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
         hrn = None
         if args:
             hrn = args[0]
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
         hrn = None
         if args:
             hrn = args[0]
-        arg_list = [user_cred, hrn]  
-        request_hash = self.key.compute_hash(arg_list)
-        result = self.registry.get_registries(user_cred, hrn, request_hash)
-        self.display_list(result)
+        result = self.registry.get_registries(user_cred, hrn)
+        display_list(result)
         return
         return
+
  
     #
     # Slice-related commands
  
     #
     # Slice-related commands
@@ -594,10 +731,12 @@ class Sfi:
     # list instantiated slices
     def slices(self,opts, args):
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
     # list instantiated slices
     def slices(self,opts, args):
         user_cred = self.get_user_cred().save_to_string(save_parents=True)
-        arg_list = [user_cred]
-        request_hash = self.key.compute_hash(arg_list)
-        results = self.slicemgr.get_slices(user_cred, request_hash)
-        self.display_list(results)
+        server = self.slicemgr
+        # direct connection to the nodes component manager interface
+        if opts.component:
+            server = self.get_component_server_from_hrn(opts.component)
+        results = server.get_slices(user_cred)
+        display_list(results)
         return
     
     # show rspec for named slice
         return
     
     # show rspec for named slice
@@ -606,9 +745,7 @@ class Sfi:
         server = self.slicemgr
         if opts.aggregate:
             agg_hrn = opts.aggregate
         server = self.slicemgr
         if opts.aggregate:
             agg_hrn = opts.aggregate
-            arg_list = [user_cred, arg_hrn]
-            request_hash = self.key.compute_hash(arg_list)
-            aggregates = self.registry.get_aggregates(user_cred, agg_hrn, request_hash)
+            aggregates = self.registry.get_aggregates(user_cred, agg_hrn)
             if not aggregates:
                 raise Exception, "No such aggregate %s" % agg_hrn
             aggregate = aggregates[0]
             if not aggregates:
                 raise Exception, "No such aggregate %s" % agg_hrn
             aggregate = aggregates[0]
@@ -621,205 +758,172 @@ class Sfi:
             cred = user_cred
             hrn = None
 
             cred = user_cred
             hrn = None
 
-        arg_list = [cred, hrn]
-        request_hash = self.key.compute_hash(arg_list)  
-        result = server.get_resources(cred, hrn, request_hash)
+        result = server.get_resources(cred, hrn)
         format = opts.format
        
         format = opts.format
        
-        self.display_rspec(result, format)
+        display_rspec(result, format)
         if (opts.file is not None):
         if (opts.file is not None):
-            self.save_rspec_to_file(result, opts.file)
+            file = opts.file
+            if not file.startswith(os.sep):
+                file = os.path.join(self.options.sfi_dir, file)
+            save_rspec_to_file(result, file)
         return
     
     # created named slice with given rspec
     def create(self,opts, args):
         return
     
     # created named slice with given rspec
     def create(self,opts, args):
-       slice_hrn = args[0]
-       user_cred = self.get_user_cred()
-       slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
-       rspec_file = self.get_rspec_file(args[1])
-       rspec=open(rspec_file).read()
-       server = self.slicemgr
-       if opts.aggregate:
-           aggregates = self.registry.get_aggregates(user_cred, opts.aggregate)
-           if not aggregates:
-               raise Exception, "No such aggregate %s" % opts.aggregate
-           aggregate = aggregates[0]
-           url = "http://%s:%s" % (aggregate['addr'], aggregate['port'])
-           server = GeniClient(url, self.key_file, self.cert_file, self.options.protocol)
-       arg_list = [slice_cred, slice_hrn, rspec]
-       request_hash = self.key.compute_hash(arg_list) 
-       return server.create_slice(slice_cred, slice_hrn, rspec, request_hash)
-    
+        slice_hrn = args[0]
+        user_cred = self.get_user_cred()
+        slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
+        rspec_file = self.get_rspec_file(args[1])
+        rspec=open(rspec_file).read()
+        server = self.slicemgr
+        if opts.aggregate:
+            aggregates = self.registry.get_aggregates(user_cred, opts.aggregate)
+            if not aggregates:
+                raise Exception, "No such aggregate %s" % opts.aggregate
+            aggregate = aggregates[0]
+            url = "http://%s:%s" % (aggregate['addr'], aggregate['port'])
+            server = xmlrpcprotocol.get_server(url, self.key_file, self.cert_file, self.options.protocol)
+        return server.create_slice(slice_cred, slice_hrn, rspec)
+
+    # get a ticket for the specified slice
+    def get_ticket(self, opts, args):
+        slice_hrn, rspec_path = args[0], args[1]
+        user_cred = self.get_user_cred()
+        slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
+        rspec_file = self.get_rspec_file(rspec_path) 
+        rspec=open(rspec_file).read()
+        server = self.slicemgr
+        if opts.aggregate:
+            aggregates = self.registry.get_aggregates(user_cred, opts.aggregate)
+            if not aggregates:
+                raise Exception, "No such aggregate %s" % opts.aggregate
+            aggregate = aggregates[0]
+            url = "http://%s:%s" % (aggregate['addr'], aggregate['port'])
+            server = xmlrpcprotocol.get_server(url, self.key_file, self.cert_file, self.options.protocol)
+        ticket_string = server.get_ticket(slice_cred, slice_hrn, rspec)
+        file = os.path.join(self.options.sfi_dir, get_leaf(slice_hrn) + ".ticket")
+        print "writing ticket to ", file        
+        ticket = SfaTicket(string=ticket_string)
+        ticket.save_to_file(filename=file, save_parents=True)
+
+    def redeem_ticket(self, opts, args):
+        ticket_file = args[0]
+        
+        # get slice hrn from the ticket
+        # use this to get the right slice credential 
+        ticket = SfaTicket(filename=ticket_file)
+        ticket.decode()
+        slice_hrn = ticket.attributes['slivers'][0]['hrn']
+        user_cred = self.get_user_cred()
+        slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
+        
+        # get a list node hostnames from the nodespecs in the rspec 
+        rspec = RSpec()
+        rspec.parseString(ticket.rspec)
+        nodespecs = rspec.getDictsByTagName('NodeSpec')
+        hostnames = [nodespec['name'] for nodespec in nodespecs]
+        
+        # create an xmlrpc connection to the component manager at each of these
+        # components and gall redeem_ticket
+        connections = {}
+        for hostname in hostnames:
+            try:
+                cm_port = "12346" 
+                url = "https://%(hostname)s:%(cm_port)s" % locals() 
+                print "Calling get_ticket at %(url)s " % locals(),  
+                cm = xmlrpcprotocol.get_server(url, self.key_file, self.cert_file)
+                cm.redeem_ticket(slice_cred, ticket.save_to_string(save_parents=True))
+                print "Success"
+            except socket.gaierror:
+                print "Failed:",
+                print "Componet Manager not accepting requests" 
+            except Exception, e:
+                print "Failed:", e.message
+             
+        return
     # delete named slice
     def delete(self,opts, args):
         slice_hrn = args[0]
     # delete named slice
     def delete(self,opts, args):
         slice_hrn = args[0]
+        server = self.slicemgr
+        # direct connection to the nodes component manager interface
+        if opts.component:
+            server = self.get_component_server_from_hrn(opts.component)
         slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
         slice_cred = self.get_slice_cred(slice_hrn).save_to_string(save_parents=True)
-        arg_list = [slice_cred, slice_hrn]
-        request_hash = self.key.compute_hash(arg_list) 
-        return self.slicemgr.delete_slice(slice_cred, slice_hrn, request_hash)
+        return server.delete_slice(slice_cred, slice_hrn)
     
     # start named slice
     def start(self,opts, args):
         slice_hrn = args[0]
     
     # start named slice
     def start(self,opts, args):
         slice_hrn = args[0]
-        slice_cred = self.get_slice_cred(args[0])
-        arg_list = [slice_cred, slice_hrn]
-        request_hash = self.key.compute_hash(arg_list)
-        return self.slicemgr.start_slice(slice_cred, slice_hrn, request_hash)
+        server = self.slicemgr
+        # direct connection to the nodes component manager interface
+        if opts.component:
+            server = self.get_component_server_from_hrn(opts.component)
+        slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
+        return server.start_slice(slice_cred, slice_hrn)
     
     # stop named slice
     def stop(self,opts, args):
         slice_hrn = args[0]
     
     # stop named slice
     def stop(self,opts, args):
         slice_hrn = args[0]
+        server = self.slicemgr
+        # direct connection to the nodes component manager interface
+        if opts.component:
+            server = self.get_component_server_from_hrn(opts.component)
+
         slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
         slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
-        arg_list = [slice_cred, slice_hrn]
-        request_hash = self.key.compute_hash(arg_list)
-        return self.slicemgr.stop_slice(slice_cred, slice_hrn, request_hash)
+        return server.stop_slice(slice_cred, slice_hrn)
     
     # reset named slice
     def reset(self,opts, args):
         slice_hrn = args[0]
     
     # reset named slice
     def reset(self,opts, args):
         slice_hrn = args[0]
+        server = self.slicemgr
+        # direct connection to the nodes component manager interface
+        if opts.component:
+            server = self.get_component_server_from_hrn(opts.component)
         slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
         slice_cred = self.get_slice_cred(args[0]).save_to_string(save_parents=True)
-        arg_list = [slice_cred, slice_hrn]
-        request_hash = self.key.compute_hash(arg_list)
-        return self.slicemgr.reset_slice(slice_cred, slice_hrn, request_hash)
-    
-    #
-    #
-    # Display, Save, and Filter RSpecs and Records
-    #   - to be replace by EMF-generated routines
-    #
-    #
-    
-    def display_rspec(self,rspec, format = 'rspec'):
-        if format in ['dns']:
-            spec = RSpec()
-            spec.parseString(rspec)
-            hostnames = []
-            nodespecs = spec.getDictsByTagName('NodeSpec')
-            for nodespec in nodespecs:
-                if nodespec.has_key('name') and nodespec['name']:
-                    if isinstance(nodespec['name'], ListType):
-                        hostnames.extend(nodespec['name'])
-                    elif isinstance(nodespec['name'], StringTypes):
-                        hostnames.append(nodespec['name'])
-            result = hostnames
-        elif format in ['ip']:
-            spec = RSpec()
-            spec.parseString(rspec)
-            ips = []
-            ifspecs = spec.getDictsByTagName('IfSpec')
-            for ifspec in ifspecs:
-                if ifspec.has_key('addr') and ifspec['addr']:
-                    ips.append(ifspec['addr'])
-            result = ips 
-        else:     
-            result = rspec
-    
-        print result
-        return
-    
-    def display_list(self,results):
-        for result in results:
-            print result
-    
-    def save_rspec_to_file(self,rspec, filename):
-       if not filename.startswith(os.sep):
-           filename = self.options.sfi_dir + filename
-       if not filename.endswith(".rspec"):
-           filename = filename + ".rspec"
-    
-       f = open(filename, 'w')
-       f.write(rspec)
-       f.close()
-       return
-    
-    def display_records(self,recordList, dump = False):
-       ''' Print all fields in the record'''
-       for record in recordList:
-          self.display_record(record, dump)
-    
-    def display_record(self,record, dump = False):
-       if dump:
-           record.dump()
-       else:
-           info = record.getdict()
-           print "%s (%s)" % (info['hrn'], info['type'])
-       return
-    
-    def filter_records(self,type, records):
-       filtered_records = []
-       for record in records:
-           if (record['type'] == type) or (type == "all"):
-               filtered_records.append(record)
-       return filtered_records
-    
-    def save_records_to_file(self,filename, recordList):
-       index = 0
-       for record in recordList:
-           if index>0:
-               self.save_record_to_file(filename + "." + str(index), record)
-           else:
-               self.save_record_to_file(filename, record)
-           index = index + 1
-    
-    def save_record_to_file(self,filename, record):
-       if record['type'] in ['user']:
-           record = UserRecord(dict = record)
-       elif record['type'] in ['slice']:
-           record = SliceRecord(dict = record)
-       elif record['type'] in ['node']:
-           record = NodeRecord(dict = record)
-       elif record['type'] in ['authority', 'ma', 'sa']:
-          record = AuthorityRecord(dict = record)
-       else:
-           record = GeniRecord(dict = record) 
-       if not filename.startswith(os.sep):
-           filename = self.options.sfi_dir + filename
-       str = record.save_to_string()
-       file(filename, "w").write(str)
-       return
-    
-    def load_record_from_file(self,filename):
-       str = file(filename, "r").read()
-       record = GeniRecord(string=str)
-       return record
+        return server.reset_slice(slice_cred, slice_hrn)
     
     #
     # Main: parse arguments and dispatch to command
     #
     def main(self):
     
     #
     # Main: parse arguments and dispatch to command
     #
     def main(self):
-       parser = self.create_parser()
-       (options, args) = parser.parse_args()
-       self.options = options
-    
-       if len(args) <= 0:
+        parser = self.create_parser()
+        (options, args) = parser.parse_args()
+        self.options = options
+   
+        if options.hashrequest:
+            self.hashrequest=True
+        if len(args) <= 0:
             print "No command given. Use -h for help."
             return -1
     
             print "No command given. Use -h for help."
             return -1
     
-       command = args[0]
-       (cmd_opts, cmd_args) = self.create_cmd_parser(command).parse_args(args[1:])
-       if self.options.verbose :
-          print "Registry %s, sm %s, dir %s, user %s, auth %s" % (options.registry,
-                                                                   options.sm,
-                                                                   options.sfi_dir,
-                                                                   options.user,
+        command = args[0]
+        (cmd_opts, cmd_args) = self.create_cmd_parser(command).parse_args(args[1:])
+        if self.options.verbose :
+            print "Registry %s, sm %s, dir %s, user %s, auth %s" % (options.registry, options.sm,
+                                                                   options.sfi_dir, options.user,
                                                                    options.auth)
                                                                    options.auth)
-          print "Command %s" %command
-          if command in ("resources"):
-             print "resources cmd_opts %s" %cmd_opts.format
-          elif command in ("list","show","remove"):
-             print "cmd_opts.type %s" %cmd_opts.type
-          print "cmd_args %s" %cmd_args
-    
-       self.set_servers()
+            print "Command %s" %command
+            if command in ("resources"):
+                print "resources cmd_opts %s" %cmd_opts.format
+            elif command in ("list","show","remove"):
+                print "cmd_opts.type %s" %cmd_opts.type
+            print "cmd_args %s" %cmd_args
+    
+        self.set_servers()
+    
+        try:
+            self.dispatch(command, cmd_opts, cmd_args)
+        except KeyError:
+            raise 
+            print "Command not found:", command
+            sys.exit(1)
     
     
-       try:
-          self.dispatch(command, cmd_opts, cmd_args)
-       except KeyError:
-          raise 
-          print "Command not found:", command
-          sys.exit(1)
-    
-       return
+        return
     
 if __name__=="__main__":
    Sfi().main()
     
 if __name__=="__main__":
    Sfi().main()