blob: 281abd07ce213d726b1961d117f9838302c030f9 [file] [log] [blame]
Austin Schuh812d0d12021-11-04 20:16:48 -07001// Copyright (c) FIRST and other WPILib contributors.
2// Open Source Software; you can modify and/or share it under the terms of
3// the WPILib BSD license file in the root directory of this project.
Brian Silverman8fce7482020-01-05 13:18:21 -08004
5#include "wpi/HttpParser.h" // NOLINT(build/include_order)
6
7#include "gtest/gtest.h"
8
9namespace wpi {
10
11TEST(HttpParserTest, UrlMethodHeadersComplete) {
12 HttpParser p{HttpParser::kRequest};
13 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -070014 p.url.connect([&](std::string_view path) {
Brian Silverman8fce7482020-01-05 13:18:21 -080015 ASSERT_EQ(path, "/foo/bar");
16 ASSERT_EQ(p.GetUrl(), "/foo/bar");
17 ++callbacks;
18 });
19 p.Execute("GET /foo");
20 p.Execute("/bar");
21 ASSERT_EQ(callbacks, 0);
22 p.Execute(" HTTP/1.1\r\n\r\n");
23 ASSERT_EQ(callbacks, 1);
24 ASSERT_EQ(p.GetUrl(), "/foo/bar");
25 ASSERT_EQ(p.GetMethod(), HTTP_GET);
26 ASSERT_FALSE(p.HasError());
27}
28
29TEST(HttpParserTest, UrlMethodHeader) {
30 HttpParser p{HttpParser::kRequest};
31 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -070032 p.url.connect([&](std::string_view path) {
Brian Silverman8fce7482020-01-05 13:18:21 -080033 ASSERT_EQ(path, "/foo/bar");
34 ASSERT_EQ(p.GetUrl(), "/foo/bar");
35 ++callbacks;
36 });
37 p.Execute("GET /foo");
38 p.Execute("/bar");
39 ASSERT_EQ(callbacks, 0);
40 p.Execute(" HTTP/1.1\r\n");
41 ASSERT_EQ(callbacks, 0);
42 p.Execute("F");
43 ASSERT_EQ(callbacks, 1);
44 ASSERT_EQ(p.GetUrl(), "/foo/bar");
45 ASSERT_EQ(p.GetMethod(), HTTP_GET);
46 ASSERT_FALSE(p.HasError());
47}
48
49TEST(HttpParserTest, StatusHeadersComplete) {
50 HttpParser p{HttpParser::kResponse};
51 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -070052 p.status.connect([&](std::string_view status) {
Brian Silverman8fce7482020-01-05 13:18:21 -080053 ASSERT_EQ(status, "OK");
54 ASSERT_EQ(p.GetStatusCode(), 200u);
55 ++callbacks;
56 });
57 p.Execute("HTTP/1.1 200");
58 p.Execute(" OK");
59 ASSERT_EQ(callbacks, 0);
60 p.Execute("\r\n\r\n");
61 ASSERT_EQ(callbacks, 1);
62 ASSERT_EQ(p.GetStatusCode(), 200u);
63 ASSERT_FALSE(p.HasError());
64}
65
66TEST(HttpParserTest, StatusHeader) {
67 HttpParser p{HttpParser::kResponse};
68 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -070069 p.status.connect([&](std::string_view status) {
Brian Silverman8fce7482020-01-05 13:18:21 -080070 ASSERT_EQ(status, "OK");
71 ASSERT_EQ(p.GetStatusCode(), 200u);
72 ++callbacks;
73 });
74 p.Execute("HTTP/1.1 200");
75 p.Execute(" OK\r\n");
76 ASSERT_EQ(callbacks, 0);
77 p.Execute("F");
78 ASSERT_EQ(callbacks, 1);
79 ASSERT_EQ(p.GetStatusCode(), 200u);
80 ASSERT_FALSE(p.HasError());
81}
82
83TEST(HttpParserTest, HeaderFieldComplete) {
84 HttpParser p{HttpParser::kRequest};
85 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -070086 p.header.connect([&](std::string_view name, std::string_view value) {
Brian Silverman8fce7482020-01-05 13:18:21 -080087 ASSERT_EQ(name, "Foo");
88 ASSERT_EQ(value, "Bar");
89 ++callbacks;
90 });
91 p.Execute("GET / HTTP/1.1\r\n");
92 ASSERT_EQ(callbacks, 0);
93 p.Execute("Fo");
94 ASSERT_EQ(callbacks, 0);
95 p.Execute("o: ");
96 ASSERT_EQ(callbacks, 0);
97 p.Execute("Bar");
98 ASSERT_EQ(callbacks, 0);
99 p.Execute("\r\n");
100 ASSERT_EQ(callbacks, 0);
101 p.Execute("\r\n");
102 ASSERT_EQ(callbacks, 1);
103 ASSERT_FALSE(p.HasError());
104}
105
106TEST(HttpParserTest, HeaderFieldNext) {
107 HttpParser p{HttpParser::kRequest};
108 int callbacks = 0;
Austin Schuh812d0d12021-11-04 20:16:48 -0700109 p.header.connect([&](std::string_view name, std::string_view value) {
Brian Silverman8fce7482020-01-05 13:18:21 -0800110 ASSERT_EQ(name, "Foo");
111 ASSERT_EQ(value, "Bar");
112 ++callbacks;
113 });
114 p.Execute("GET / HTTP/1.1\r\n");
115 ASSERT_EQ(callbacks, 0);
116 p.Execute("Fo");
117 ASSERT_EQ(callbacks, 0);
118 p.Execute("o: ");
119 ASSERT_EQ(callbacks, 0);
120 p.Execute("Bar");
121 ASSERT_EQ(callbacks, 0);
122 p.Execute("\r\n");
123 ASSERT_EQ(callbacks, 0);
124 p.Execute("F");
125 ASSERT_EQ(callbacks, 1);
126 ASSERT_FALSE(p.HasError());
127}
128
129TEST(HttpParserTest, HeadersComplete) {
130 HttpParser p{HttpParser::kRequest};
131 int callbacks = 0;
132 p.headersComplete.connect([&](bool keepAlive) {
133 ASSERT_EQ(keepAlive, false);
134 ++callbacks;
135 });
136 p.Execute("GET / HTTP/1.0\r\n");
137 ASSERT_EQ(callbacks, 0);
138 p.Execute("\r\n");
139 ASSERT_EQ(callbacks, 1);
140 ASSERT_FALSE(p.HasError());
141}
142
143TEST(HttpParserTest, HeadersCompleteHTTP11) {
144 HttpParser p{HttpParser::kRequest};
145 int callbacks = 0;
146 p.headersComplete.connect([&](bool keepAlive) {
147 ASSERT_EQ(keepAlive, true);
148 ++callbacks;
149 });
150 p.Execute("GET / HTTP/1.1\r\n");
151 ASSERT_EQ(callbacks, 0);
152 p.Execute("\r\n");
153 ASSERT_EQ(callbacks, 1);
154 ASSERT_FALSE(p.HasError());
155}
156
157TEST(HttpParserTest, HeadersCompleteKeepAlive) {
158 HttpParser p{HttpParser::kRequest};
159 int callbacks = 0;
160 p.headersComplete.connect([&](bool keepAlive) {
161 ASSERT_EQ(keepAlive, true);
162 ++callbacks;
163 });
164 p.Execute("GET / HTTP/1.0\r\n");
165 ASSERT_EQ(callbacks, 0);
166 p.Execute("Connection: Keep-Alive\r\n");
167 ASSERT_EQ(callbacks, 0);
168 p.Execute("\r\n");
169 ASSERT_EQ(callbacks, 1);
170 ASSERT_FALSE(p.HasError());
171}
172
173TEST(HttpParserTest, HeadersCompleteUpgrade) {
174 HttpParser p{HttpParser::kRequest};
175 int callbacks = 0;
176 p.headersComplete.connect([&](bool) {
177 ASSERT_TRUE(p.IsUpgrade());
178 ++callbacks;
179 });
180 p.Execute("GET / HTTP/1.0\r\n");
181 ASSERT_EQ(callbacks, 0);
182 p.Execute("Connection: Upgrade\r\n");
183 p.Execute("Upgrade: websocket\r\n");
184 ASSERT_EQ(callbacks, 0);
185 p.Execute("\r\n");
186 ASSERT_EQ(callbacks, 1);
187 ASSERT_FALSE(p.HasError());
188}
189
190TEST(HttpParserTest, Reset) {
191 HttpParser p{HttpParser::kRequest};
192 int callbacks = 0;
193 p.headersComplete.connect([&](bool) { ++callbacks; });
194 p.Execute("GET / HTTP/1.1\r\n");
195 ASSERT_EQ(callbacks, 0);
196 p.Execute("\r\n");
197 ASSERT_EQ(callbacks, 1);
198 p.Reset(HttpParser::kRequest);
199 p.Execute("GET / HTTP/1.1\r\n");
200 ASSERT_EQ(callbacks, 1);
201 p.Execute("\r\n");
202 ASSERT_EQ(callbacks, 2);
203 ASSERT_FALSE(p.HasError());
204}
205
206} // namespace wpi