1use crate::*;
2
3impl std::error::Error for RequestError {}
5
6impl Display for RequestError {
8 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
9 match self {
10 Self::HttpRead(status) => write!(f, "Http read error [{}]", status.code()),
11 Self::GetTcpStream(status) => write!(f, "Failed to get tcp stream [{}]", status.code()),
12 Self::GetTlsStream(status) => write!(f, "Failed to get tls stream [{}]", status.code()),
13 Self::ReadConnection(status) => write!(f, "Connection read error [{}]", status.code()),
14 Self::RequestAborted(status) => write!(f, "Request aborted [{}]", status.code()),
15 Self::TlsStreamConnect(status) => {
16 write!(f, "Tls stream connection error [{}]", status.code())
17 }
18 Self::NeedOpenRedirect(status) => {
19 write!(f, "Open redirect required [{}]", status.code())
20 }
21 Self::MaxRedirectTimes(status) => {
22 write!(f, "Exceeded maximum redirect attempts [{}]", status.code())
23 }
24 Self::MethodsNotSupport(status) => {
25 write!(f, "Http method not supported [{}]", status.code())
26 }
27 Self::RedirectInvalidUrl(status) => {
28 write!(f, "Invalid redirect url [{}]", status.code())
29 }
30 Self::ClientDisconnected(status) => {
31 write!(f, "Client disconnected [{}]", status.code())
32 }
33 Self::RedirectUrlDeadLoop(status) => {
34 write!(f, "Redirect url dead loop detected [{}]", status.code())
35 }
36 Self::ClientClosedConnection(status) => {
37 write!(f, "Client closed connection [{}]", status.code())
38 }
39 Self::IncompleteWebSocketFrame(status) => write!(
40 f,
41 "WebSocket connection closed before a complete frame was received [{}]",
42 status.code()
43 ),
44 Self::RequestTooLong(status) => write!(f, "Request line too long [{}]", status.code()),
45 Self::PathTooLong(status) => write!(f, "Path too long [{}]", status.code()),
46 Self::QueryTooLong(status) => write!(f, "Query string too long [{}]", status.code()),
47 Self::HeaderLineTooLong(status) => {
48 write!(f, "Header line too long [{}]", status.code())
49 }
50 Self::TooManyHeaders(status) => write!(f, "Too many headers [{}]", status.code()),
51 Self::HeaderKeyTooLong(status) => write!(f, "Header key too long [{}]", status.code()),
52 Self::HeaderValueTooLong(status) => {
53 write!(f, "Header value too long [{}]", status.code())
54 }
55 Self::ContentLengthTooLarge(status) => {
56 write!(f, "Content length too large [{}]", status.code())
57 }
58 Self::InvalidContentLength(status) => {
59 write!(f, "Invalid content length [{}]", status.code())
60 }
61 Self::InvalidUrlScheme(status) => write!(f, "Invalid URL scheme [{}]", status.code()),
62 Self::InvalidUrlHost(status) => write!(f, "Invalid URL host [{}]", status.code()),
63 Self::InvalidUrlPort(status) => write!(f, "Invalid URL port [{}]", status.code()),
64 Self::InvalidUrlPath(status) => write!(f, "Invalid URL path [{}]", status.code()),
65 Self::InvalidUrlQuery(status) => write!(f, "Invalid URL query [{}]", status.code()),
66 Self::InvalidUrlFragment(status) => {
67 write!(f, "Invalid URL fragment [{}]", status.code())
68 }
69 Self::ReadTimeoutNotSet(status) => {
70 write!(f, "Failed to set read timeout [{}]", status.code())
71 }
72 Self::WriteTimeoutNotSet(status) => {
73 write!(f, "Failed to set write timeout [{}]", status.code())
74 }
75 Self::TcpConnectionFailed(status) => {
76 write!(f, "Tcp connection failed [{}]", status.code())
77 }
78 Self::TlsHandshakeFailed(status) => {
79 write!(f, "Tls handshake failed [{}]", status.code())
80 }
81 Self::TlsCertificateInvalid(status) => {
82 write!(f, "Tls certificate invalid [{}]", status.code())
83 }
84 Self::WebSocketFrameTooLarge(status) => {
85 write!(f, "WebSocket frame too large [{}]", status.code())
86 }
87 Self::WebSocketOpcodeUnsupported(status) => {
88 write!(f, "WebSocket opcode unsupported [{}]", status.code())
89 }
90 Self::WebSocketMaskMissing(status) => {
91 write!(f, "WebSocket mask missing [{}]", status.code())
92 }
93 Self::WebSocketPayloadCorrupted(status) => {
94 write!(f, "WebSocket payload corrupted [{}]", status.code())
95 }
96 Self::WebSocketInvalidUtf8(status) => {
97 write!(f, "WebSocket invalid UTF-8 [{}]", status.code())
98 }
99 Self::WebSocketInvalidCloseCode(status) => {
100 write!(f, "WebSocket invalid close code [{}]", status.code())
101 }
102 Self::WebSocketInvalidExtension(status) => {
103 write!(f, "WebSocket invalid extension [{}]", status.code())
104 }
105 Self::HttpRequestPartsInsufficient(status) => {
106 write!(f, "HTTP request parts insufficient [{}]", status.code())
107 }
108 Self::TcpStreamConnect(status) => {
109 write!(f, "TCP stream connection error [{}]", status.code())
110 }
111 Self::TlsConnectorBuild(status) => {
112 write!(f, "TLS connector build error [{}]", status.code())
113 }
114 Self::InvalidUrl(status) => {
115 write!(f, "Invalid URL error [{}]", status.code())
116 }
117 Self::SetReadTimeout(status) => {
118 write!(f, "Set read timeout error [{}]", status.code())
119 }
120 Self::SetWriteTimeout(status) => {
121 write!(f, "Set write timeout error [{}]", status.code())
122 }
123 Self::ConfigReadError(status) => {
124 write!(f, "Configuration read error [{}]", status.code())
125 }
126 Self::TcpStreamConnectString(status) => {
127 write!(f, "TCP stream connection error [{}]", status.code())
128 }
129 Self::TlsConnectorBuildString(status) => {
130 write!(f, "TLS connector build error [{}]", status.code())
131 }
132 Self::SetReadTimeoutString(status) => {
133 write!(f, "Set read timeout error [{}]", status.code())
134 }
135 Self::SetWriteTimeoutString(status) => {
136 write!(f, "Set write timeout error [{}]", status.code())
137 }
138 Self::Unknown(status) => write!(f, "Unknown error occurred [{}]", status.code()),
139 }
140 }
141}
142
143impl RequestError {
144 #[inline(always)]
156 pub fn get_http_status(&self) -> HttpStatus {
157 match self {
158 Self::HttpRead(status) => *status,
159 Self::GetTcpStream(status) => *status,
160 Self::GetTlsStream(status) => *status,
161 Self::ReadConnection(status) => *status,
162 Self::RequestAborted(status) => *status,
163 Self::TlsStreamConnect(status) => *status,
164 Self::NeedOpenRedirect(status) => *status,
165 Self::MaxRedirectTimes(status) => *status,
166 Self::MethodsNotSupport(status) => *status,
167 Self::RedirectInvalidUrl(status) => *status,
168 Self::ClientDisconnected(status) => *status,
169 Self::RedirectUrlDeadLoop(status) => *status,
170 Self::ClientClosedConnection(status) => *status,
171 Self::IncompleteWebSocketFrame(status) => *status,
172 Self::RequestTooLong(status) => *status,
173 Self::PathTooLong(status) => *status,
174 Self::QueryTooLong(status) => *status,
175 Self::HeaderLineTooLong(status) => *status,
176 Self::TooManyHeaders(status) => *status,
177 Self::HeaderKeyTooLong(status) => *status,
178 Self::HeaderValueTooLong(status) => *status,
179 Self::ContentLengthTooLarge(status) => *status,
180 Self::InvalidContentLength(status) => *status,
181 Self::InvalidUrlScheme(status) => *status,
182 Self::InvalidUrlHost(status) => *status,
183 Self::InvalidUrlPort(status) => *status,
184 Self::InvalidUrlPath(status) => *status,
185 Self::InvalidUrlQuery(status) => *status,
186 Self::InvalidUrlFragment(status) => *status,
187 Self::ReadTimeoutNotSet(status) => *status,
188 Self::WriteTimeoutNotSet(status) => *status,
189 Self::TcpConnectionFailed(status) => *status,
190 Self::TlsHandshakeFailed(status) => *status,
191 Self::TlsCertificateInvalid(status) => *status,
192 Self::WebSocketFrameTooLarge(status) => *status,
193 Self::WebSocketOpcodeUnsupported(status) => *status,
194 Self::WebSocketMaskMissing(status) => *status,
195 Self::WebSocketPayloadCorrupted(status) => *status,
196 Self::WebSocketInvalidUtf8(status) => *status,
197 Self::WebSocketInvalidCloseCode(status) => *status,
198 Self::WebSocketInvalidExtension(status) => *status,
199 Self::HttpRequestPartsInsufficient(status) => *status,
200 Self::TcpStreamConnect(status) => *status,
201 Self::TlsConnectorBuild(status) => *status,
202 Self::InvalidUrl(status) => *status,
203 Self::SetReadTimeout(status) => *status,
204 Self::SetWriteTimeout(status) => *status,
205 Self::ConfigReadError(status) => *status,
206 Self::TcpStreamConnectString(status) => *status,
207 Self::TlsConnectorBuildString(status) => *status,
208 Self::SetReadTimeoutString(status) => *status,
209 Self::SetWriteTimeoutString(status) => *status,
210 Self::Unknown(status) => *status,
211 }
212 }
213
214 pub fn get_http_status_code(&self) -> ResponseStatusCode {
226 self.get_http_status().code()
227 }
228}
229
230impl Default for RequestConfig {
231 #[inline(always)]
237 fn default() -> Self {
238 Self {
239 buffer_size: DEFAULT_BUFFER_SIZE,
240 max_request_line_length: DEFAULT_MAX_REQUEST_LINE_LENGTH,
241 max_path_length: DEFAULT_MAX_PATH_LENGTH,
242 max_query_length: DEFAULT_MAX_QUERY_LENGTH,
243 max_header_line_length: DEFAULT_MAX_HEADER_LINE_LENGTH,
244 max_header_count: DEFAULT_MAX_HEADER_COUNT,
245 max_header_key_length: DEFAULT_MAX_HEADER_KEY_LENGTH,
246 max_header_value_length: DEFAULT_MAX_HEADER_VALUE_LENGTH,
247 max_body_size: DEFAULT_MAX_BODY_SIZE,
248 max_ws_frame_size: DEFAULT_MAX_WS_FRAME_SIZE,
249 max_ws_frames: DEFAULT_MAX_WS_FRAMES,
250 http_read_timeout_ms: DEFAULT_HTTP_READ_TIMEOUT_MS,
251 ws_read_timeout_ms: DEFAULT_WS_READ_TIMEOUT_MS,
252 }
253 }
254}
255
256impl RequestConfig {
257 #[inline(always)]
263 pub fn new() -> Self {
264 Self::default()
265 }
266
267 #[inline(always)]
276 pub fn high_security() -> Self {
277 Self {
278 buffer_size: DEFAULT_HIGH_SECURITY_BUFFER_SIZE,
279 max_request_line_length: DEFAULT_HIGH_SECURITY_MAX_REQUEST_LINE_LENGTH,
280 max_path_length: DEFAULT_HIGH_SECURITY_MAX_PATH_LENGTH,
281 max_query_length: DEFAULT_HIGH_SECURITY_MAX_QUERY_LENGTH,
282 max_header_line_length: DEFAULT_HIGH_SECURITY_MAX_HEADER_LINE_LENGTH,
283 max_header_count: DEFAULT_HIGH_SECURITY_MAX_HEADER_COUNT,
284 max_header_key_length: DEFAULT_HIGH_SECURITY_MAX_HEADER_KEY_LENGTH,
285 max_header_value_length: DEFAULT_HIGH_SECURITY_MAX_HEADER_VALUE_LENGTH,
286 max_body_size: DEFAULT_HIGH_SECURITY_MAX_BODY_SIZE,
287 max_ws_frame_size: DEFAULT_HIGH_SECURITY_MAX_WS_FRAME_SIZE,
288 max_ws_frames: DEFAULT_HIGH_SECURITY_MAX_WS_FRAMES,
289 http_read_timeout_ms: DEFAULT_HIGH_SECURITY_HTTP_READ_TIMEOUT_MS,
290 ws_read_timeout_ms: DEFAULT_HIGH_SECURITY_WS_READ_TIMEOUT_MS,
291 }
292 }
293}
294
295impl Default for Request {
299 #[inline(always)]
300 fn default() -> Self {
301 Self {
302 method: Method::default(),
303 host: String::new(),
304 version: HttpVersion::default(),
305 path: String::new(),
306 querys: hash_map_xx_hash3_64(),
307 headers: hash_map_xx_hash3_64(),
308 body: Vec::new(),
309 }
310 }
311}
312
313impl Request {
314 #[inline(always)]
320 pub fn new() -> Self {
321 Self::default()
322 }
323
324 pub async fn http_from_stream(
337 stream: &ArcRwLockStream,
338 config: &RequestConfig,
339 ) -> Result<Request, RequestError> {
340 let mut buf_stream: RwLockWriteGuard<'_, TcpStream> = stream.write().await;
341 let buffer_size: usize = *config.get_buffer_size();
342 let reader: &mut BufReader<&mut TcpStream> =
343 &mut BufReader::with_capacity(buffer_size, &mut buf_stream);
344 let mut request_line: String = String::with_capacity(buffer_size);
345 let timeout_duration: Duration = Duration::from_millis(config.http_read_timeout_ms);
346 let bytes_read: usize = timeout(
347 timeout_duration,
348 AsyncBufReadExt::read_line(reader, &mut request_line),
349 )
350 .await
351 .map_err(|_| RequestError::ReadTimeoutNotSet(HttpStatus::RequestTimeout))?
352 .map_err(|_| RequestError::HttpRead(HttpStatus::BadRequest))?;
353 if bytes_read > config.max_request_line_length {
354 return Err(RequestError::RequestTooLong(HttpStatus::BadRequest));
355 }
356 let parts: Vec<&str> = request_line.split_whitespace().collect();
357 let parts_len: usize = parts.len();
358 if parts_len < 3 {
359 return Err(RequestError::HttpRequestPartsInsufficient(
360 HttpStatus::BadRequest,
361 ));
362 }
363 let full_path: &str = parts[1];
364 if full_path.len() > config.max_path_length {
365 return Err(RequestError::PathTooLong(HttpStatus::URITooLong));
366 }
367 let method: RequestMethod = parts[0]
368 .parse::<RequestMethod>()
369 .unwrap_or(Method::Unknown(parts[0].to_string()));
370 let full_path: RequestPath = full_path.to_string();
371 let version: RequestVersion = parts[2]
372 .parse::<RequestVersion>()
373 .unwrap_or(RequestVersion::Unknown(parts[2].to_string()));
374 let hash_index: Option<usize> = full_path.find(HASH);
375 let query_index: Option<usize> = full_path.find(QUERY);
376 let query_string: String = query_index.map_or_else(String::new, |i| {
377 let temp: &str = &full_path[i + 1..];
378 if hash_index.is_none() || hash_index.unwrap() <= i {
379 return temp.to_owned();
380 }
381 temp.split(HASH).next().unwrap_or_default().to_owned()
382 });
383 if query_string.len() > config.max_query_length {
384 return Err(RequestError::QueryTooLong(HttpStatus::URITooLong));
385 }
386 let querys: RequestQuerys = Self::parse_querys(&query_string);
387 let path: RequestPath = if let Some(i) = query_index.or(hash_index) {
388 full_path[..i].to_owned()
389 } else {
390 full_path.to_owned()
391 };
392 let mut headers: RequestHeaders = hash_map_xx_hash3_64();
393 let mut host: RequestHost = String::new();
394 let mut content_length: usize = 0;
395 let mut header_count: usize = 0;
396 loop {
397 let header_line: &mut String = &mut String::with_capacity(buffer_size);
398 let timeout_duration: Duration = Duration::from_millis(config.http_read_timeout_ms);
399 let bytes_read: usize = timeout(
400 timeout_duration,
401 AsyncBufReadExt::read_line(reader, header_line),
402 )
403 .await
404 .map_err(|_| RequestError::ReadTimeoutNotSet(HttpStatus::RequestTimeout))?
405 .map_err(|_| RequestError::HttpRead(HttpStatus::BadRequest))?;
406 if bytes_read > config.max_header_line_length {
407 return Err(RequestError::HeaderLineTooLong(
408 HttpStatus::RequestHeaderFieldsTooLarge,
409 ));
410 }
411 let header_line: &str = header_line.trim();
412 if header_line.is_empty() {
413 break;
414 }
415 header_count += 1;
416 if header_count > config.max_header_count {
417 return Err(RequestError::TooManyHeaders(
418 HttpStatus::RequestHeaderFieldsTooLarge,
419 ));
420 }
421 if let Some((key_part, value_part)) = header_line.split_once(COLON) {
422 let key: String = key_part.trim().to_ascii_lowercase();
423 if key.is_empty() {
424 continue;
425 }
426 if key.len() > config.max_header_key_length {
427 return Err(RequestError::HeaderKeyTooLong(
428 HttpStatus::RequestHeaderFieldsTooLarge,
429 ));
430 }
431 let value: String = value_part.trim().to_string();
432 if value.len() > config.max_header_value_length {
433 return Err(RequestError::HeaderValueTooLong(
434 HttpStatus::RequestHeaderFieldsTooLarge,
435 ));
436 }
437 if key == HOST {
438 host = value.clone();
439 } else if key == CONTENT_LENGTH {
440 match value.parse::<usize>() {
441 Ok(length) => {
442 if length > config.max_body_size {
443 return Err(RequestError::ContentLengthTooLarge(
444 HttpStatus::PayloadTooLarge,
445 ));
446 }
447 content_length = length;
448 }
449 Err(_) => {
450 return Err(RequestError::InvalidContentLength(HttpStatus::BadRequest));
451 }
452 }
453 }
454 headers.entry(key).or_default().push_back(value);
455 }
456 }
457 let mut body: RequestBody = Vec::with_capacity(content_length);
458 if content_length > 0 {
459 body.resize(content_length, 0);
460 let timeout_duration: Duration = Duration::from_millis(config.http_read_timeout_ms);
461 timeout(
462 timeout_duration,
463 AsyncReadExt::read_exact(reader, &mut body),
464 )
465 .await
466 .map_err(|_| RequestError::ReadTimeoutNotSet(HttpStatus::RequestTimeout))?
467 .map_err(|_| RequestError::ReadConnection(HttpStatus::BadRequest))?;
468 }
469 Ok(Request {
470 method,
471 host,
472 version,
473 path,
474 querys,
475 headers,
476 body,
477 })
478 }
479
480 pub async fn ws_from_stream(
493 &mut self,
494 stream: &ArcRwLockStream,
495 config: &RequestConfig,
496 ) -> Result<Request, RequestError> {
497 let buffer_size: usize = *config.get_buffer_size();
498 let mut dynamic_buffer: Vec<u8> = Vec::with_capacity(buffer_size);
499 let temp_buffer_size: usize = buffer_size;
500 let mut temp_buffer: Vec<u8> = vec![0; temp_buffer_size];
501 let mut full_frame: Vec<u8> = Vec::with_capacity(config.max_ws_frame_size);
502 let mut frame_count: usize = 0;
503 let mut is_client_response: bool = false;
504 let ws_read_timeout_ms: u64 =
505 (config.ws_read_timeout_ms >> 1) + (config.ws_read_timeout_ms & 1);
506 loop {
507 let timeout_duration: Duration = Duration::from_millis(ws_read_timeout_ms);
508 let len: usize = match timeout(
509 timeout_duration,
510 stream.write().await.read(&mut temp_buffer),
511 )
512 .await
513 {
514 Ok(result) => match result {
515 Ok(len) => len,
516 Err(err) => {
517 if err.kind() == ErrorKind::ConnectionReset
518 || err.kind() == ErrorKind::ConnectionAborted
519 {
520 return Err(RequestError::ClientDisconnected(HttpStatus::BadRequest));
521 }
522 return Err(RequestError::Unknown(HttpStatus::InternalServerError));
523 }
524 },
525 Err(_) => {
526 if !is_client_response {
527 return Err(RequestError::ReadTimeoutNotSet(HttpStatus::RequestTimeout));
528 }
529 is_client_response = false;
530 stream.try_send_body(&PING_FRAME).await.map_err(|_| {
531 RequestError::WriteTimeoutNotSet(HttpStatus::InternalServerError)
532 })?;
533 let _ = stream.try_flush().await;
534 continue;
535 }
536 };
537 if len == 0 {
538 return Err(RequestError::IncompleteWebSocketFrame(
539 HttpStatus::BadRequest,
540 ));
541 }
542 dynamic_buffer.extend_from_slice(&temp_buffer[..len]);
543 while let Some((frame, consumed)) = WebSocketFrame::decode_ws_frame(&dynamic_buffer) {
544 is_client_response = true;
545 dynamic_buffer.drain(0..consumed);
546 frame_count += 1;
547 if frame_count > config.max_ws_frames {
548 return Err(RequestError::TooManyHeaders(
549 HttpStatus::RequestHeaderFieldsTooLarge,
550 ));
551 }
552 match frame.get_opcode() {
553 WebSocketOpcode::Close => {
554 return Err(RequestError::ClientClosedConnection(HttpStatus::BadRequest));
555 }
556 WebSocketOpcode::Ping | WebSocketOpcode::Pong => {
557 continue;
558 }
559 WebSocketOpcode::Text | WebSocketOpcode::Binary => {
560 let payload_data: &[u8] = frame.get_payload_data();
561 if payload_data.len() > config.max_ws_frame_size {
562 return Err(RequestError::WebSocketFrameTooLarge(
563 HttpStatus::PayloadTooLarge,
564 ));
565 }
566 if full_frame.len() + payload_data.len() > config.max_ws_frame_size {
567 return Err(RequestError::WebSocketFrameTooLarge(
568 HttpStatus::PayloadTooLarge,
569 ));
570 }
571 full_frame.extend_from_slice(payload_data);
572 if *frame.get_fin() {
573 let mut request: Request = self.clone();
574 request.body = full_frame;
575 return Ok(request);
576 }
577 }
578 _ => {
579 return Err(RequestError::WebSocketOpcodeUnsupported(
580 HttpStatus::NotImplemented,
581 ));
582 }
583 }
584 }
585 }
586 }
587
588 fn parse_querys<Q>(query: Q) -> RequestQuerys
600 where
601 Q: AsRef<str>,
602 {
603 let mut query_map: RequestQuerys = hash_map_xx_hash3_64();
604 for pair in query.as_ref().split(AND) {
605 if let Some((key, value)) = pair.split_once(EQUAL) {
606 if !key.is_empty() {
607 query_map.insert(key.to_string(), value.to_string());
608 }
609 } else if !pair.is_empty() {
610 query_map.insert(pair.to_string(), String::new());
611 }
612 }
613 query_map
614 }
615
616 #[inline(always)]
628 pub fn try_get_query<K>(&self, key: K) -> Option<RequestQuerysValue>
629 where
630 K: AsRef<str>,
631 {
632 self.querys.get(key.as_ref()).cloned()
633 }
634
635 #[inline(always)]
651 pub fn get_query<K>(&self, key: K) -> RequestQuerysValue
652 where
653 K: AsRef<str>,
654 {
655 self.try_get_query(key).unwrap()
656 }
657
658 #[inline(always)]
668 pub fn try_get_header<K>(&self, key: K) -> Option<RequestHeadersValue>
669 where
670 K: AsRef<str>,
671 {
672 self.headers.get(key.as_ref()).cloned()
673 }
674
675 #[inline(always)]
689 pub fn get_header<K>(&self, key: K) -> RequestHeadersValue
690 where
691 K: AsRef<str>,
692 {
693 self.try_get_header(key).unwrap()
694 }
695
696 #[inline(always)]
706 pub fn try_get_header_front<K>(&self, key: K) -> Option<RequestHeadersValueItem>
707 where
708 K: AsRef<str>,
709 {
710 self.headers
711 .get(key.as_ref())
712 .and_then(|values| values.front().cloned())
713 }
714
715 #[inline(always)]
729 pub fn get_header_front<K>(&self, key: K) -> RequestHeadersValueItem
730 where
731 K: AsRef<str>,
732 {
733 self.try_get_header_front(key).unwrap()
734 }
735
736 #[inline(always)]
746 pub fn try_get_header_back<K>(&self, key: K) -> Option<RequestHeadersValueItem>
747 where
748 K: AsRef<str>,
749 {
750 self.headers
751 .get(key.as_ref())
752 .and_then(|values| values.back().cloned())
753 }
754
755 #[inline(always)]
769 pub fn get_header_back<K>(&self, key: K) -> RequestHeadersValueItem
770 where
771 K: AsRef<str>,
772 {
773 self.try_get_header_back(key).unwrap()
774 }
775
776 #[inline(always)]
786 pub fn try_get_header_length<K>(&self, key: K) -> Option<usize>
787 where
788 K: AsRef<str>,
789 {
790 self.headers.get(key.as_ref()).map(|values| values.len())
791 }
792
793 #[inline(always)]
807 pub fn get_header_length<K>(&self, key: K) -> usize
808 where
809 K: AsRef<str>,
810 {
811 self.try_get_header_length(key).unwrap()
812 }
813
814 #[inline(always)]
820 pub fn get_headers_values_length(&self) -> usize {
821 self.headers.values().map(|values| values.len()).sum()
822 }
823
824 #[inline(always)]
830 pub fn get_headers_length(&self) -> usize {
831 self.headers.len()
832 }
833
834 #[inline(always)]
844 pub fn has_header<K>(&self, key: K) -> bool
845 where
846 K: AsRef<str>,
847 {
848 self.headers.contains_key(key.as_ref())
849 }
850
851 #[inline(always)]
862 pub fn has_header_value<K, V>(&self, key: K, value: V) -> bool
863 where
864 K: AsRef<str>,
865 V: AsRef<str>,
866 {
867 if let Some(values) = self.headers.get(key.as_ref()) {
868 values.contains(&value.as_ref().to_owned())
869 } else {
870 false
871 }
872 }
873
874 #[inline(always)]
883 pub fn get_body_string(&self) -> String {
884 String::from_utf8_lossy(self.get_body()).into_owned()
885 }
886
887 pub fn try_get_body_json<T>(&self) -> Result<T, serde_json::Error>
900 where
901 T: DeserializeOwned,
902 {
903 serde_json::from_slice(self.get_body())
904 }
905
906 pub fn get_body_json<T>(&self) -> T
923 where
924 T: DeserializeOwned,
925 {
926 self.try_get_body_json().unwrap()
927 }
928
929 #[inline(always)]
938 pub fn get_string(&self) -> String {
939 let body: &Vec<u8> = self.get_body();
940 let body_type: &'static str = if std::str::from_utf8(body).is_ok() {
941 PLAIN
942 } else {
943 BINARY
944 };
945 format!(
946 "[Request] => [method]: {}; [host]: {}; [version]: {}; [path]: {}; [querys]: {:?}; [headers]: {:?}; [body]: {} bytes {};",
947 self.get_method(),
948 self.get_host(),
949 self.get_version(),
950 self.get_path(),
951 self.get_querys(),
952 self.get_headers(),
953 body.len(),
954 body_type
955 )
956 }
957
958 #[inline(always)]
968 pub fn get_upgrade_type(&self) -> UpgradeType {
969 let upgrade_type: UpgradeType = self
970 .try_get_header_back(UPGRADE)
971 .and_then(|data| data.parse::<UpgradeType>().ok())
972 .unwrap_or_default();
973 upgrade_type
974 }
975
976 #[inline(always)]
984 pub fn is_ws(&self) -> bool {
985 self.get_upgrade_type().is_ws()
986 }
987
988 #[inline(always)]
994 pub fn is_h2c(&self) -> bool {
995 self.get_upgrade_type().is_h2c()
996 }
997
998 #[inline(always)]
1004 pub fn is_tls(&self) -> bool {
1005 self.get_upgrade_type().is_tls()
1006 }
1007
1008 #[inline(always)]
1014 pub fn is_unknown_upgrade(&self) -> bool {
1015 self.get_upgrade_type().is_unknown()
1016 }
1017
1018 #[inline(always)]
1024 pub fn is_http1_1_or_higher(&self) -> bool {
1025 self.get_version().is_http1_1_or_higher()
1026 }
1027
1028 #[inline(always)]
1034 pub fn is_http0_9(&self) -> bool {
1035 self.get_version().is_http0_9()
1036 }
1037
1038 #[inline(always)]
1044 pub fn is_http1_0(&self) -> bool {
1045 self.get_version().is_http1_0()
1046 }
1047
1048 #[inline(always)]
1054 pub fn is_http1_1(&self) -> bool {
1055 self.get_version().is_http1_1()
1056 }
1057
1058 #[inline(always)]
1064 pub fn is_http2(&self) -> bool {
1065 self.get_version().is_http2()
1066 }
1067
1068 #[inline(always)]
1074 pub fn is_http3(&self) -> bool {
1075 self.get_version().is_http3()
1076 }
1077
1078 #[inline(always)]
1084 pub fn is_unknown_version(&self) -> bool {
1085 self.get_version().is_unknown()
1086 }
1087
1088 #[inline(always)]
1094 pub fn is_http(&self) -> bool {
1095 self.get_version().is_http()
1096 }
1097
1098 #[inline(always)]
1104 pub fn is_get(&self) -> bool {
1105 self.get_method().is_get()
1106 }
1107
1108 #[inline(always)]
1114 pub fn is_post(&self) -> bool {
1115 self.get_method().is_post()
1116 }
1117
1118 #[inline(always)]
1124 pub fn is_put(&self) -> bool {
1125 self.get_method().is_put()
1126 }
1127
1128 #[inline(always)]
1134 pub fn is_delete(&self) -> bool {
1135 self.get_method().is_delete()
1136 }
1137
1138 #[inline(always)]
1144 pub fn is_patch(&self) -> bool {
1145 self.get_method().is_patch()
1146 }
1147
1148 #[inline(always)]
1154 pub fn is_head(&self) -> bool {
1155 self.get_method().is_head()
1156 }
1157
1158 #[inline(always)]
1164 pub fn is_options(&self) -> bool {
1165 self.get_method().is_options()
1166 }
1167
1168 #[inline(always)]
1174 pub fn is_connect(&self) -> bool {
1175 self.get_method().is_connect()
1176 }
1177
1178 #[inline(always)]
1184 pub fn is_trace(&self) -> bool {
1185 self.get_method().is_trace()
1186 }
1187
1188 #[inline(always)]
1194 pub fn is_unknown_method(&self) -> bool {
1195 self.get_method().is_unknown()
1196 }
1197
1198 #[inline(always)]
1214 pub fn is_enable_keep_alive(&self) -> bool {
1215 if let Some(connection_value) = self.try_get_header_back(CONNECTION) {
1216 if connection_value.eq_ignore_ascii_case(KEEP_ALIVE) {
1217 return true;
1218 } else if connection_value.eq_ignore_ascii_case(CLOSE) {
1219 return self.is_ws();
1220 }
1221 }
1222 self.is_http1_1_or_higher() || self.is_ws()
1223 }
1224
1225 #[inline(always)]
1231 pub fn is_disable_keep_alive(&self) -> bool {
1232 !self.is_enable_keep_alive()
1233 }
1234}