diff options
author | Tobias Markmann <tm@ayena.de> | 2016-06-07 19:40:15 (GMT) |
---|---|---|
committer | Kevin Smith <kevin.smith@isode.com> | 2016-06-14 20:04:42 (GMT) |
commit | 0d5dcec01a396ab64c559a5b0cd04eb38f2f1954 (patch) | |
tree | 64bc61c8f51313787717afacfd5a8e4cc777b778 /Swiften/Base/URL.cpp | |
parent | 1dbcf543910b85b53a95461ed4770264e0ddbc4c (diff) | |
download | swift-0d5dcec01a396ab64c559a5b0cd04eb38f2f1954.zip swift-0d5dcec01a396ab64c559a5b0cd04eb38f2f1954.tar.bz2 |
Add support for URLs with IPv6 addresses in Swift::URL
Test-Information:
Added unit tests and test cases from RFC 2732.
All tests pass on OS X 10.11.5.
Change-Id: Ic76e57985109912871c05d12253f73d3653bd7a3
Diffstat (limited to 'Swiften/Base/URL.cpp')
-rw-r--r-- | Swiften/Base/URL.cpp | 45 |
1 files changed, 36 insertions, 9 deletions
diff --git a/Swiften/Base/URL.cpp b/Swiften/Base/URL.cpp index a9a1140..4a47a11 100644 --- a/Swiften/Base/URL.cpp +++ b/Swiften/Base/URL.cpp @@ -1,11 +1,12 @@ /* - * Copyright (c) 2010 Isode Limited. + * Copyright (c) 2010-2016 Isode Limited. * All rights reserved. * See the COPYING file for more information. */ #include <Swiften/Base/URL.h> +#include <algorithm> #include <iostream> namespace Swift { @@ -62,18 +63,39 @@ URL URL::fromString(const std::string& urlString) { std::string host; boost::optional<int> port; - colonIndex = hostAndPort.find(':'); - if (colonIndex != std::string::npos) { - host = unescape(hostAndPort.substr(0, colonIndex)); - try { - port = boost::lexical_cast<int>(hostAndPort.substr(colonIndex + 1)); + if (hostAndPort[0] == '[') { + // handle IPv6 address literals + size_t addressEndIndex = hostAndPort.find(']'); + if (addressEndIndex != std::string::npos) { + host = hostAndPort.substr(1, addressEndIndex - 1); + colonIndex = hostAndPort.find(':', addressEndIndex); + if (colonIndex != std::string::npos) { + try { + port = boost::lexical_cast<int>(hostAndPort.substr(colonIndex + 1)); + } + catch (const boost::bad_lexical_cast&) { + return URL(); + } + } } - catch (const boost::bad_lexical_cast&) { + else { return URL(); } } else { - host = unescape(hostAndPort); + colonIndex = hostAndPort.find(':'); + if (colonIndex != std::string::npos) { + host = unescape(hostAndPort.substr(0, colonIndex)); + try { + port = boost::lexical_cast<int>(hostAndPort.substr(colonIndex + 1)); + } + catch (const boost::bad_lexical_cast&) { + return URL(); + } + } + else { + host = unescape(hostAndPort); + } } if (port) { @@ -102,7 +124,12 @@ std::string URL::toString() const { } result += "@"; } - result += host; + if (host.find(':') != std::string::npos) { + result += "[" + host + "]"; + } + else { + result += host; + } if (port) { result += ":"; result += boost::lexical_cast<std::string>(*port); |