In addition to Weibo, there is also WeChat
Please pay attention
WeChat public account
Shulou
2025-01-31 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Internet Technology >
Share
Shulou(Shulou.com)05/31 Report--
This article mainly explains "how to deal with Nginx discarding http packets". Interested friends may wish to have a look. The method introduced in this paper is simple, fast and practical.
Detailed explanation of an example of discarding http packets by nginx
The http framework discards the http request packet body and the http framework receives the packet body in the previous article, which are two methods provided by the http framework for each module of http to call, thus deciding what to do with the packet body. Whether to discard or receive is decided by the module. For example, the static resource module, if it receives a get request from the browser and requests a file, it can simply return the contents of the file to the browser. There is no need to receive packet data, and the get request will not actually have a packet. Therefore, the static resource module will call the discarded packet body function provided by the http framework to deal with packet loss.
Compared with the process of receiving the packet body, the operation of discarding the packet body is much easier, at least there is no need to store the packet body in the request_body buffer in the http structure, and there is no need to consider whether the packet body is only stored in memory or in a file. The discarded packet consists of three parts:
(1) the http module calls the ngx_http_discard_request_body function provided by the framework for the first time to do some initialization operations. For example, if all packets cannot be discarded in one operation, the read event needs to be re-registered in epoll so that packet loss can continue when scheduling execution again. Furthermore, the actual packet loss function ngx_http_read_discarded_request_body is called to discard the packet body.
(2) if all packets cannot be discarded in one operation, when the event is scheduled again, continue to receive the remaining packet data, and then discard it.
It can be seen from the figure that the packet loss process is a common function in these three processes. In other words, no matter whether the http module calls the ngx_http_discard_request_body function to start packet loss processing, or when the ngx_http_discarded_request_body_handler is responsible for discarding the remaining packet body, it will call the common packet loss function ngx_http_read_discarded_request_body to directly discard the packet body after receiving the packet body.
I. packet loss initialization process
Ngx_http_discard_request_body is a function called by the http module to discard the packet body. It is a transparent operation for the module. In other words, the module only needs to call this interface to discard the http request packet without knowing how the http framework implements this interface. Even if the framework does not discard all the packets at one time, it will lose packets again when the next scheduling is executed, but they do not know about the module.
/ / function: discard the first callback function of the http packet body. If it cannot be received and discarded at one time, the callback of the / / read event is set to ngx_http_discarded_request_body_handler ngx_int_t ngx_http_discard_request_body (ngx_http_request_t * r) {/ / the packet body to be discarded does not need to consider the timeout problem if (rev- > timer_set) {ngx_del_timer (rev) } / / if the length of the package is less than or equal to 0, it will be returned directly. Indicates that the packet body is discarded. / if the packet body has already been received, it does not need to be received at this time. In general, a get request does not have a packet, so the packet length is 0 if (r-> headers_in.content_length_n request_body) {return ngx_ok;} size = r-> header_in- > last-r-> header_in- > pos / / partial envelopes if (size) {/ / partial envelopes have not been fully received if (r-> headers_in.content_length_n > size) {r-> header_in- > pos + = size; r-> headers_in.content_length_n-= size;} else {/ / envelopes have all received r-> header_in- > pos + = (size_t) r-> headers_in.content_length_n R-> headers_in.content_length_n = 0; return ngx_ok;}} / / set the callback for subsequent read events r-> read_event_handler = ngx_http_discarded_request_body_handler; / / register the read event callback, insert it into epoll ngx_handle_read_event (rev, 0)) / / receive the packet content if (ngx_http_read_discarded_request_body (r) = = ngx_ok) {/ / indicates that the complete packet has been received, and will delay the shutdown of 0 r-> lingering_close = 0 } else {/ / indicates that multiple schedules are required to complete the operation of discarding the packet body, so add 1 to the reference count to prevent the packet body from being discarded here, while other / / events have caused the request to accidentally destroy r-> count++; / / marked as discarding the packet body r-> discard_body = 1;} return ngx_ok;}
When receiving the http request header, if the http packet body data is also received by the way, there is no need to continue to perform the remaining operations at this time. If the packet body is discarded successfully, the function returns directly. If all packets are not discarded in one schedule, the read event read_event_handler of the http request structure ngx_http_request_s is set to: ngx_http_discarded_request_body_handler. This function is responsible for discarding the remaining packets when it is scheduled next time. Therefore, ngx_http_discard_request_body will only be called by the http module for the first time.
Second, packet loss treatment
The ngx_http_read_discarded_request_body function is responsible for receiving packet data from the client and then discarding it. Therefore, for the module, it is the discarding packet operation, but for the framework, the discarding packet operation is actually receiving the packet operation, but the received packet data is not given to the module to use. Why does the frame receive the packet and then discard it directly? Isn't it superfluous. In fact, this is not the case, there is a reason for doing so. Suppose a weak client browser sends http packet data to the nginx server using a blocking method, and if the nginx framework does not receive it, it will cause the client browser to time out and not respond, causing the client browser to close the connection. Therefore, nginx's http framework first receives the packet data from the client from the kernel, but the data is useless for the module, so the received data will be discarded directly.
Equivalent to discarding the packet body static ngx_int_t ngx_http_read_discarded_request_body (ngx_http_request_t * r) {/ / the temporary buffer u_char buffer for receiving the packet body [NGX _ http_discard_buffer_size]; for ( ) {/ / have all been discarded successfully if (r-> headers_in.content_length_n = = 0) {/ / set the callback of the discarded read event, and do nothing to handle r-> read_event_handler = ngx_http_block_reading; return ngx_ok;} / / receive the packet from the kernel to the temporary buffer n = r-> connection- > recv (r-> connection, buffer, size)
Inside the function, only a temporary buffer variable is used to store each packet data received from the kernel. This data is not saved to the request_body buffer in the http request structure. Therefore, the packet data is not handed over to the http module, which is equivalent to being discarded. When all packets are received from the kernel, set the read event read_event_handler callback of the http request structure ngx_http_request_s to: ngx_http_block_reading, indicating that the data from the client is received again, then no processing is performed. Because all the packet data has been received, there is no need to pay attention to the other data from the client browser.
3. Discard the remaining packets
If ngx_http_discarded_request_body_handler is used to discard all packets in a single schedule, the function will be called to discard the remaining packets. The actual drop packet function is also called inside the function to receive the packet body and then discard the operation. The nginx server makes an optimization and sets a total timeout, after which the connection will be closed if all packets have not been discarded. This is a measure to protect the server to avoid long-term packet loss operations to occupy server resources.
/ / function: this function is called the first time that all packets are not discarded. When there is a read event later, the function is called void ngx_http_discarded_request_body_handler (ngx_http_request_t * r) {/ / to detect the delay shutdown time. If the total time exceeds lingering_time, no packet will be received, which is a total time. / / after the total timeout, connect the direct light ratio to if (r-> lingering_time) {timer = (ngx_msec_t) (r-> lingering_time-ngx_time ()); / / delayed shutdown time if (timer discard_body = 0; / / delayed shutdown switch clear 0 r-> lingering_close = 0; ngx_http_finalize_request (r, ngx_error); return }} / / discards rc = ngx_http_read_discarded_request_body (r) after receiving the packet body; / / indicates that the packet body has all discarded if (rc = = ngx_ok) {r-> discard_body = 0; / / the packet body has all received r-> lingering_close = 0; / / emptying the delay close flag ngx_http_finalize_request (r, ngx_done); return;}}
How is the function ngx_http_discarded_request_body_handler called by the event object? As analyzed in the previous article, the callback for the ngx_connection_s read event is set to ngx_http_request_handler. Therefore, when a read event occurs, the read callback of the request structure is called back. If you are not clear about the calling procedure, you can refer to:
Static void ngx_http_request_handler (ngx_event_t * ev) {/ / if read and write events occur at the same time, only write events will be triggered. Write event priority higher if (ev- > write) {r-> write_event_handler (r); / / set function ngx_http_handler to ngx_http_core_run_phases} else {r-> read_event_handler (r) / / the function ngx_http_process_request is set to ngx_http_block_reading}. At this point, I believe you have a better understanding of "what to do with Nginx discarding http packets". You might as well do it in practice. Here is the website, more related content can enter the relevant channels to inquire, follow us, continue to learn!
Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.
Views: 0
*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.
Continue with the installation of the previous hadoop.First, install zookooper1. Decompress zookoope
"Every 5-10 years, there's a rare product, a really special, very unusual product that's the most un
© 2024 shulou.com SLNews company. All rights reserved.