diff options
| author | Pavel Moravec <pmoravec@apache.org> | 2014-06-18 07:40:22 +0000 |
|---|---|---|
| committer | Pavel Moravec <pmoravec@apache.org> | 2014-06-18 07:40:22 +0000 |
| commit | 9c07d2fd2d1808f0a3b8ee35c86cb65e58444ae8 (patch) | |
| tree | dbe13b2003d1be4f46463cd96dd8ab71d57668b7 /qpid/cpp/src/tests | |
| parent | f9c83b18c822fbebe8417818b1025503c2238b86 (diff) | |
| download | qpid-python-9c07d2fd2d1808f0a3b8ee35c86cb65e58444ae8.tar.gz | |
QPID-5817: [C++ broker] Improve ACL authorisation of QMF methods and queries
git-svn-id: https://svn.apache.org/repos/asf/qpid/trunk@1603364 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'qpid/cpp/src/tests')
| -rwxr-xr-x | qpid/cpp/src/tests/acl.py | 163 | ||||
| -rwxr-xr-x | qpid/cpp/src/tests/ha_tests.py | 1 |
2 files changed, 159 insertions, 5 deletions
diff --git a/qpid/cpp/src/tests/acl.py b/qpid/cpp/src/tests/acl.py index ec6b229ba4..5f5d1e01fe 100755 --- a/qpid/cpp/src/tests/acl.py +++ b/qpid/cpp/src/tests/acl.py @@ -27,6 +27,7 @@ from qpid.testlib import TestBase010 from qmf.console import Session from qpid.datatypes import Message import qpid.messaging +from qpidtoollibs import BrokerAgent class ACLFile: def __init__(self, policy='data_dir/policy.acl'): @@ -40,6 +41,14 @@ class ACLFile: class ACLTests(TestBase010): + # required for testing QMF methods + def get_messaging_connection(self, user, passwd): + parms = {'username':user, 'password':passwd, 'sasl_mechanisms':'PLAIN'} + brokerurl="%s:%s" %(self.broker.host, self.broker.port) + connection = qpid.messaging.Connection(brokerurl, **parms) + connection.open() + return connection + # For connection limit tests this function # throws if the connection won't start # returns a connection that the caller can close if he likes. @@ -796,10 +805,16 @@ class ACLTests(TestBase010): aclf.write('acl deny bob@QPID create queue name=q1 durable=true\n') aclf.write('acl deny bob@QPID create queue name=q2 exclusive=true policytype=ring\n') aclf.write('acl deny bob@QPID access queue name=q3\n') - aclf.write('acl deny bob@QPID purge queue name=q3\n') aclf.write('acl deny bob@QPID delete queue name=q4\n') aclf.write('acl deny bob@QPID create queue name=q5 maxqueuesize=1000 maxqueuecount=100\n') aclf.write('acl deny bob@QPID create queue name=q6 paging=true\n') + aclf.write('acl deny bob@QPID purge queue name=q7\n') + aclf.write('acl deny bob@QPID move queue name=q7\n') + aclf.write('acl deny bob@QPID move queue name=q8 queuename=q7\n') + aclf.write('acl deny bob@QPID redirect queue name=q7\n') + aclf.write('acl deny bob@QPID redirect queue name=q8 queuename=q7\n') + aclf.write('acl deny bob@QPID reroute queue name=q7\n') + aclf.write('acl deny bob@QPID reroute queue name=q8 exchangename=amq.fanout\n') aclf.write('acl allow all all') aclf.close() @@ -881,18 +896,89 @@ class ACLTests(TestBase010): self.assertEqual(403,e.args[0].error_code) session = self.get_session('bob','bob') + # some queues needs to be created for testing purge / move / reroute / redirect + session.queue_declare(queue="q7") + session.queue_declare(queue="q8") + session.queue_declare(queue="q9") try: - session.queue_purge(queue="q3") - self.fail("ACL should deny queue purge request for q3"); + session.queue_purge(queue="q7") + self.fail("ACL should deny queue purge request for q7"); except qpid.session.SessionException, e: self.assertEqual(403,e.args[0].error_code) session = self.get_session('bob','bob') try: - session.queue_purge(queue="q4") + session.queue_purge(queue="q8") except qpid.session.SessionException, e: if (403 == e.args[0].error_code): - self.fail("ACL should allow queue purge request for q4"); + self.fail("ACL should allow queue purge request for q8"); + + # as we use QMF methods, it is easier to use BrokerAgent from messaging.connection and not use session object as above + broker_agent = BrokerAgent(self.get_messaging_connection('bob','bob')) + + try: + broker_agent.queueMoveMessages("q7", "q8", 0) + self.fail("ACL should deny queue move request from q7 to q8"); + except Exception, e: + self.assertTrue("'error_code': 7," in e.args[0]) + broker_agent = BrokerAgent(self.get_messaging_connection('bob','bob')) + + try: + broker_agent.queueMoveMessages("q8", "q9", 0) + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue move request from q8 to q9"); + + try: + broker_agent.queueMoveMessages("q9", "q8", 0) + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue move request from q9 to q8"); + + try: + broker_agent.Redirect("q7", "q8") + self.fail("ACL should deny queue redirect request from q7 to q8"); + except Exception, e: + self.assertTrue("'error_code': 7," in e.args[0]) + broker_agent = BrokerAgent(self.get_messaging_connection('bob','bob')) + + try: + broker_agent.Redirect("q8", "q9") + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue redirect request from q8 to q9"); + + try: + broker_agent.Redirect("q9", "q8") + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue redirect request from q9 to q8"); + + try: + broker_agent.getQueue('q7').reroute(0, False, "amq.fanout") + self.fail("ACL should deny queue reroute request from q7 to amq.fanout"); + except Exception, e: + self.assertTrue("'error_code': 7," in e.args[0]) + broker_agent = BrokerAgent(self.get_messaging_connection('bob','bob')) + + try: + broker_agent.getQueue('q8').reroute(0, False, "amq.fanout") + self.fail("ACL should deny queue reroute request from q8 to amq.fanout"); + except Exception, e: + self.assertTrue("'error_code': 7," in e.args[0]) + broker_agent = BrokerAgent(self.get_messaging_connection('bob','bob')) + + try: + broker_agent.getQueue('q8').reroute(0, False, "amq.direct") + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue reroute request from q8 to amq.direct"); + + try: + broker_agent.getQueue('q9').reroute(0, False, "amq.fanout") + except Exception, e: + if ("'error_code': 7," in e.args[0]): + self.fail("ACL should allow queue reroute request from q9 to amq.fanout"); try: session.queue_delete(queue="q4") @@ -1748,6 +1834,52 @@ class ACLTests(TestBase010): self.assertEqual(7,e.args[0]["error_code"]) assert e.args[0]["error_text"].find("unauthorized-access") == 0 + def test_qmf_query(self): + aclf = self.get_acl_file() + aclf.write('acl allow all access exchange\n') + aclf.write('acl allow all bind exchange\n') + aclf.write('acl allow all create queue\n') + aclf.write('acl allow all access queue\n') + aclf.write('acl allow all delete queue\n') + aclf.write('acl allow all consume queue\n') + aclf.write('acl allow all access method\n') + aclf.write('acl allow bob@QPID access query name=org.apache.qpid.broker:queue:q1\n') + aclf.write('acl allow bob@QPID access query schemaclass=exchange\n') + aclf.write('acl deny all all') + aclf.close() + + result = self.reload_acl() + if (result): + self.fail(result) + + bob = BrokerAdmin(self.config.broker, "bob", "bob") + + try: + bob.query(object_name="org.apache.qpid.broker:queue:q1") + except Exception, e: + if ("unauthorized-access:" in e.args[0]): + self.fail("ACL should allow queue QMF query for q1"); + + try: + bob.query(object_name="org.apache.qpid.broker:queue:q2") + self.fail("ACL should deny queue QMF query for q2"); + except Exception, e: + self.assertTrue("unauthorized-access:" in e.args[0]) + bob = BrokerAdmin(self.config.broker, "bob", "bob") + + try: + bob.query(class_name="binding") + self.fail("ACL should deny class binding QMF query"); + except Exception, e: + self.assertTrue("unauthorized-access:" in e.args[0]) + bob = BrokerAdmin(self.config.broker, "bob", "bob") + + try: + bob.query(class_name="exchange") + except Exception, e: + if ("unauthorized-access:" in e.args[0]): + self.fail("ACL should allow class exchange QMF query"); + #===================================== # ACL consume tests @@ -3611,6 +3743,27 @@ class BrokerAdmin: raise Exception(response.content['_values']) else: raise Exception("Invalid response received, unexpected opcode: %s" % response.properties['qmf.opcode']) else: raise Exception("Invalid response received, not a qmfv2 method: %s" % response.properties['x-amqp-0-10.app-id']) + + def query(self, object_name=None, class_name=None): + content = { "_what": "OBJECT" } + if object_name is not None: + content["_object_id"] = {"_object_name": object_name } + if class_name is not None: + content["_schema_id"] = {"_class_name": class_name } + request = qpid.messaging.Message(reply_to=self.reply_to, content=content) + request.properties["x-amqp-0-10.app-id"] = "qmf2" + request.properties["qmf.opcode"] = "_query_request" + self.sender.send(request) + response = self.receiver.fetch() + self.session.acknowledge() + if response.properties['x-amqp-0-10.app-id'] == 'qmf2': + if response.properties['qmf.opcode'] == '_query_response': + return + elif response.properties['qmf.opcode'] == '_exception': + raise Exception(response.content['_values']) + else: raise Exception("Invalid response received, unexpected opcode: %s" % response.properties['qmf.opcode']) + else: raise Exception("Invalid response received, not a qmfv2 method: %s" % response.properties['x-amqp-0-10.app-id']) + def create_exchange(self, name, exchange_type=None, options={}): properties = options if exchange_type: properties["exchange_type"] = exchange_type diff --git a/qpid/cpp/src/tests/ha_tests.py b/qpid/cpp/src/tests/ha_tests.py index e2ebf220cf..1e870c55a8 100755 --- a/qpid/cpp/src/tests/ha_tests.py +++ b/qpid/cpp/src/tests/ha_tests.py @@ -613,6 +613,7 @@ acl allow zag@QPID publish exchange acl allow zag@QPID delete exchange acl allow zag@QPID access method acl allow zag@QPID create link +acl allow zag@QPID access query # Normal user acl allow zig@QPID all all acl deny all all |
