void HttpClient::proxyConnect(PNetworkStream stream, ConstStrA host, ConstStrA authorization) { if (host.find(':') == naturalNull) { return proxyConnect(stream,StringA(host+ConstStrA(":443")),authorization); } PNetworkStream nstream = new BufferedNetworkStream(stream); HttpRequest req(stream.get(), host, mCONNECT, !useHTTP10); if (!authorization.empty()) { req.setHeader(fldProxyAuthorization,authorization); } req.closeOutput(); class ResponseResult: public IHttpResponseCB { public: virtual void storeStatus(natural statusCode, ConstStrA statusMessage) { status = statusCode; statusMsg.append(statusMessage); } virtual void storeHeaderLine(ConstStrA, ConstStrA) { } natural status; AutoArray<char, SmallAlloc<32> > statusMsg; }; ResponseResult res; HttpResponse resp(stream.get(),res,HttpResponse::readHeadersNow); if (status != 200) throw HttpStatusException(THISLOCATION,host,res.status, res.statusMsg); }
void HttpReqImpl::openPostChunk() const { ScanTextA scn(*inout); scn.setNL("\r\n"); scn("\n%"); if (scn(" %(+)[0-9A-Za-z]1 \n%")) { remainPostData = scn[1].hex(); if (remainPostData == 0) { chunkedPost = false; if (scn("\n%") == false) throw HttpStatusException(THISLOCATION,path,400,"Bad request"); } if (postBodyLimit < remainPostData) { throw HttpStatusException(THISLOCATION, path, 413, "Request is too large"); } else { postBodyLimit-= remainPostData; } } else { throw HttpStatusException(THISLOCATION,path,400,"Bad request"); } }
void WinHttpStream::sendRequest() { if (!exceptionDisabled) { curState = stReadResponse; natural status = getStatusCode(); if (status >= 300) throw HttpStatusException(THISLOCATION,url,status,String()); } }
PNetworkStream WebSocketsClient::onInitConnection(BredyHttpClient::HttpClient &http) { http.send(); if (http.getStatus() != 101) { throw HttpStatusException(THISLOCATION,url,http.getStatus(), http.getStatusMessage()); } //TODO: check headers to ensure, that ws connection is really established return http.getConnection(); }
void HttpReqImpl::setMaxPostSize(natural bytes) { if (remainPostData > bytes) throw HttpStatusException(THISLOCATION,path,413,"Request is too large"); postBodyLimit = bytes; }
void HttpClient::sendRequest(natural contentLength, PostStreamOption pso) { try { createRequest(urlToOpen,methodToOpen); request->setContentLength(contentLength); bool use100 = false; if (!useHTTP10) { switch(pso) { case psoDefault: case psoAllow100: use100 = connectionReused; break; case psoFavour100: case psoForce100: use100 = true;break; case psoBuffer: request->setContentLength(HttpRequest::calculateLength);break; case psoAvoid100NoReuseConn: if (connectionReused) { closeConnection(); createRequest(urlToOpen,methodToOpen); };break; case psoAvoid100: break; } if (use100) { setHeader(fldExpect,continue100); } } for (HdrMap::Iterator iter = reqHdrMap.getFwIter(); iter.hasItems();) { const HdrMap::KeyValue &kv = iter.getNext(); request->setHeader(kv.key, kv.value); } request->beginBody(); createResponse(false); if (use100) { //flush buffers now nstream->flush(); if (nstream->wait(INetworkResource::waitForInput,10000) != INetworkResource::waitTimeout) { response->readHeaders(); //there can other response, so if we cannot continue, return response to the caller if (!response->canContinue()) { //check status if (status == 417) {//we got precondition failed - no worries, we can repeat the request response->skipRemainBody(false); return sendRequest(contentLength, psoAvoid100); } else { loadResponse(); throw HttpStatusException(THISLOCATION,urlToOpen,status, statusMessage); } } } } }catch (NetworkException &) { if (connectionReused) { closeConnection(); sendRequest(contentLength,pso); } else { throw; } }catch (IOException &) { if (connectionReused) { closeConnection(); sendRequest(contentLength,pso); } else { throw; } } }