]> git.ipfire.org Git - thirdparty/squid.git/blob - src/clients/Client.h
Merge from trunk rev.13939
[thirdparty/squid.git] / src / clients / Client.h
1 /*
2 * Copyright (C) 1996-2015 The Squid Software Foundation and contributors
3 *
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
7 */
8
9 #ifndef SQUID_SRC_CLIENTS_CLIENT_H
10 #define SQUID_SRC_CLIENTS_CLIENT_H
11
12 #include "base/AsyncJob.h"
13 #include "BodyPipe.h"
14 #include "CommCalls.h"
15 #include "FwdState.h"
16 #include "StoreIOBuffer.h"
17 #if USE_ADAPTATION
18 #include "adaptation/forward.h"
19 #include "adaptation/Initiator.h"
20 #endif
21
22 class HttpMsg;
23 class HttpReply;
24
25 /**
26 * Client is a common base for classes such as HttpStateData and FtpStateData.
27 * All such classes must be able to consume request bodies from a BodyPipe
28 * or ICAP producer, adapt virgin responses using ICAP, and provide a
29 * consumer with responses.
30 */
31 class Client:
32 #if USE_ADAPTATION
33 public Adaptation::Initiator,
34 public BodyProducer,
35 #endif
36 public BodyConsumer
37 {
38
39 public:
40 Client(FwdState *);
41 virtual ~Client();
42
43 /// \return primary or "request data connection"
44 virtual const Comm::ConnectionPointer & dataConnection() const = 0;
45
46 // BodyConsumer: consume request body or adapted response body.
47 // The implementation just calls the corresponding HTTP or ICAP handle*()
48 // method, depending on the pipe.
49 virtual void noteMoreBodyDataAvailable(BodyPipe::Pointer);
50 virtual void noteBodyProductionEnded(BodyPipe::Pointer);
51 virtual void noteBodyProducerAborted(BodyPipe::Pointer);
52
53 /// read response data from the network
54 virtual void maybeReadVirginBody() = 0;
55
56 /// abnormal transaction termination; reason is for debugging only
57 virtual void abortTransaction(const char *reason) = 0;
58
59 /// a hack to reach HttpStateData::orignal_request
60 virtual HttpRequest *originalRequest();
61
62 #if USE_ADAPTATION
63 // Adaptation::Initiator API: start an ICAP transaction and receive adapted headers.
64 virtual void noteAdaptationAnswer(const Adaptation::Answer &answer);
65 virtual void noteAdaptationAclCheckDone(Adaptation::ServiceGroupPointer group);
66
67 // BodyProducer: provide virgin response body to ICAP.
68 virtual void noteMoreBodySpaceAvailable(BodyPipe::Pointer );
69 virtual void noteBodyConsumerAborted(BodyPipe::Pointer );
70 #endif
71 virtual bool getMoreRequestBody(MemBuf &buf);
72 virtual void processReplyBody() = 0;
73
74 //AsyncJob virtual methods
75 virtual void swanSong();
76 virtual bool doneAll() const;
77
78 public: // should be protected
79 void serverComplete(); /**< call when no server communication is expected */
80
81 private:
82 void serverComplete2(); /**< Continuation of serverComplete */
83 bool completed; /**< serverComplete() has been called */
84
85 protected:
86 // kids customize these
87 virtual void haveParsedReplyHeaders(); /**< called when got final headers */
88 virtual void completeForwarding(); /**< default calls fwd->complete() */
89
90 // BodyConsumer for HTTP: consume request body.
91 bool startRequestBodyFlow();
92 void handleMoreRequestBodyAvailable();
93 void handleRequestBodyProductionEnded();
94 virtual void handleRequestBodyProducerAborted() = 0;
95
96 // sending of the request body to the server
97 void sendMoreRequestBody();
98 // has body; kids overwrite to increment I/O stats counters
99 virtual void sentRequestBody(const CommIoCbParams &io) = 0;
100 virtual void doneSendingRequestBody() = 0;
101
102 virtual void closeServer() = 0; /**< end communication with the server */
103 virtual bool doneWithServer() const = 0; /**< did we end communication? */
104 /// whether we may receive more virgin response body bytes
105 virtual bool mayReadVirginReplyBody() const = 0;
106
107 /// Entry-dependent callbacks use this check to quit if the entry went bad
108 bool abortOnBadEntry(const char *abortReason);
109
110 bool blockCaching();
111
112 #if USE_ADAPTATION
113 void startAdaptation(const Adaptation::ServiceGroupPointer &group, HttpRequest *cause);
114 void adaptVirginReplyBody(const char *buf, ssize_t len);
115 void cleanAdaptation();
116 virtual bool doneWithAdaptation() const; /**< did we end ICAP communication? */
117
118 // BodyConsumer for ICAP: consume adapted response body.
119 void handleMoreAdaptedBodyAvailable();
120 void handleAdaptedBodyProductionEnded();
121 void handleAdaptedBodyProducerAborted();
122
123 void handleAdaptedHeader(HttpMsg *msg);
124 void handleAdaptationCompleted();
125 void handleAdaptationBlocked(const Adaptation::Answer &answer);
126 void handleAdaptationAborted(bool bypassable = false);
127
128 /// called by StoreEntry when it has more buffer space available
129 void resumeBodyStorage();
130 /// called when the entire adapted response body is consumed
131 void endAdaptedBodyConsumption();
132 #endif
133
134 protected:
135 const HttpReply *virginReply() const;
136 HttpReply *virginReply();
137 HttpReply *setVirginReply(HttpReply *r);
138
139 HttpReply *finalReply();
140 HttpReply *setFinalReply(HttpReply *r);
141
142 // Kids use these to stuff data into the response instead of messing with the entry directly
143 void adaptOrFinalizeReply();
144 void addVirginReplyBody(const char *buf, ssize_t len);
145 void storeReplyBody(const char *buf, ssize_t len);
146 /// \deprecated use SBuf I/O API and calcBufferSpaceToReserve() instead
147 size_t replyBodySpace(const MemBuf &readBuf, const size_t minSpace) const;
148 /// determine how much space the buffer needs to reserve
149 size_t calcBufferSpaceToReserve(const size_t space, const size_t wantSpace) const;
150
151 void adjustBodyBytesRead(const int64_t delta);
152
153 // These should be private
154 int64_t currentOffset; /**< Our current offset in the StoreEntry */
155 MemBuf *responseBodyBuffer; /**< Data temporarily buffered for ICAP */
156
157 public: // should not be
158 StoreEntry *entry;
159 FwdState::Pointer fwd;
160 HttpRequest *request;
161
162 protected:
163 BodyPipe::Pointer requestBodySource; /**< to consume request body */
164 AsyncCall::Pointer requestSender; /**< set if we are expecting Comm::Write to call us back */
165
166 #if USE_ADAPTATION
167 BodyPipe::Pointer virginBodyDestination; /**< to provide virgin response body */
168 CbcPointer<Adaptation::Initiate> adaptedHeadSource; /**< to get adapted response headers */
169 BodyPipe::Pointer adaptedBodySource; /**< to consume adated response body */
170
171 bool adaptationAccessCheckPending;
172 bool startedAdaptation;
173 #endif
174 bool receivedWholeRequestBody; ///< handleRequestBodyProductionEnded called
175
176 private:
177 void sendBodyIsTooLargeError();
178 void maybePurgeOthers();
179
180 HttpReply *theVirginReply; /**< reply received from the origin server */
181 HttpReply *theFinalReply; /**< adapted reply from ICAP or virgin reply */
182 };
183
184 #endif /* SQUID_SRC_CLIENTS_CLIENT_H */
185