You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by tr...@apache.org on 2012/07/26 16:38:54 UTC

svn commit: r1366020 - in /qpid/trunk/qpid: cpp/src/tests/ extras/qmf/src/py/qmf/ python/qpid/ tools/src/py/ tools/src/py/qpidtoollibs/

Author: tross
Date: Thu Jul 26 14:38:53 2012
New Revision: 1366020

URL: http://svn.apache.org/viewvc?rev=1366020&view=rev
Log:
QPID-3175 - Added SSL/x.509-auth capability to Python clients and Python tools

Added:
    qpid/trunk/qpid/cpp/src/tests/ping_broker   (with props)
Modified:
    qpid/trunk/qpid/cpp/src/tests/ssl_test
    qpid/trunk/qpid/extras/qmf/src/py/qmf/console.py
    qpid/trunk/qpid/python/qpid/connection.py
    qpid/trunk/qpid/python/qpid/delegates.py
    qpid/trunk/qpid/python/qpid/framer.py
    qpid/trunk/qpid/python/qpid/sasl.py
    qpid/trunk/qpid/python/qpid/util.py
    qpid/trunk/qpid/tools/src/py/qpid-cluster
    qpid/trunk/qpid/tools/src/py/qpid-config
    qpid/trunk/qpid/tools/src/py/qpid-ha
    qpid/trunk/qpid/tools/src/py/qpid-printevents
    qpid/trunk/qpid/tools/src/py/qpid-queue-stats
    qpid/trunk/qpid/tools/src/py/qpid-route
    qpid/trunk/qpid/tools/src/py/qpid-stat
    qpid/trunk/qpid/tools/src/py/qpid-tool
    qpid/trunk/qpid/tools/src/py/qpidtoollibs/broker.py

Added: qpid/trunk/qpid/cpp/src/tests/ping_broker
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/cpp/src/tests/ping_broker?rev=1366020&view=auto
==============================================================================
--- qpid/trunk/qpid/cpp/src/tests/ping_broker (added)
+++ qpid/trunk/qpid/cpp/src/tests/ping_broker Thu Jul 26 14:38:53 2012
@@ -0,0 +1,127 @@
+#!/usr/bin/env python
+
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements.  See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership.  The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+import os
+from optparse import OptionParser, OptionGroup
+import sys
+import locale
+import socket
+import re
+from qpid.messaging import Connection
+
+home = os.environ.get("QPID_TOOLS_HOME", os.path.normpath("/usr/share/qpid-tools"))
+sys.path.append(os.path.join(home, "python"))
+
+from qpidtoollibs import BrokerAgent
+from qpidtoollibs import Display, Header, Sorter, YN, Commas, TimeLong
+
+
+class Config:
+    def __init__(self):
+        self._host = "localhost"
+        self._connTimeout = 10
+
+config = Config()
+conn_options = {}
+
+def OptionsAndArguments(argv):
+    """ Set global variables for options, return arguments """
+
+    global config
+    global conn_options
+
+    usage = "%prog [options]"
+
+    parser = OptionParser(usage=usage)
+
+    parser.add_option("-b", "--broker",  action="store", type="string", default="localhost", metavar="<url>",
+                      help="URL of the broker to query")
+    parser.add_option("-t", "--timeout", action="store", type="int", default=10, metavar="<secs>",
+                      help="Maximum time to wait for broker connection (in seconds)")
+    parser.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>",
+                      help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+    parser.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
+    parser.add_option("--ssl-key", action="store", type="string", metavar="<key>", help="Client SSL private key (PEM Format)")
+    parser.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
+
+    opts, args = parser.parse_args(args=argv)
+
+    config._host = opts.broker
+    config._connTimeout = opts.timeout
+
+    if opts.sasl_mechanism:
+        conn_options['sasl_mechanisms'] = opts.sasl_mechanism
+    if opts.ssl_certificate:
+        conn_options['ssl_certfile'] = opts.ssl_certificate
+    if opts.ssl_key:
+        conn_options['ssl_key'] = opts.ssl_key
+    if opts.ha_admin:
+        conn_options['client_properties'] = {'qpid.ha-admin' : 1}
+    return args
+
+class BrokerManager:
+    def __init__(self):
+        self.brokerName = None
+        self.connection = None
+        self.broker     = None
+        self.cluster    = None
+
+    def SetBroker(self, brokerUrl):
+        self.url = brokerUrl
+        self.connection = Connection.establish(self.url, **conn_options)
+        self.broker = BrokerAgent(self.connection)
+
+    def Disconnect(self):
+        """ Release any allocated brokers.  Ignore any failures as the tool is
+        shutting down.
+        """
+        try:
+            connection.close()
+        except:
+            pass
+
+    def Ping(self, args):
+        for sequence in range(10):
+            result = self.broker.echo(sequence, "ECHO BODY")
+            if result['sequence'] != sequence:
+                raise Exception("Invalid Sequence")
+
+
+def main(argv=None):
+
+    args = OptionsAndArguments(argv)
+    bm   = BrokerManager()
+
+    try:
+        bm.SetBroker(config._host)
+        bm.Ping(args)
+        bm.Disconnect()
+        return 0
+    except KeyboardInterrupt:
+        print
+    except Exception,e:
+        print "Failed: %s - %s" % (e.__class__.__name__, e)
+
+    bm.Disconnect()   # try to deallocate brokers
+    return 1
+
+if __name__ == "__main__":
+    sys.exit(main())

