Graham Dumpleton
grahamd at dscpl.com.au
Thu Jan 25 04:49:16 EST 2007
Actually, there is another interesting way one can stop it without resorting to specific status values. Ie., can be done for OK response as well. That is: && (!apr_table_get(r->subprocess_env, "nokeepalive") In other words, in your request handler have: req.subprocess_env["nokeepalive"] = "1" Graham On 25/01/2007, at 8:37 PM, Graham Dumpleton wrote: > > On 25/01/2007, at 8:14 PM, export at hope.cz wrote: > >> Graham and Mike >> Thank you for help and some explanation about my question. >> Mike you say:"It is good practice to send a "Connection: Close" >> header along with your >> error response", >> But how shall I send that?Can you please send detail? >> Thank you again for help > > Probably simpler to return an error status of HTTP_BAD_REQUEST. This > is one of the error status values which is guaranteed to always > result in the > connection being closed even if keep alive was requested. There are > others > which do the same, but I guess it depends on what one classifies a > request > to upload an unsupported file type as. > > Overall the logic for determining if keep alive is maintained is > quite convoluted. > > #define ap_status_drops_connection(x) \ > (((x) == > HTTP_BAD_REQUEST) || \ > ((x) == > HTTP_REQUEST_TIME_OUT) || \ > ((x) == > HTTP_LENGTH_REQUIRED) || \ > ((x) == > HTTP_REQUEST_ENTITY_TOO_LARGE) || \ > ((x) == > HTTP_REQUEST_URI_TOO_LARGE) || \ > ((x) == > HTTP_INTERNAL_SERVER_ERROR) || \ > ((x) == > HTTP_SERVICE_UNAVAILABLE) || \ > ((x) == HTTP_NOT_IMPLEMENTED)) > > /* The following convoluted conditional determines whether or not > * the current connection should remain persistent after this > response > * (a.k.a. HTTP Keep-Alive) and whether or not the output message > * body should use the HTTP/1.1 chunked transfer-coding. In > English, > * > * IF we have not marked this connection as errored; > * and the response body has a defined length due to the > status code > * being 304 or 204, the request method being HEAD, already > * having defined Content-Length or Transfer-Encoding: > chunked, or > * the request version being HTTP/1.1 and thus capable of > being set > * as chunked [we know the (r->chunked = 1) side-effect > is ugly]; > * and the server configuration enables keep-alive; > * and the server configuration has a reasonable inter- > request timeout; > * and there is no maximum # requests or the max hasn't been > reached; > * and the response status does not require a close; > * and the response generator has not already indicated close; > * and the client did not request non-persistence > (Connection: close); > * and we haven't been configured to ignore the buggy twit > * or they're a buggy twit coming through a HTTP/1.1 proxy > * and the client is requesting an HTTP/1.0-style keep-alive > * or the client claims to be HTTP/1.1 compliant (perhaps > a proxy); > * THEN we can be persistent, which requires more headers be > output. > * > * Note that the condition evaluation order is extremely > important. > */ > > if ((r->connection->keepalive != AP_CONN_CLOSE) > && ((r->status == HTTP_NOT_MODIFIED) > || (r->status == HTTP_NO_CONTENT) > || r->header_only > || apr_table_get(r->headers_out, "Content-Length") > || ap_find_last_token(r->pool, > apr_table_get(r->headers_out, > "Transfer-Encoding"), > "chunked") > || ((r->proto_num >= HTTP_VERSION(1,1)) > && (r->chunked = 1))) /* THIS CODE IS CORRECT, see > above. */ > && r->server->keep_alive > && (r->server->keep_alive_timeout > 0) > && ((r->server->keep_alive_max == 0) > || (r->server->keep_alive_max > r->connection- > >keepalives)) > && !ap_status_drops_connection(r->status) > && !wimpy > && !ap_find_token(r->pool, conn, "close") > && (!apr_table_get(r->subprocess_env, "nokeepalive") > || apr_table_get(r->headers_in, "Via")) > && ((ka_sent = ap_find_token(r->pool, conn, "keep-alive")) > || (r->proto_num >= HTTP_VERSION(1,1)))) { > int left = r->server->keep_alive_max - r->connection- > >keepalives; > > r->connection->keepalive = AP_CONN_KEEPALIVE; > r->connection->keepalives++; > > _______________________________________________ > Mod_python mailing list > Mod_python at modpython.org > http://mailman.modpython.org/mailman/listinfo/mod_python
|