in WdtTransferRequest.cpp [129:229]
ErrorCode WdtUri::process(const string& url) {
if (url.size() < WDT_URL_PREFIX.size()) {
WLOG(ERROR) << "Url doesn't specify wdt protocol";
return URI_PARSE_ERROR;
}
StringPiece urlPiece(url, 0, WDT_URL_PREFIX.size());
StringPiece wdtPrefix(WDT_URL_PREFIX);
if (urlPiece != wdtPrefix) {
WLOG(ERROR) << "Url does not specify wdt protocol " << url;
return URI_PARSE_ERROR;
}
urlPiece = StringPiece(url, WDT_URL_PREFIX.size());
if (urlPiece.empty()) {
WLOG(ERROR) << "Empty host name " << url;
return URI_PARSE_ERROR;
}
ErrorCode status = OK;
// Parse hostname
if (urlPiece[0] == '[') {
urlPiece.advance(1);
size_t hostNameEnd = urlPiece.find(']');
if (hostNameEnd == string::npos) {
WLOG(ERROR) << "Didn't find ] for ipv6 address " << url;
return URI_PARSE_ERROR;
}
hostName_.assign(urlPiece.data(), 0, hostNameEnd);
urlPiece.advance(hostNameEnd + 1);
} else {
size_t urlIndex = 0;
for (; urlIndex < urlPiece.size(); ++urlIndex) {
if (urlPiece[urlIndex] == ':') {
break;
}
if (urlPiece[urlIndex] == '?') {
break;
}
}
hostName_.assign(urlPiece.data(), 0, urlIndex);
urlPiece.advance(urlIndex);
}
if (hostName_.empty()) {
status = URI_PARSE_ERROR;
WLOG(ERROR) << "Empty hostname " << url;
}
if (urlPiece.empty()) {
return status;
}
// TODO: allow for '/' like wdt://[::1]:1234/?num_ports=3
// parse port number
if (urlPiece[0] == ':') {
urlPiece.advance(1);
size_t paramsIndex = urlPiece.find('?');
if (paramsIndex == string::npos) {
paramsIndex = urlPiece.size();
}
try {
string portStr;
portStr.assign(urlPiece.data(), 0, paramsIndex);
port_ = folly::to<int32_t>(portStr);
} catch (std::exception& e) {
WLOG(ERROR) << "Invalid port, can't be parsed " << url;
status = URI_PARSE_ERROR;
}
urlPiece.advance(paramsIndex);
}
if (urlPiece.empty()) {
return status;
}
if (urlPiece[0] != '?') {
WLOG(ERROR) << "Unexpected delimiter for params " << urlPiece[0];
return URI_PARSE_ERROR;
}
urlPiece.advance(1);
// parse params
while (!urlPiece.empty()) {
StringPiece keyValuePair = urlPiece.split_step('&');
if (keyValuePair.empty()) {
// Last key value pair
keyValuePair = urlPiece;
urlPiece.advance(urlPiece.size());
}
StringPiece key = keyValuePair.split_step('=');
StringPiece value = keyValuePair;
if (key.empty()) {
// Value can be empty but key can't be empty
WLOG(ERROR) << "Errors parsing params, url = " << url;
status = URI_PARSE_ERROR;
break;
}
string unescapedValue;
if (!unescape(unescapedValue, value)) {
status = URI_PARSE_ERROR;
}
queryParams_[key.toString()] = unescapedValue;
}
return status;
}