1 /*
2 * nghttp2 - HTTP/2 C Library
3 *
4 * Copyright (c) 2016 Tatsuhiro Tsujikawa
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining
7 * a copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sublicense, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be
15 * included in all copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 */
25 #include "shrpx_http_test.h"
26
27 #ifdef HAVE_UNISTD_H
28 # include <unistd.h>
29 #endif // HAVE_UNISTD_H
30
31 #include <cstdlib>
32
33 #include "munitxx.h"
34
35 #include "shrpx_http.h"
36 #include "shrpx_config.h"
37 #include "shrpx_log.h"
38
39 using namespace std::literals;
40
41 namespace shrpx {
42
43 namespace {
44 const MunitTest tests[]{
45 munit_void_test(test_shrpx_http_create_forwarded),
46 munit_void_test(test_shrpx_http_create_via_header_value),
47 munit_void_test(test_shrpx_http_create_affinity_cookie),
48 munit_void_test(test_shrpx_http_create_altsvc_header_value),
49 munit_void_test(test_shrpx_http_check_http_scheme),
50 munit_test_end(),
51 };
52 } // namespace
53
54 const MunitSuite http_suite{
55 "/http", tests, NULL, 1, MUNIT_SUITE_OPTION_NONE,
56 };
57
test_shrpx_http_create_forwarded(void)58 void test_shrpx_http_create_forwarded(void) {
59 BlockAllocator balloc(1024, 1024);
60
61 assert_stdsv_equal(
62 "by=\"example.com:3000\";for=\"[::1]\";host=\"www.example.com\";"
63 "proto=https"sv,
64 http::create_forwarded(
65 balloc,
66 FORWARDED_BY | FORWARDED_FOR | FORWARDED_HOST | FORWARDED_PROTO,
67 "example.com:3000"_sr, "[::1]"_sr, "www.example.com"_sr, "https"_sr));
68
69 assert_stdsv_equal("for=192.168.0.1"sv,
70 http::create_forwarded(balloc, FORWARDED_FOR, "alpha"_sr,
71 "192.168.0.1"_sr, "bravo"_sr,
72 "charlie"_sr));
73
74 assert_stdsv_equal(
75 "by=_hidden;for=\"[::1]\""sv,
76 http::create_forwarded(balloc, FORWARDED_BY | FORWARDED_FOR, "_hidden"_sr,
77 "[::1]"_sr, ""_sr, ""_sr));
78
79 assert_stdsv_equal(
80 "by=\"[::1]\";for=_hidden"sv,
81 http::create_forwarded(balloc, FORWARDED_BY | FORWARDED_FOR, "[::1]"_sr,
82 "_hidden"_sr, ""_sr, ""_sr));
83
84 assert_stdsv_equal(""sv, http::create_forwarded(balloc,
85 FORWARDED_BY | FORWARDED_FOR |
86 FORWARDED_HOST |
87 FORWARDED_PROTO,
88 ""_sr, ""_sr, ""_sr, ""_sr));
89 }
90
test_shrpx_http_create_via_header_value(void)91 void test_shrpx_http_create_via_header_value(void) {
92 std::array<char, 16> buf;
93
94 auto end = http::create_via_header_value(std::begin(buf), 1, 1);
95
96 assert_stdstring_equal("1.1 nghttpx", (std::string{std::begin(buf), end}));
97
98 std::fill(std::begin(buf), std::end(buf), '\0');
99
100 end = http::create_via_header_value(std::begin(buf), 2, 0);
101
102 assert_stdstring_equal("2 nghttpx", (std::string{std::begin(buf), end}));
103 }
104
test_shrpx_http_create_affinity_cookie(void)105 void test_shrpx_http_create_affinity_cookie(void) {
106 BlockAllocator balloc(1024, 1024);
107 StringRef c;
108
109 c = http::create_affinity_cookie(balloc, "cookie-val"_sr, 0xf1e2d3c4u,
110 StringRef{}, false);
111
112 assert_stdsv_equal("cookie-val=f1e2d3c4"sv, c);
113
114 c = http::create_affinity_cookie(balloc, "alpha"_sr, 0x00000000u, StringRef{},
115 true);
116
117 assert_stdsv_equal("alpha=00000000; Secure"sv, c);
118
119 c = http::create_affinity_cookie(balloc, "bravo"_sr, 0x01111111u, "bar"_sr,
120 false);
121
122 assert_stdsv_equal("bravo=01111111; Path=bar"sv, c);
123
124 c = http::create_affinity_cookie(balloc, "charlie"_sr, 0x01111111u, "bar"_sr,
125 true);
126
127 assert_stdsv_equal("charlie=01111111; Path=bar; Secure"sv, c);
128 }
129
test_shrpx_http_create_altsvc_header_value(void)130 void test_shrpx_http_create_altsvc_header_value(void) {
131 {
132 BlockAllocator balloc(1024, 1024);
133 std::vector<AltSvc> altsvcs{
134 AltSvc{
135 .protocol_id = "h3"_sr,
136 .host = "127.0.0.1"_sr,
137 .service = "443"_sr,
138 .params = "ma=3600"_sr,
139 },
140 };
141
142 assert_stdsv_equal(R"(h3="127.0.0.1:443"; ma=3600)"sv,
143 http::create_altsvc_header_value(balloc, altsvcs));
144 }
145
146 {
147 BlockAllocator balloc(1024, 1024);
148 std::vector<AltSvc> altsvcs{
149 AltSvc{
150 .protocol_id = "h3"_sr,
151 .service = "443"_sr,
152 .params = "ma=3600"_sr,
153 },
154 AltSvc{
155 .protocol_id = "h3%"_sr,
156 .host = "\"foo\""_sr,
157 .service = "4433"_sr,
158 },
159 };
160
161 assert_stdsv_equal(R"(h3=":443"; ma=3600, h3%25="\"foo\":4433")"sv,
162 http::create_altsvc_header_value(balloc, altsvcs));
163 }
164 }
165
166 void test_shrpx_http_check_http_scheme(void) {
167 assert_true(http::check_http_scheme("https"_sr, true));
168 assert_false(http::check_http_scheme("https"_sr, false));
169 assert_false(http::check_http_scheme("http"_sr, true));
170 assert_true(http::check_http_scheme("http"_sr, false));
171 assert_false(http::check_http_scheme("foo"_sr, true));
172 assert_false(http::check_http_scheme("foo"_sr, false));
173 assert_false(http::check_http_scheme(StringRef{}, true));
174 assert_false(http::check_http_scheme(StringRef{}, false));
175 }
176
177 } // namespace shrpx
178