Propchange: qpid/trunk/qpid/cpp/src/tests/ping_broker
------------------------------------------------------------------------------
    svn:executable = *

Modified: qpid/trunk/qpid/cpp/src/tests/ssl_test
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/cpp/src/tests/ssl_test?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/cpp/src/tests/ssl_test (original)
+++ qpid/trunk/qpid/cpp/src/tests/ssl_test Thu Jul 26 14:38:53 2012
@@ -148,6 +148,11 @@ URL=$TEST_HOSTNAME:$PORT
 MSG=`./qpid-receive -b $URL --connection-options '{transport:ssl,heartbeat:2}' -a "foo;{create:always}" --messages 1`
 test "$MSG" = "hello again" || { echo "receive failed '$MSG' != 'hello again'"; exit 1; }
 
+## Test using the Python client
+echo "Testing Non-Authenticating with Python Client..."
+URL=amqps://$TEST_HOSTNAME:$PORT
+if `$top_srcdir/src/tests/ping_broker -b $URL`; then echo "    Passed"; else { echo "    Failed"; exit 1; }; fi
+
 #### Client Authentication tests
 
 start_authenticating_broker

Modified: qpid/trunk/qpid/extras/qmf/src/py/qmf/console.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/extras/qmf/src/py/qmf/console.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/extras/qmf/src/py/qmf/console.py (original)
+++ qpid/trunk/qpid/extras/qmf/src/py/qmf/console.py Thu Jul 26 14:38:53 2012
@@ -2422,8 +2422,12 @@ class Broker(Thread):
       sock.settimeout(5)
       oldTimeout = sock.gettimeout()
       sock.settimeout(self.connTimeout)
+      connSock = None
       if self.ssl:
