From: rousskov <> Date: Tue, 8 May 2007 22:46:37 +0000 (+0000) Subject: Bug #1819 fix: retry the ICAP transaction when its pconn fails. X-Git-Tag: SQUID_3_0_PRE6~12 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=9d4d7c5ea07774b4f5a01551e868aa9b2d031843;p=thirdparty%2Fsquid.git Bug #1819 fix: retry the ICAP transaction when its pconn fails. The changes in these files (all ICAP initiators) were minor, except the client side no longer bypasses failed queries for essential ICAP services because ICAPLauncher tells its initiator whether the failure is bypassable. Search src/ICAP/ICAPXaction.cc log around v1.7 for complete details of the bug #1819 fix. --- diff --git a/src/Server.h b/src/Server.h index c8f03745e5..34ce848521 100644 --- a/src/Server.h +++ b/src/Server.h @@ -1,6 +1,6 @@ /* - * $Id: Server.h,v 1.3 2007/04/06 04:50:05 rousskov Exp $ + * $Id: Server.h,v 1.4 2007/05/08 16:46:37 rousskov Exp $ * * AUTHOR: Duane Wessels * @@ -53,7 +53,6 @@ #if ICAP_CLIENT #include "ICAP/ICAPServiceRep.h" #include "ICAP/ICAPInitiator.h" -#include "ICAP/ICAPModXact.h" class ICAPAccessCheck; #endif @@ -90,8 +89,8 @@ public: virtual void icapAclCheckDone(ICAPServiceRep::Pointer) = 0; // ICAPInitiator: start an ICAP transaction and receive adapted headers. - virtual void noteIcapHeadersAdapted(); - virtual void noteIcapHeadersAborted(); + virtual void noteIcapAnswer(HttpMsg *message); + virtual void noteIcapQueryAbort(bool final); // BodyProducer: provide virgin response body to ICAP. virtual void noteMoreBodySpaceAvailable(BodyPipe &); @@ -135,7 +134,7 @@ protected: void handleAdaptedBodyProducerAborted(); void handleIcapCompleted(); - void handleIcapAborted(); + void handleIcapAborted(bool bypassable = false); #endif public: // should not be @@ -150,7 +149,7 @@ protected: #if ICAP_CLIENT BodyPipe::Pointer virginBodyDestination; // to provide virgin response body - ICAPModXact::Pointer adaptedHeadSource; // to get adapted response headers + ICAPInitiate *adaptedHeadSource; // to get adapted response headers BodyPipe::Pointer adaptedBodySource; // to consume adated response body bool icapAccessCheckPending; diff --git a/src/client_side_request.cc b/src/client_side_request.cc index 2d93cd3117..f50f6961f2 100644 --- a/src/client_side_request.cc +++ b/src/client_side_request.cc @@ -1,6 +1,6 @@ /* - * $Id: client_side_request.cc,v 1.83 2007/04/28 22:26:37 hno Exp $ + * $Id: client_side_request.cc,v 1.84 2007/05/08 16:46:37 rousskov Exp $ * * DEBUG: section 85 Client-side Request Routines * AUTHOR: Robert Collins (Originally Duane Wessels in client_side.c) @@ -258,10 +258,8 @@ ClientHttpRequest::~ClientHttpRequest() freeResources(); #if ICAP_CLIENT - if (icapHeadSource != NULL) { - icapHeadSource->noteInitiatorAborted(); - icapHeadSource = NULL; - } + announceInitiatorAbort(icapHeadSource); + if (icapBodySource != NULL) stopConsumingFrom(icapBodySource); #endif @@ -1086,17 +1084,15 @@ ClientHttpRequest::startIcap(ICAPServiceRep::Pointer service) assert(!icapHeadSource); assert(!icapBodySource); - icapHeadSource = new ICAPModXact(this, request, NULL, service); - ICAPModXact::AsyncStart(icapHeadSource.getRaw()); + icapHeadSource = initiateIcap( + new ICAPModXactLauncher(this, request, NULL, service)); return true; } void -ClientHttpRequest::noteIcapHeadersAdapted() +ClientHttpRequest::noteIcapAnswer(HttpMsg *msg) { assert(cbdataReferenceValid(this)); // indicates bug - - HttpMsg *msg = icapHeadSource->adapted.header; assert(msg); if (HttpRequest *new_req = dynamic_cast(msg)) { @@ -1133,18 +1129,18 @@ ClientHttpRequest::noteIcapHeadersAdapted() } // we are done with getting headers (but may be receiving body) - icapHeadSource = NULL; + clearIcap(icapHeadSource); if (!request_satisfaction_mode) doCallouts(); } void -ClientHttpRequest::noteIcapHeadersAborted() +ClientHttpRequest::noteIcapQueryAbort(bool final) { - icapHeadSource = NULL; + clearIcap(icapHeadSource); assert(!icapBodySource); - handleIcapFailure(); + handleIcapFailure(!final); } void @@ -1200,18 +1196,16 @@ ClientHttpRequest::noteBodyProducerAborted(BodyPipe &) } void -ClientHttpRequest::handleIcapFailure() +ClientHttpRequest::handleIcapFailure(bool bypassable) { - debugs(85,3, HERE << "handleIcapFailure"); + debugs(85,3, HERE << "handleIcapFailure(" << bypassable << ")"); const bool usedStore = storeEntry() && !storeEntry()->isEmpty(); const bool usedPipe = request->body_pipe != NULL && request->body_pipe->consumedSize() > 0; - // XXX: we must not try to recover if the ICAP service is not bypassable! - - if (!usedStore && !usedPipe) { - debugs(85, 2, "WARNING: ICAP REQMOD callout failed, proceeding with original request"); + if (bypassable && !usedStore && !usedPipe) { + debugs(85,3, HERE << "ICAP REQMOD callout failed, bypassing: " << calloutContext); if (calloutContext) doCallouts(); return; diff --git a/src/client_side_request.h b/src/client_side_request.h index 671329e0ab..e95296134c 100644 --- a/src/client_side_request.h +++ b/src/client_side_request.h @@ -1,6 +1,6 @@ /* - * $Id: client_side_request.h,v 1.27 2007/04/06 04:50:06 rousskov Exp $ + * $Id: client_side_request.h,v 1.28 2007/05/08 16:46:37 rousskov Exp $ * * * SQUID Web Proxy Cache http://www.squid-cache.org/ @@ -45,7 +45,6 @@ #if ICAP_CLIENT #include "ICAP/ICAPServiceRep.h" #include "ICAP/ICAPInitiator.h" -#include "ICAP/ICAPModXact.h" class HttpMsg; #endif @@ -163,12 +162,14 @@ private: public: bool startIcap(ICAPServiceRep::Pointer); - void handleIcapFailure(); // private but exposed for ClientRequestContext + + // private but exposed for ClientRequestContext + void handleIcapFailure(bool bypassable = false); private: // ICAPInitiator API, called by ICAPXaction - virtual void noteIcapHeadersAdapted(); - virtual void noteIcapHeadersAborted(); + virtual void noteIcapAnswer(HttpMsg *message); + virtual void noteIcapQueryAbort(bool final); // BodyConsumer API, called by BodyPipe virtual void noteMoreBodyDataAvailable(BodyPipe &); @@ -178,7 +179,7 @@ private: void endRequestSatisfaction(); private: - ICAPModXact::Pointer icapHeadSource; + ICAPInitiate *icapHeadSource; BodyPipe::Pointer icapBodySource; bool request_satisfaction_mode;