Skip to content

Commit d5418e5

Browse files
authored
default_port works with protocol values (i.e. scheme + ':') (#136)
* Check for protocol (scheme + ':') before getting the default port * constexpr on is_special and default_port * Not every compiler likes constexpr with std::lower_bound
1 parent 2036b16 commit d5418e5

File tree

4 files changed

+33
-10
lines changed

4 files changed

+33
-10
lines changed

.clang-format

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,3 +32,5 @@ BreakBeforeBraces: Attach
3232
SpacesInParentheses: false
3333
SpaceInEmptyParentheses: false
3434
SpacesInCStyleCastParentheses: false
35+
SortIncludes: false
36+
SortUsingDeclarations: false

include/skyr/v1/core/schemes.hpp

Lines changed: 20 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -28,26 +28,36 @@ constexpr static auto schemes = default_port_list{{
2828
{"ws"sv, static_cast<std::uint16_t>(80)},
2929
{"wss"sv, static_cast<std::uint16_t>(443)},
3030
}};
31-
32-
constexpr static auto scheme_less(
33-
const default_port_list::value_type &special_scheme,
34-
std::string_view scheme) {
35-
return special_scheme.first < scheme;
36-
};
3731
} // namespace details
3832

3933
/// \param scheme
4034
/// \returns
4135
inline auto is_special(std::string_view scheme) noexcept {
42-
auto it = std::lower_bound(cbegin(details::schemes), cend(details::schemes), scheme, details::scheme_less);
43-
return ((it != end(details::schemes)) && !(scheme < it->first));
36+
constexpr auto less = [] (const auto &special_scheme, auto scheme) {
37+
return special_scheme.first < scheme;
38+
};
39+
40+
if (scheme.back() == ':') {
41+
scheme.remove_suffix(1);
42+
}
43+
auto first = std::cbegin(details::schemes), last = std::cend(details::schemes);
44+
auto it = std::lower_bound(first, last, scheme, less);
45+
return ((it != last) && !(scheme < it->first));
4446
}
4547

4648
/// \param scheme
4749
/// \returns
4850
inline auto default_port(std::string_view scheme) noexcept {
49-
auto it = std::lower_bound(cbegin(details::schemes), cend(details::schemes), scheme, details::scheme_less);
50-
return ((it != end(details::schemes)) && !(scheme < it->first)) ? it->second : std::nullopt;
51+
constexpr auto less = [] (const auto &special_scheme, auto scheme) {
52+
return special_scheme.first < scheme;
53+
};
54+
55+
if (scheme.back() == ':') {
56+
scheme.remove_suffix(1);
57+
}
58+
auto first = std::cbegin(details::schemes), last = std::cend(details::schemes);
59+
auto it = std::lower_bound(first, last, scheme, less);
60+
return ((it != last) && !(scheme < it->first)) ? it->second : std::nullopt;
5161
}
5262
} // namespace v1
5363
} // namespace skyr

include/skyr/v1/url.hpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -219,6 +219,11 @@ class url {
219219
/// \returns The [URL origin](https://url.spec.whatwg.org/#origin)
220220
[[nodiscard]] auto origin() const -> string_type;
221221

222+
/// The URL scheme
223+
[[nodiscard]] auto scheme() const -> string_type {
224+
return url_.scheme;
225+
}
226+
222227
/// The URL scheme + `":"`
223228
///
224229
/// \returns The [URL protocol](https://url.spec.whatwg.org/#dom-url-protocol)

tests/url/url_tests.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -440,6 +440,12 @@ TEST_CASE("url_tests", "[url]") {
440440
CHECK_FALSE(port);
441441
}
442442

443+
SECTION("http_default_port_is_80_using_protocol") {
444+
auto port = skyr::url::default_port("http:");
445+
REQUIRE(port);
446+
CHECK(80 == port.value());
447+
}
448+
443449
SECTION("about_blank") {
444450
auto instance = skyr::url("about:blank");
445451
CHECK("about:" == instance.protocol());

0 commit comments

Comments
 (0)