240 lines
7.9 KiB
C++
240 lines
7.9 KiB
C++
// Copyright 2010 The Chromium Authors
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
// found in the LICENSE file.
|
|
|
|
#include "net/base/proxy_server.h"
|
|
|
|
#include "base/strings/string_number_conversions.h"
|
|
#include "net/base/proxy_string_util.h"
|
|
#include "testing/gtest/include/gtest/gtest.h"
|
|
#include "third_party/abseil-cpp/absl/types/optional.h"
|
|
|
|
namespace net {
|
|
|
|
namespace {
|
|
|
|
TEST(ProxyServerTest, DefaultConstructor) {
|
|
ProxyServer proxy_server;
|
|
EXPECT_FALSE(proxy_server.is_valid());
|
|
}
|
|
|
|
TEST(ProxyServerTest, FromSchemeHostAndPort) {
|
|
const struct {
|
|
const ProxyServer::Scheme input_scheme;
|
|
const char* const input_host;
|
|
const absl::optional<uint16_t> input_port;
|
|
const char* const input_port_str;
|
|
const char* const expected_host;
|
|
const uint16_t expected_port;
|
|
} tests[] = {
|
|
{ProxyServer::SCHEME_HTTP, "foopy", 80, "80", "foopy", 80},
|
|
|
|
// Non-standard port
|
|
{ProxyServer::SCHEME_HTTP, "foopy", 10, "10", "foopy", 10},
|
|
{ProxyServer::SCHEME_HTTP, "foopy", 0, "0", "foopy", 0},
|
|
|
|
// Hostname canonicalization
|
|
{ProxyServer::SCHEME_HTTP, "FoOpY", 80, "80", "foopy", 80},
|
|
{ProxyServer::SCHEME_HTTP, "f\u00fcpy", 80, "80", "xn--fpy-hoa", 80},
|
|
|
|
// IPv4 literal
|
|
{ProxyServer::SCHEME_HTTP, "1.2.3.4", 80, "80", "1.2.3.4", 80},
|
|
|
|
// IPv4 literal canonicalization
|
|
{ProxyServer::SCHEME_HTTP, "127.1", 80, "80", "127.0.0.1", 80},
|
|
{ProxyServer::SCHEME_HTTP, "0x7F.0x1", 80, "80", "127.0.0.1", 80},
|
|
{ProxyServer::SCHEME_HTTP, "0177.01", 80, "80", "127.0.0.1", 80},
|
|
|
|
// IPv6 literal
|
|
{ProxyServer::SCHEME_HTTP, "[3ffe:2a00:100:7031::1]", 80, "80",
|
|
"[3ffe:2a00:100:7031::1]", 80},
|
|
{ProxyServer::SCHEME_HTTP, "3ffe:2a00:100:7031::1", 80, "80",
|
|
"[3ffe:2a00:100:7031::1]", 80},
|
|
|
|
// IPv6 literal canonicalization
|
|
{ProxyServer::SCHEME_HTTP, "FEDC:BA98:7654:3210:FEDC:BA98:7654:3210", 80,
|
|
"80", "[fedc:ba98:7654:3210:fedc:ba98:7654:3210]", 80},
|
|
{ProxyServer::SCHEME_HTTP, "::192.9.5.5", 80, "80", "[::c009:505]", 80},
|
|
|
|
// Other schemes
|
|
{ProxyServer::SCHEME_HTTPS, "foopy", 111, "111", "foopy", 111},
|
|
{ProxyServer::SCHEME_QUIC, "foopy", 111, "111", "foopy", 111},
|
|
{ProxyServer::SCHEME_SOCKS4, "foopy", 111, "111", "foopy", 111},
|
|
{ProxyServer::SCHEME_SOCKS5, "foopy", 111, "111", "foopy", 111},
|
|
|
|
// Default ports
|
|
{ProxyServer::SCHEME_HTTP, "foopy", absl::nullopt, "", "foopy", 80},
|
|
{ProxyServer::SCHEME_HTTPS, "foopy", absl::nullopt, "", "foopy", 443},
|
|
{ProxyServer::SCHEME_QUIC, "foopy", absl::nullopt, "", "foopy", 443},
|
|
{ProxyServer::SCHEME_SOCKS4, "foopy", absl::nullopt, "", "foopy", 1080},
|
|
{ProxyServer::SCHEME_SOCKS5, "foopy", absl::nullopt, "", "foopy", 1080},
|
|
};
|
|
|
|
for (size_t i = 0; i < std::size(tests); ++i) {
|
|
SCOPED_TRACE(base::NumberToString(i) + ": " + tests[i].input_host + ":" +
|
|
base::NumberToString(tests[i].input_port.value_or(-1)));
|
|
auto proxy = ProxyServer::FromSchemeHostAndPort(
|
|
tests[i].input_scheme, tests[i].input_host, tests[i].input_port);
|
|
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_EQ(proxy.scheme(), tests[i].input_scheme);
|
|
EXPECT_EQ(proxy.GetHost(), tests[i].expected_host);
|
|
EXPECT_EQ(proxy.GetPort(), tests[i].expected_port);
|
|
|
|
auto proxy_from_string_port = ProxyServer::FromSchemeHostAndPort(
|
|
tests[i].input_scheme, tests[i].input_host, tests[i].input_port_str);
|
|
EXPECT_TRUE(proxy_from_string_port.is_valid());
|
|
EXPECT_EQ(proxy, proxy_from_string_port);
|
|
}
|
|
}
|
|
|
|
TEST(ProxyServerTest, InvalidHostname) {
|
|
const char* const tests[]{
|
|
"",
|
|
"[]",
|
|
"[foo]",
|
|
"foo:",
|
|
"foo:80",
|
|
":",
|
|
"http://foo",
|
|
"3ffe:2a00:100:7031::1]",
|
|
"[3ffe:2a00:100:7031::1",
|
|
"foo.80",
|
|
};
|
|
|
|
for (size_t i = 0; i < std::size(tests); ++i) {
|
|
SCOPED_TRACE(base::NumberToString(i) + ": " + tests[i]);
|
|
auto proxy = ProxyServer::FromSchemeHostAndPort(ProxyServer::SCHEME_HTTP,
|
|
tests[i], 80);
|
|
EXPECT_FALSE(proxy.is_valid());
|
|
}
|
|
}
|
|
|
|
TEST(ProxyServerTest, InvalidPort) {
|
|
const char* const tests[]{
|
|
"-1",
|
|
"65536",
|
|
"foo",
|
|
"0x35",
|
|
};
|
|
|
|
for (size_t i = 0; i < std::size(tests); ++i) {
|
|
SCOPED_TRACE(base::NumberToString(i) + ": " + tests[i]);
|
|
auto proxy = ProxyServer::FromSchemeHostAndPort(ProxyServer::SCHEME_HTTP,
|
|
"foopy", tests[i]);
|
|
EXPECT_FALSE(proxy.is_valid());
|
|
}
|
|
}
|
|
|
|
TEST(ProxyServerTest, ComparatorAndEquality) {
|
|
const struct {
|
|
// Inputs.
|
|
ProxyServer server1;
|
|
ProxyServer server2;
|
|
|
|
// Expectation.
|
|
// -1 means server1 is less than server2
|
|
// 0 means server1 equals server2
|
|
// 1 means server1 is greater than server2
|
|
int expected_comparison;
|
|
} kTests[] = {
|
|
{// Equal.
|
|
ProxyUriToProxyServer("foo:11", ProxyServer::SCHEME_HTTP),
|
|
ProxyUriToProxyServer("http://foo:11", ProxyServer::SCHEME_HTTP), 0},
|
|
{// Port is different.
|
|
ProxyUriToProxyServer("foo:333", ProxyServer::SCHEME_HTTP),
|
|
ProxyUriToProxyServer("foo:444", ProxyServer::SCHEME_HTTP), -1},
|
|
{// Host is different.
|
|
ProxyUriToProxyServer("foo:33", ProxyServer::SCHEME_HTTP),
|
|
ProxyUriToProxyServer("bar:33", ProxyServer::SCHEME_HTTP), 1},
|
|
{// Scheme is different.
|
|
ProxyUriToProxyServer("socks4://foo:33", ProxyServer::SCHEME_HTTP),
|
|
ProxyUriToProxyServer("http://foo:33", ProxyServer::SCHEME_HTTP), 1},
|
|
};
|
|
|
|
for (const auto& test : kTests) {
|
|
EXPECT_TRUE(test.server1.is_valid());
|
|
EXPECT_TRUE(test.server2.is_valid());
|
|
|
|
switch (test.expected_comparison) {
|
|
case -1:
|
|
EXPECT_TRUE(test.server1 < test.server2);
|
|
EXPECT_FALSE(test.server2 < test.server1);
|
|
EXPECT_FALSE(test.server2 == test.server1);
|
|
EXPECT_FALSE(test.server1 == test.server2);
|
|
break;
|
|
case 0:
|
|
EXPECT_FALSE(test.server1 < test.server2);
|
|
EXPECT_FALSE(test.server2 < test.server1);
|
|
EXPECT_TRUE(test.server2 == test.server1);
|
|
EXPECT_TRUE(test.server1 == test.server2);
|
|
break;
|
|
case 1:
|
|
EXPECT_FALSE(test.server1 < test.server2);
|
|
EXPECT_TRUE(test.server2 < test.server1);
|
|
EXPECT_FALSE(test.server2 == test.server1);
|
|
EXPECT_FALSE(test.server1 == test.server2);
|
|
break;
|
|
default:
|
|
FAIL() << "Invalid expectation. Can be only -1, 0, 1";
|
|
}
|
|
}
|
|
}
|
|
|
|
// Tests the various "is_*()" methods on ProxyServer.
|
|
TEST(ProxyServerTest, Properties) {
|
|
// HTTP proxy.
|
|
{
|
|
auto proxy = PacResultElementToProxyServer("PROXY foo");
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_TRUE(proxy.is_http());
|
|
EXPECT_FALSE(proxy.is_https());
|
|
EXPECT_TRUE(proxy.is_http_like());
|
|
EXPECT_FALSE(proxy.is_secure_http_like());
|
|
}
|
|
|
|
// HTTPS proxy.
|
|
{
|
|
auto proxy = PacResultElementToProxyServer("HTTPS foo");
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_FALSE(proxy.is_http());
|
|
EXPECT_TRUE(proxy.is_https());
|
|
EXPECT_TRUE(proxy.is_http_like());
|
|
EXPECT_TRUE(proxy.is_secure_http_like());
|
|
}
|
|
|
|
// QUIC proxy.
|
|
{
|
|
auto proxy = PacResultElementToProxyServer("QUIC foo");
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_FALSE(proxy.is_http());
|
|
EXPECT_FALSE(proxy.is_https());
|
|
EXPECT_TRUE(proxy.is_http_like());
|
|
EXPECT_TRUE(proxy.is_secure_http_like());
|
|
}
|
|
|
|
// SOCKS5 proxy.
|
|
{
|
|
auto proxy = PacResultElementToProxyServer("SOCKS5 foo");
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_FALSE(proxy.is_http());
|
|
EXPECT_FALSE(proxy.is_https());
|
|
EXPECT_FALSE(proxy.is_http_like());
|
|
EXPECT_FALSE(proxy.is_secure_http_like());
|
|
}
|
|
|
|
// DIRECT
|
|
{
|
|
auto proxy = PacResultElementToProxyServer("DIRECT");
|
|
ASSERT_TRUE(proxy.is_valid());
|
|
EXPECT_FALSE(proxy.is_http());
|
|
EXPECT_FALSE(proxy.is_https());
|
|
EXPECT_FALSE(proxy.is_http_like());
|
|
EXPECT_FALSE(proxy.is_secure_http_like());
|
|
}
|
|
}
|
|
|
|
} // namespace
|
|
|
|
} // namespace net
|