diff options
| author | Gordon Sim <gsim@apache.org> | 2011-03-07 10:34:42 +0000 |
|---|---|---|
| committer | Gordon Sim <gsim@apache.org> | 2011-03-07 10:34:42 +0000 |
| commit | 0cb1503ac264dab57b5cbc41a24f71017ecfaa03 (patch) | |
| tree | 4d2336f75744b91ffa9c910c848cc3ea58d8cd17 /cpp/src | |
| parent | 23d4c49d615c39eeb994cb50b12bd149d25c2bad (diff) | |
| download | qpid-python-0cb1503ac264dab57b5cbc41a24f71017ecfaa03.tar.gz | |
QPID-3115: Recognise sasl_mechanisms (plural) and support a space separate list as does the python client (continue to recognise sasl-mechanism as well for backword compatibility)
git-svn-id: https://svn.apache.org/repos/asf/qpid/trunk/qpid@1078733 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'cpp/src')
| -rw-r--r-- | cpp/src/qpid/client/ConnectionHandler.cpp | 48 | ||||
| -rw-r--r-- | cpp/src/qpid/client/amqp0_10/ConnectionImpl.cpp | 4 |
2 files changed, 35 insertions, 17 deletions
diff --git a/cpp/src/qpid/client/ConnectionHandler.cpp b/cpp/src/qpid/client/ConnectionHandler.cpp index 8dc1e8338a..4fbf55aa60 100644 --- a/cpp/src/qpid/client/ConnectionHandler.cpp +++ b/cpp/src/qpid/client/ConnectionHandler.cpp @@ -22,6 +22,7 @@ #include "qpid/client/ConnectionHandler.h" #include "qpid/SaslFactory.h" +#include "qpid/StringUtils.h" #include "qpid/client/Bounds.h" #include "qpid/framing/amqp_framing.h" #include "qpid/framing/all_method_bodies.h" @@ -202,6 +203,24 @@ void ConnectionHandler::fail(const std::string& message) namespace { std::string SPACE(" "); + +std::string join(const std::vector<std::string>& in) +{ + std::string result; + for (std::vector<std::string>::const_iterator i = in.begin(); i != in.end(); ++i) { + if (result.size()) result += SPACE; + result += *i; + } + return result; +} + +void intersection(const std::vector<std::string>& a, const std::vector<std::string>& b, std::vector<std::string>& results) +{ + for (std::vector<std::string>::const_iterator i = a.begin(); i != a.end(); ++i) { + if (std::find(b.begin(), b.end(), *i) != b.end()) results.push_back(*i); + } +} + } void ConnectionHandler::start(const FieldTable& /*serverProps*/, const Array& mechanisms, const Array& /*locales*/) @@ -216,25 +235,24 @@ void ConnectionHandler::start(const FieldTable& /*serverProps*/, const Array& me maxSsf ); - std::string mechlist; - bool chosenMechanismSupported = mechanism.empty(); - for (Array::const_iterator i = mechanisms.begin(); i != mechanisms.end(); ++i) { - if (!mechanism.empty() && mechanism == (*i)->get<std::string>()) { - chosenMechanismSupported = true; - mechlist = (*i)->get<std::string>() + SPACE + mechlist; - } else { - if (i != mechanisms.begin()) mechlist += SPACE; - mechlist += (*i)->get<std::string>(); + std::vector<std::string> mechlist; + if (mechanism.empty()) { + //mechlist is simply what the server offers + mechanisms.collect(mechlist); + } else { + //mechlist is the intersection of those indicated by user and + //those supported by server, in the order listed by user + std::vector<std::string> allowed = split(mechanism, " "); + std::vector<std::string> supported; + mechanisms.collect(supported); + intersection(allowed, supported, mechlist); + if (mechlist.empty()) { + throw Exception(QPID_MSG("Desired mechanism(s) not valid: " << mechanism << " (supported: " << join(supported) << ")")); } } - if (!chosenMechanismSupported) { - fail("Selected mechanism not supported: " + mechanism); - } - if (sasl.get()) { - string response = sasl->start(mechanism.empty() ? mechlist : mechanism, - getSecuritySettings ? getSecuritySettings() : 0); + string response = sasl->start(join(mechlist), getSecuritySettings ? getSecuritySettings() : 0); proxy.startOk(properties, sasl->getMechanism(), response, locale); } else { //TODO: verify that desired mechanism and locale are supported diff --git a/cpp/src/qpid/client/amqp0_10/ConnectionImpl.cpp b/cpp/src/qpid/client/amqp0_10/ConnectionImpl.cpp index ae99e01725..a87a8dea67 100644 --- a/cpp/src/qpid/client/amqp0_10/ConnectionImpl.cpp +++ b/cpp/src/qpid/client/amqp0_10/ConnectionImpl.cpp @@ -101,8 +101,8 @@ void ConnectionImpl::setOption(const std::string& name, const Variant& value) settings.username = value.asString(); } else if (name == "password") { settings.password = value.asString(); - } else if (name == "sasl-mechanism" || name == "sasl_mechanism") { - //TODO: handle space separate lists of mechanisms + } else if (name == "sasl-mechanism" || name == "sasl_mechanism" || + name == "sasl-mechanisms" || name == "sasl_mechanisms") { settings.mechanism = value.asString(); } else if (name == "sasl-service" || name == "sasl_service") { settings.service = value.asString(); |