-        connSock = ssl(sock)
+        if 'ssl_certfile' in self.connectArgs:
+          connSock = ssl(sock, certfile=self.connectArgs['ssl_certfile'])
+        else:
+          connSock = ssl(sock)
       else:
         connSock = sock
       self.conn = Connection(connSock, username=self.authUser, password=self.authPass,

Modified: qpid/trunk/qpid/python/qpid/connection.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/python/qpid/connection.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/python/qpid/connection.py (original)
+++ qpid/trunk/qpid/python/qpid/connection.py Thu Jul 26 14:38:53 2012
@@ -166,8 +166,9 @@ class Connection(Framer):
         # If we have a security layer and it sends us no decoded data,
         # that's OK as long as its return code is happy.
         if self.security_layer_rx:
-          status, data = self.security_layer_rx.decode(data)
-          if not status:
+          try:
+            data = self.security_layer_rx.decode(data)
+          except:
             self.detach_all()
             break
       # When we do not use SSL transport, we get periodic 

Modified: qpid/trunk/qpid/python/qpid/delegates.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/python/qpid/delegates.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/python/qpid/delegates.py (original)
+++ qpid/trunk/qpid/python/qpid/delegates.py Thu Jul 26 14:38:53 2012
@@ -24,13 +24,7 @@ from exceptions import VersionError, Clo
 from logging import getLogger
 from ops import Control
 import sys
-
-_have_sasl = None
-try:
-  import saslwrapper
-  _have_sasl = True
-except:
-  pass
+from qpid import sasl
 
 log = getLogger("qpid.io.ctl")
 
@@ -172,20 +166,19 @@ class Client(Delegate):
     self.username  = username
     self.password  = password
 
-    if _have_sasl:
-      self.sasl = saslwrapper.Client()
-      if username and len(username) > 0:
-        self.sasl.setAttr("username", str(username))
-      if password and len(password) > 0:
-        self.sasl.setAttr("password", str(password))
-      self.sasl.setAttr("service", str(kwargs.get("service", "qpidd")))
-      if "host" in kwargs:
-        self.sasl.setAttr("host", str(kwargs["host"]))
-      if "min_ssf" in kwargs:
-        self.sasl.setAttr("minssf", kwargs["min_ssf"])
-      if "max_ssf" in kwargs:
-        self.sasl.setAttr("maxssf", kwargs["max_ssf"])
-      self.sasl.init()
+    self.sasl = sasl.Client()
+    if username and len(username) > 0:
+      self.sasl.setAttr("username", str(username))
+    if password and len(password) > 0:
+      self.sasl.setAttr("password", str(password))
+    self.sasl.setAttr("service", str(kwargs.get("service", "qpidd")))
+    if "host" in kwargs:
+      self.sasl.setAttr("host", str(kwargs["host"]))
+    if "min_ssf" in kwargs:
+      self.sasl.setAttr("minssf", kwargs["min_ssf"])
+    if "max_ssf" in kwargs:
+      self.sasl.setAttr("maxssf", kwargs["max_ssf"])
+    self.sasl.init()
 
   def start(self):
     # XXX
@@ -204,39 +197,29 @@ class Client(Delegate):
         mech_list += str(mech) + " "
     mech = None
     initial = None
-    if _have_sasl:
-      status, mech, initial = self.sasl.start(mech_list)
-      if status == False:
-        raise Closed("SASL error: %s" % self.sasl.getError())
-    else:
-      if self.username and self.password and ("PLAIN" in mech_list):
-        mech = "PLAIN"
-        initial = "\0%s\0%s" % (self.username, self.password)
-      else:
-        mech = "ANONYMOUS"
-        if not mech in mech_list:
-          raise Closed("No acceptable SASL authentication mechanism available")
+    try:
+      mech, initial = self.sasl.start(mech_list)
+    except Exception, e:
+      raise Closed(str(e))
     ch.connection_start_ok(client_properties=self.client_properties,
                            mechanism=mech, response=initial)
 
   def connection_secure(self, ch, secure):
     resp = None
-    if _have_sasl:
-      status, resp = self.sasl.step(secure.challenge)
-      if status == False:
-        raise Closed("SASL error: %s" % self.sasl.getError())
+    try:
+      resp = self.sasl.step(secure.challenge)
+    except Exception, e:
+      raise Closed(str(e))
     ch.connection_secure_ok(response=resp)
 
   def connection_tune(self, ch, tune):
     ch.connection_tune_ok(heartbeat=self.heartbeat)
     ch.connection_open()
-    if _have_sasl:
-      self.connection.user_id = self.sasl.getUserId()
-      self.connection.security_layer_tx = self.sasl
+    self.connection.user_id = self.sasl.auth_username()
+    self.connection.security_layer_tx = self.sasl
 
   def connection_open_ok(self, ch, open_ok):
-    if _have_sasl:
-      self.connection.security_layer_rx = self.sasl
+    self.connection.security_layer_rx = self.sasl
     self.connection.opened = True
     notify(self.connection.condition)
 

Modified: qpid/trunk/qpid/python/qpid/framer.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/python/qpid/framer.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/python/qpid/framer.py (original)
+++ qpid/trunk/qpid/python/qpid/framer.py Thu Jul 26 14:38:53 2012
@@ -51,9 +51,10 @@ class Framer(Packer):
     self.sock_lock.acquire()
     try:
       if self.security_layer_tx:
-        status, cipher_buf = self.security_layer_tx.encode(self.tx_buf)
-        if status == False:
-          raise Closed(self.security_layer_tx.getError())
+        try:
+          cipher_buf = self.security_layer_tx.encode(self.tx_buf)
+        except SASLError, e:
+          raise Closed(str(e))
         self._write(cipher_buf)
       else:
         self._write(self.tx_buf)
@@ -91,9 +92,10 @@ class Framer(Packer):
       try:
         s = self.sock.recv(n) # NOTE: instead of "n", arg should be "self.maxbufsize"
         if self.security_layer_rx:
-          status, s = self.security_layer_rx.decode(s)
-          if status == False:
-            raise Closed(self.security_layer_tx.getError())
+          try:
+            s = self.security_layer_rx.decode(s)
+          except SASLError, e:
+            raise Closed(str(e))
       except socket.timeout:
         if self.aborted():
           raise Closed()

Modified: qpid/trunk/qpid/python/qpid/sasl.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/python/qpid/sasl.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/python/qpid/sasl.py (original)
+++ qpid/trunk/qpid/python/qpid/sasl.py Thu Jul 26 14:38:53 2012
@@ -29,6 +29,9 @@ class WrapperClient:
 
   def setAttr(self, name, value):
     status = self._cli.setAttr(str(name), str(value))
+    if status and name == 'username':
+      status = self._cli.setAttr('externaluser', str(value))
+      
     if not status:
       raise SASLError(self._cli.getError())
 

Modified: qpid/trunk/qpid/python/qpid/util.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/python/qpid/util.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/python/qpid/util.py (original)
+++ qpid/trunk/qpid/python/qpid/util.py Thu Jul 26 14:38:53 2012
@@ -25,9 +25,9 @@ except ImportError:
   from socket import ssl as wrap_socket
   class ssl:
 
-    def __init__(self, sock):
+    def __init__(self, sock, keyfile=None, certfile=None, trustfile=None):
       self.sock = sock
-      self.ssl = wrap_socket(sock)
+      self.ssl = wrap_socket(sock, keyfile=keyfile, certfile=certfile, ca_certs=trustfile)
 
     def recv(self, n):
       return self.ssl.read(n)

Modified: qpid/trunk/qpid/tools/src/py/qpid-cluster
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-cluster?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-cluster (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-cluster Thu Jul 26 14:38:53 2012
@@ -64,17 +64,19 @@ class IpAddr:
         return bestAddr
 
 class BrokerManager:
-    def __init__(self, config):
-        self.config = config
-        self.brokerName = None
-        self.qmf        = None
-        self.broker     = None
-        self.brokers    = []
+    def __init__(self, config, conn_options):
+        self.config       = config
+        self.cert         = None
+        self.conn_options = conn_options
+        self.brokerName   = None
+        self.qmf          = None
+        self.broker       = None
+        self.brokers      = []
 
     def SetBroker(self, brokerUrl):
         self.url = brokerUrl
         self.qmf = Session()
-        self.broker = self.qmf.addBroker(brokerUrl, self.config._connTimeout)
+        self.broker = self.qmf.addBroker(brokerUrl, self.config._connTimeout, **self.conn_options)
         agents = self.qmf.getAgents()
         for a in agents:
             if a.getAgentBank() == '0':
@@ -240,6 +242,8 @@ def main(argv=None):
                       description="Example: $ qpid-cluster -C  broker-host:10000")
 
         parser.add_option("-t", "--timeout", action="store", type="int", default=10, metavar="SECS", help="Maximum time to wait for broker connection (in seconds)")
+        parser.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+        parser.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
         parser.add_option("-C", "--all-connections", action="store_true", default=False, help="View client connections to all cluster members")
         parser.add_option("-c", "--connections",  metavar="ID", help="View client connections to specified member")
         parser.add_option("-d", "--del-connection",  metavar="HOST:PORT", help="Disconnect a client connection")
@@ -280,7 +284,13 @@ def main(argv=None):
         config._force = opts.force
         config._numeric = opts.numeric
 
-        bm    = BrokerManager(config)
+        conn_options = {}
+        if opts.sasl_mechanism:
+            conn_options['mechanisms'] = opts.sasl_mechanism
+        if opts.ssl_certificate:
+            conn_options['ssl_certfile'] = opts.ssl_certificate
+
+        bm = BrokerManager(config, conn_options)
 
         try:
             bm.SetBroker(config._host)
@@ -303,7 +313,6 @@ def main(argv=None):
 
         bm.Disconnect()
     except Exception, e:
-        raise
         print str(e)
         return 1
 

Modified: qpid/trunk/qpid/tools/src/py/qpid-config
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-config?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-config (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-config Thu Jul 26 14:38:53 2012
@@ -88,7 +88,6 @@ class Config:
         self._altern_ex         = None
         self._durable           = False
         self._replicate       = None
-        self._ha_admin          = False
         self._clusterDurable    = False
         self._if_empty          = True
         self._if_unused         = True
@@ -102,7 +101,6 @@ class Config:
         self._ive               = False
         self._eventGeneration   = None
         self._file              = None
-        self._sasl_mechanism    = None
         self._flowStopCount     = None
         self._flowResumeCount   = None
         self._flowStopSize      = None
@@ -114,6 +112,7 @@ class Config:
         self._returnCode        = 0
 
 config = Config()
+conn_options = {}
 
 FILECOUNT = "qpid.file_count"
 FILESIZE  = "qpid.file_size"
@@ -177,6 +176,9 @@ def OptionsAndArguments(argv):
     group1.add_option("-r", "--recursive", action="store_true", help="Show bindings in queue or exchange list")
     group1.add_option("-b", "--broker", action="store", type="string", default="localhost:5672", metavar="<address>", help="Address of qpidd broker with syntax: [username/password@] hostname | ip-address [:<port>]")
     group1.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+    group1.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
+    group1.add_option("--ssl-key", action="store", type="string", metavar="<key>", help="Client SSL private key (PEM Format)")
+    group1.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
     parser.add_option_group(group1)
 
     group_ls = OptionGroup(parser, "Options for Listing Exchanges and Queues")
@@ -187,7 +189,6 @@ def OptionsAndArguments(argv):
     group2.add_option("--alternate-exchange", action="store", type="string", metavar="<aexname>", help="Name of the alternate-exchange for the new queue or exchange. Exchanges route messages to the alternate exchange if they are unable to route them elsewhere. Queues route messages to the alternate exchange if they are rejected by a subscriber or orphaned by queue deletion.")
     group2.add_option("--durable", action="store_true", help="The new queue or exchange is durable.")
     group2.add_option("--replicate", action="store", metavar="<level>", help="Enable automatic replication in a HA cluster. <level> is 'none', 'configuration' or 'all').")
-    group2.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
     parser.add_option_group(group2)
 
     group3 = OptionGroup(parser, "Options for Adding Queues")
@@ -306,6 +307,16 @@ def OptionsAndArguments(argv):
         config._extra_arguments = opts.extra_arguments
     if opts.start_replica:
         config._start_replica = opts.start_replica
+
+    if opts.sasl_mechanism:
+        conn_options['sasl_mechanisms'] = opts.sasl_mechanism
+    if opts.ssl_certificate:
+        conn_options['ssl_certfile'] = opts.ssl_certificate
+    if opts.ssl_key:
+        conn_options['ssl_key'] = opts.ssl_key
+    if opts.ha_admin:
+        conn_options['client_properties'] = {'qpid.ha-admin' : 1}
+
     return args
 
 
@@ -355,11 +366,9 @@ class BrokerManager:
         self.conn       = None
         self.broker     = None
 
-    def SetBroker(self, brokerUrl, mechanism):
+    def SetBroker(self, brokerUrl):
         self.url = brokerUrl
-        client_properties={}
-        if config._ha_admin: client_properties["qpid.ha-admin"] = 1
-        self.conn = Connection.establish(self.url, sasl_mechanisms=mechanism, client_properties=client_properties)
+        self.conn = Connection.establish(self.url, **conn_options)
         self.broker = BrokerAgent(self.conn)
 
     def Disconnect(self):
@@ -690,7 +699,7 @@ def main(argv=None):
     bm   = BrokerManager()
 
     try:
-        bm.SetBroker(config._host, config._sasl_mechanism)
+        bm.SetBroker(config._host)
         if len(args) == 0:
             bm.Overview()
         else:

Modified: qpid/trunk/qpid/tools/src/py/qpid-ha
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-ha?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-ha (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-ha Thu Jul 26 14:38:53 2012
@@ -19,8 +19,7 @@
 # under the License.
 #
 
-import qmf.console, optparse, sys, time, os
-from qpid.management import managementChannel, managementClient
+import optparse, sys, time, os
 from qpid.messaging import Connection
 from qpid.messaging import Message as QpidMessage
 from qpidtoollibs.broker import BrokerAgent
@@ -47,6 +46,8 @@ class Command:
         self.help = help
         self.op=optparse.OptionParser(usage)
         self.op.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+        self.op.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
+        self.op.add_option("--ssl-key", action="store", type="string", metavar="<key>", help="Client SSL private key (PEM Format)")
         self.op.add_option("-b", "--broker", action="store", type="string", default="localhost:5672", metavar="<address>", help="Address of qpidd broker with syntax: [username/password@] hostname | ip-address [:<port>]")
 
     def execute(self, args):
@@ -54,13 +55,19 @@ class Command:
         if len(args) != len(self.arg_names)+1:
             self.op.print_help()
             raise Exception("Wrong number of arguments")
-        connection = Connection.establish(
-            opts.broker,
-            sasl_mechanisms=opts.sasl_mechanism,
-            client_properties={"qpid.ha-admin":1})
+        conn_options = {}
+        if opts.sasl_mechanism:
+            conn_options['sasl_mechanisms'] = opts.sasl_mechanism
+        if opts.ssl_certificate:
+            conn_options['ssl_certfile'] = opts.ssl_certificate
+        if opts.ssl_key:
+            conn_options['ssl_key'] = opts.ssl_key
+        conn_options['client_properties'] = {'qpid.ha-admin' : 1}
+
+        connection = Connection.establish(opts.broker, **conn_options)
         qmf_broker = BrokerAgent(connection)
         ha_broker = qmf_broker.getHaBroker()
-        if not ha_broker: raise Exception("HA module is not loaded on broker at %s"%broker)
+        if not ha_broker: raise Exception("HA module is not loaded on broker at %s" % opts.broker)
         try: self.do_execute(qmf_broker, ha_broker, opts, args)
         finally: connection.close()
 

Modified: qpid/trunk/qpid/tools/src/py/qpid-printevents
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-printevents?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-printevents (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-printevents Thu Jul 26 14:38:53 2012
@@ -57,11 +57,10 @@ class EventReceiver(Thread):
   This class does not use the "reconnect" option because it needs to report as
   events when the connection is established and when it's lost.
   """
-  def __init__(self, printer, url, mechanism, options):
+  def __init__(self, printer, url, options):
     Thread.__init__(self)
     self.printer   = printer
     self.url       = url
-    self.mechanism = mechanism
     self.options   = options
     self.running   = True
     self.helper    = EventHelper()
@@ -73,7 +72,7 @@ class EventReceiver(Thread):
     isOpen = False
     while self.running:
       try:
-        conn = Connection.establish(self.url, sasl_mechanisms=self.mechanism, client_properties=self.options)
+        conn = Connection.establish(self.url, **options)
         isOpen = True
         self.printer.pr(strftime("%c", gmtime(time())) + " NOTIC qpid-printevents:brokerConnected broker=%s" % self.url)
 
@@ -133,23 +132,37 @@ def main(argv=None):
   p = optparse.OptionParser(usage=_usage, description=_description, formatter=JHelpFormatter())
   p.add_option("--heartbeats", action="store_true", default=False, help="Use heartbeats.")
   p.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+  p.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
+  p.add_option("--ssl-key", action="store", type="string", metavar="<key>", help="Client SSL private key (PEM Format)")
+  p.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
 
   options, arguments = p.parse_args(args=argv)
   if len(arguments) == 0:
     arguments.append("localhost")
 
   brokers   = []
-  mechanism = options.sasl_mechanism
-  props     = {'qpid.ha-admin' : 1}
+  conn_options = {}
+  props = {}
   printer   = Printer()
 
+  if options.sasl_mechanism:
+    conn_options['sasl_mechanisms'] = options.sasl_mechanism
+  if options.ssl_certificate:
+    conn_options['ssl_certfile'] = options.ssl_certificate
+  if options.ssl_key:
+    conn_options['ssl_key'] = options.ssl_key
+  if options.ha_admin:
+    props['qpid.ha-admin'] = 1
   if options.heartbeats:
     props['heartbeat'] = 5
 
+  if len(props) > 0:
+    conn_options['client_properties'] = props
+
   try:
     try:
       for host in arguments:
-        er = EventReceiver(printer, host, mechanism, props)
+        er = EventReceiver(printer, host, conn_options)
         brokers.append(er)
         er.start()
 

Modified: qpid/trunk/qpid/tools/src/py/qpid-queue-stats
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-queue-stats?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-queue-stats (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-queue-stats Thu Jul 26 14:38:53 2012
@@ -32,13 +32,13 @@ from qpid.connection import Connection, 
 from time            import sleep
 
 class BrokerManager(Console):
-  def __init__(self, host, mechanism):
+  def __init__(self, host, conn_options):
     self.url = host
     self.objects = {}
     self.filter  = None
     self.session = Session(self, rcvEvents=False, rcvHeartbeats=False,
                            userBindings=True, manageConnections=True)
-    self.broker  = self.session.addBroker(self.url, None, mechanism)
+    self.broker  = self.session.addBroker(self.url, **conn_options)
     self.firstError = True
 
   def setFilter(self,filter):
@@ -126,17 +126,23 @@ def main(argv=None):
   p.add_option('--broker-address','-a', default='localhost' , help='broker-addr is in the form:  [username/password@] hostname | ip-address [:<port>] \n ex:  localhost, 10.1.1.7:10000, broker-host:10000, guest/guest@localhost')
   p.add_option('--filter','-f' ,default=None ,help='a list of comma separated queue names (regex are accepted) to show')
   p.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
- 
+  p.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
 
   options, arguments = p.parse_args(args=argv)
 
+  conn_options = {}
+  if options.sasl_mechanism:
+    conn_options['mechanisms'] = options.sasl_mechanism
+  if options.ssl_certificate:
+    conn_options['ssl_certfile'] = options.ssl_certificate
+
   host = options.broker_address
   filter = []
   if options.filter != None:
     for s in options.filter.split(","):
         filter.append(re.compile(s))
 
-  bm = BrokerManager(host, options.sasl_mechanism)
+  bm = BrokerManager(host, conn_options)
   bm.setFilter(filter)
   bm.Display()
  

Modified: qpid/trunk/qpid/tools/src/py/qpid-route
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-route?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-route (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-route Thu Jul 26 14:38:53 2012
@@ -53,16 +53,15 @@ def Usage():
 
 class Config:
     def __init__(self):
-        self._verbose   = False
-        self._quiet     = False
-        self._durable   = False
-        self._dellink   = False
-        self._srclocal  = False
-        self._transport = "tcp"
-        self._ack       = 0
-        self._connTimeout = 10
-        self._client_sasl_mechanism = None
-        self._ha_admin  = False
+        self._verbose      = False
+        self._quiet        = False
+        self._durable      = False
+        self._dellink      = False
+        self._srclocal     = False
+        self._transport    = "tcp"
+        self._ack          = 0
+        self._connTimeout  = 10
+        self._conn_options = {}
 
 config = Config()
 
@@ -97,6 +96,7 @@ def OptionsAndArguments(argv):
     parser.add_option("-t", "--transport", action="store", type="string", default="tcp", metavar="<transport>", help="Transport to use for links, defaults to tcp")
 
     parser.add_option("--client-sasl-mechanism", action="store", type="string", metavar="<mech>", help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). Used when the client connects to the destination broker (not for authentication between the source and destination brokers - that is specified using the [mechanisms] argument to 'add route'). SASL automatically picks the most secure available mechanism - use this option to override.")
+    parser.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
     parser.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
     opts, encArgs = parser.parse_args(args=argv)
 
@@ -130,13 +130,16 @@ def OptionsAndArguments(argv):
         config._transport = opts.transport
 
     if opts.ha_admin:
-        config._ha_admin = True
+        config._conn_options['client_properties'] = {'qpid.ha-admin' : 1}
 
     if opts.ack:
         config._ack = opts.ack
 
     if opts.client_sasl_mechanism:
-        config._client_sasl_mechanism = opts.client_sasl_mechanism
+        config._conn_options['mechanisms'] = opts.client_sasl_mechanism
+
+    if opts.ssl_certificate:
+        config._conn_options['ssl_certfile'] = opts.ssl_certificate
 
     return args
 
@@ -147,9 +150,7 @@ class RouteManager:
         self.local = BrokerURL(localBroker)
         self.remote  = None
         self.qmf = Session()
-        client_properties = {}
-        if config._ha_admin: client_properties["qpid.ha-admin"] = 1
-        self.broker = self.qmf.addBroker(localBroker, config._connTimeout, config._client_sasl_mechanism, client_properties=client_properties)
+        self.broker = self.qmf.addBroker(localBroker, config._connTimeout, **config._conn_options)
         self.broker._waitForStable()
         self.agent = self.broker.getBrokerAgent()
 

Modified: qpid/trunk/qpid/tools/src/py/qpid-stat
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-stat?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-stat (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-stat Thu Jul 26 14:38:53 2012
@@ -42,15 +42,15 @@ class Config:
         self._limit = 50
         self._increasing = False
         self._sortcol = None
-        self._sasl_mechanism = None
-        self._ha_admin = False
 
 config = Config()
+conn_options = {}
 
 def OptionsAndArguments(argv):
     """ Set global variables for options, return arguments """
 
     global config
+    global conn_options
 
     usage = \
 """%prog -g [options]
@@ -70,6 +70,8 @@ def OptionsAndArguments(argv):
                       help="Maximum time to wait for broker connection (in seconds)")
     group1.add_option("--sasl-mechanism", action="store", type="string", metavar="<mech>",
                       help="SASL mechanism for authentication (e.g. EXTERNAL, ANONYMOUS, PLAIN, CRAM-MD, DIGEST-MD5, GSSAPI). SASL automatically picks the most secure available mechanism - use this option to override.")
+    group1.add_option("--ssl-certificate", action="store", type="string", metavar="<cert>", help="Client SSL certificate (PEM Format)")
+    group1.add_option("--ssl-key", action="store", type="string", metavar="<key>", help="Client SSL private key (PEM Format)")
     group1.add_option("--ha-admin", action="store_true", help="Allow connection to a HA backup broker.")
     parser.add_option_group(group1)
 
@@ -100,8 +102,15 @@ def OptionsAndArguments(argv):
     config._connTimeout = opts.timeout
     config._increasing = opts.increasing
     config._limit = opts.limit
-    config._sasl_mechanism = opts.sasl_mechanism
-    config._ha_admin = opts.ha_admin
+
+    if opts.sasl_mechanism:
+        conn_options['sasl_mechanisms'] = opts.sasl_mechanism
+    if opts.ssl_certificate:
+        conn_options['ssl_certfile'] = opts.ssl_certificate
+    if opts.ssl_key:
+        conn_options['ssl_key'] = opts.ssl_key
+    if opts.ha_admin:
+        conn_options['client_properties'] = {'qpid.ha-admin' : 1}
 
     return args
 
@@ -137,11 +146,9 @@ class BrokerManager:
         self.broker     = None
         self.cluster    = None
 
-    def SetBroker(self, brokerUrl, mechanism):
+    def SetBroker(self, brokerUrl):
         self.url = brokerUrl
-        client_properties={}
-        if config._ha_admin: client_properties["qpid.ha-admin"] = 1
-        self.connection = Connection.establish(self.url, sasl_mechanisms=mechanism, client_properties=client_properties)
+        self.connection = Connection.establish(self.url, **conn_options)
         self.broker = BrokerAgent(self.connection)
 
     def Disconnect(self):
@@ -246,9 +253,10 @@ class BrokerManager:
     def displayConn(self):
         disp = Display(prefix="  ")
         heads = []
-        heads.append(Header('client-addr'))
+        heads.append(Header('connection'))
         heads.append(Header('cproc'))
         heads.append(Header('cpid'))
+        heads.append(Header('mech'))
         heads.append(Header('auth'))
         heads.append(Header('connected', Header.DURATION))
         heads.append(Header('idle', Header.DURATION))
@@ -262,6 +270,7 @@ class BrokerManager:
             row.append(conn.address)
             row.append(conn.remoteProcessName)
             row.append(conn.remotePid)
+            row.append(conn.saslMechanism)
             row.append(conn.authIdentity)
             row.append(broker.getUpdateTime() - conn.getCreateTime())
             row.append(broker.getUpdateTime() - conn.getUpdateTime())
@@ -537,7 +546,7 @@ def main(argv=None):
     bm   = BrokerManager()
 
     try:
-        bm.SetBroker(config._host, config._sasl_mechanism)
+        bm.SetBroker(config._host)
         bm.display(args)
         bm.Disconnect()
         return 0

Modified: qpid/trunk/qpid/tools/src/py/qpid-tool
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpid-tool?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpid-tool (original)
+++ qpid/trunk/qpid/tools/src/py/qpid-tool Thu Jul 26 14:38:53 2012
@@ -173,11 +173,11 @@ class Mcli(Cmd):
 class QmfData(Console):
   """
   """
-  def __init__(self, disp, url):
+  def __init__(self, disp, url, cert):
     self.disp = disp
     self.url = url
     self.session = Session(self, manageConnections=True)
-    self.broker = self.session.addBroker(self.url)
+    self.broker = self.session.addBroker(self.url, ssl_certfile=cert)
     self.lock = Lock()
     self.connected = None
     self.closing = None
@@ -724,10 +724,13 @@ if _host[0] == '-':
   sys.exit(1)
 
 disp = Display()
+cert = None
+if len(cargs) > 1:
+  cert = cargs[1]
 
 # Attempt to make a connection to the target broker
 try:
-  data = QmfData(disp, _host)
+  data = QmfData(disp, _host, cert)
 except Exception, e:
   if str(e).find("Exchange not found") != -1:
     print "Management not enabled on broker:  Use '-m yes' option on broker startup."

Modified: qpid/trunk/qpid/tools/src/py/qpidtoollibs/broker.py
URL: http://svn.apache.org/viewvc/qpid/trunk/qpid/tools/src/py/qpidtoollibs/broker.py?rev=1366020&r1=1366019&r2=1366020&view=diff
==============================================================================
--- qpid/trunk/qpid/tools/src/py/qpidtoollibs/broker.py (original)
+++ qpid/trunk/qpid/tools/src/py/qpidtoollibs/broker.py Thu Jul 26 14:38:53 2012
@@ -194,9 +194,10 @@ class BrokerAgent(object):
   def getMemory(self):
     return self._getSingleObject(Memory)
 
-  def echo(self, sequence, body):
+  def echo(self, sequence = 1, body = "Body"):
     """Request a response to test the path to the management broker"""
-    pass
+    args = {'sequence' : sequence, 'body' : body}
+    return self._method('echo', args)
 
   def connect(self, host, port, durable, authMechanism, username, password, transport):
     """Establish a connection to another broker"""



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org