/** * Extracts the response from the method as a InputStream. * * @param method the method that was executed * @return the response either as a stream, or as a deserialized java object * @throws IOException can be thrown */ protected static Object extractResponseBody(HttpMethod method, Exchange exchange) throws IOException, ClassNotFoundException { InputStream is = method.getResponseBodyAsStream(); if (is == null) { return null; } Header header = method.getResponseHeader(Exchange.CONTENT_ENCODING); String contentEncoding = header != null ? header.getValue() : null; if (!exchange.getProperty(Exchange.SKIP_GZIP_ENCODING, Boolean.FALSE, Boolean.class)) { is = GZIPHelper.uncompressGzip(contentEncoding, is); } // Honor the character encoding String contentType = null; header = method.getResponseHeader("content-type"); if (header != null) { contentType = header.getValue(); // find the charset and set it to the Exchange HttpHelper.setCharsetFromContentType(contentType, exchange); } InputStream response = doExtractResponseBodyAsStream(is, exchange); // if content type is a serialized java object then de-serialize it back to a Java object if (contentType != null && contentType.equals(HttpConstants.CONTENT_TYPE_JAVA_SERIALIZED_OBJECT)) { return HttpHelper.deserializeJavaObjectFromStream(response); } else { return response; } }
boolean isZipContent(HttpMethod httpMethod) { if (null != httpMethod.getResponseHeader(Constants.CONTENT_ENCODING)) { String acceptEncoding = httpMethod.getResponseHeader(Constants.CONTENT_ENCODING).getValue(); if (acceptEncoding.toLowerCase().indexOf("gzip") > -1) { return true; } } return false; }
private String getNotModified(String dataId, CacheData cacheData, HttpMethod httpMethod) { Header md5Header = httpMethod.getResponseHeader(Constants.CONTENT_MD5); if (null == md5Header) { throw new RuntimeException("RP_NO_CHANGE response not contain MD5"); } String md5 = md5Header.getValue(); if (!cacheData.getMd5().equals(md5)) { String lastMd5 = cacheData.getMd5(); cacheData.setMd5(Constants.NULL); cacheData.setLastModifiedHeader(Constants.NULL); throw new RuntimeException( "MD5 verify error,DataID:[" + dataId + "]MD5 last:[" + lastMd5 + "]MD5 current:[" + md5 + "]"); } cacheData.setMd5(md5); changeSpacingInterval(httpMethod); if (log.isInfoEnabled()) { log.info("DataId: " + dataId + ",not changed"); } return null; }
public Object doTransform(Object src, String encoding) throws TransformerException { Object msg; HttpMethod httpMethod = (HttpMethod) src; Header contentType = httpMethod.getResponseHeader(HttpConstants.HEADER_CONTENT_TYPE); try { if (contentType != null && !contentType.getValue().startsWith("text/")) { msg = httpMethod.getResponseBody(); } else { msg = httpMethod.getResponseBodyAsString(); } } catch (IOException e) { throw new TransformerException(this, e); } // Standard headers Map headerProps = new HashMap(); Header[] headers = httpMethod.getRequestHeaders(); String name; for (int i = 0; i < headers.length; i++) { name = headers[i].getName(); if (name.startsWith("X-" + MuleProperties.PROPERTY_PREFIX)) { name = name.substring(2); } headerProps.put(headers[i].getName(), headers[i].getValue()); } // Set Mule Properties return new MuleMessage(msg, headerProps); }
public void innerProcess(CrawlURI curi) { if (!curi.isHttpTransaction() || curi.getFetchStatus() <= 0) { // If not http or if an error status code, skip. return; } numberOfCURIsHandled++; HttpMethod method = (HttpMethod) curi.getObject(A_HTTP_TRANSACTION); if (method.getResponseHeader("Location") != null) { addHeaderLink(curi, method.getResponseHeader("Location")); curi.setNextProcessor(curi.nextProcessorChain().getFirstProcessor()); curi.setNextProcessorChain(curi.nextProcessorChain().getNextProcessorChain()); } addHeaderLink(curi, method.getResponseHeader("Content-Location")); }
private String getSuccess( String dataId, String group, CacheData cacheData, HttpMethod httpMethod) { String configInfo = Constants.NULL; configInfo = getContent(httpMethod); if (null == configInfo) { throw new RuntimeException("RP_OK configInfo is null"); } Header md5Header = httpMethod.getResponseHeader(Constants.CONTENT_MD5); if (null == md5Header) { throw new RuntimeException("RP_OK not contain MD5, " + configInfo); } String md5 = md5Header.getValue(); if (!checkContent(configInfo, md5)) { throw new RuntimeException( "MD5 verify error,DataID:[" + dataId + "]ConfigInfo:[" + configInfo + "]MD5:[" + md5 + "]"); } Header lastModifiedHeader = httpMethod.getResponseHeader(Constants.LAST_MODIFIED); if (null == lastModifiedHeader) { throw new RuntimeException("RP_OK result not contain lastModifiedHeader"); } String lastModified = lastModifiedHeader.getValue(); cacheData.setMd5(md5); cacheData.setLastModifiedHeader(lastModified); changeSpacingInterval(httpMethod); String key = makeCacheKey(dataId, group); contentCache.put(key, configInfo); StringBuilder buf = new StringBuilder(); buf.append("dataId=").append(dataId); buf.append(" ,group=").append(group); buf.append(" ,content=").append(configInfo); dataLog.info(buf.toString()); return configInfo; }
@NotNull public String executeMethod(@NotNull HttpMethod method) throws Exception { LOG.debug("URI: " + method.getURI()); int statusCode; String entityContent; try { statusCode = getHttpClient().executeMethod(method); LOG.debug("Status code: " + statusCode); // may be null if 204 No Content received final InputStream stream = method.getResponseBodyAsStream(); entityContent = stream == null ? "" : StreamUtil.readText(stream, CharsetToolkit.UTF8); LOG.debug(entityContent); } finally { method.releaseConnection(); } // besides SC_OK, can also be SC_NO_CONTENT in issue transition requests // see: JiraRestApi#setTaskStatus // if (statusCode == HttpStatus.SC_OK || statusCode == HttpStatus.SC_NO_CONTENT) { if (statusCode >= 200 && statusCode < 300) { return entityContent; } else if (method.getResponseHeader("Content-Type") != null) { Header header = method.getResponseHeader("Content-Type"); if (header.getValue().startsWith("application/json")) { JsonObject object = GSON.fromJson(entityContent, JsonObject.class); if (object.has("errorMessages")) { String reason = StringUtil.join(object.getAsJsonArray("errorMessages"), " "); // something meaningful to user, e.g. invalid field name in JQL query LOG.warn(reason); throw new Exception("Request failed. Reason: " + reason); } } } if (method.getResponseHeader("X-Authentication-Denied-Reason") != null) { Header header = method.getResponseHeader("X-Authentication-Denied-Reason"); // only in JIRA >= 5.x.x if (header.getValue().startsWith("CAPTCHA_CHALLENGE")) { throw new Exception("Login failed. Enter captcha in web-interface."); } } if (statusCode == HttpStatus.SC_UNAUTHORIZED) { throw new Exception(LOGIN_FAILED_CHECK_YOUR_PERMISSIONS); } String statusText = HttpStatus.getStatusText(method.getStatusCode()); throw new Exception( String.format("Request failed with HTTP error: %d %s", statusCode, statusText)); }
private int patchRedirection(int status, HttpMethod method) throws HttpException, IOException { int redirectionsCount = 0; while (redirectionsCount < MAX_REDIRECTIONS_COUNT && (status == HttpStatus.SC_MOVED_PERMANENTLY || status == HttpStatus.SC_MOVED_TEMPORARILY || status == HttpStatus.SC_TEMPORARY_REDIRECT)) { Header location = method.getResponseHeader("Location"); if (location == null) { location = method.getResponseHeader("location"); } if (location != null) { Log_OC.d(TAG + " #" + mInstanceNumber, "Location to redirect: " + location.getValue()); method.setURI(new URI(location.getValue(), true)); Header destination = method.getRequestHeader("Destination"); if (destination == null) { destination = method.getRequestHeader("destination"); } if (destination != null) { String locationStr = location.getValue(); int suffixIndex = locationStr.lastIndexOf( (mCredentials instanceof OwnCloudBearerCredentials) ? AccountUtils.ODAV_PATH : AccountUtils.WEBDAV_PATH_4_0); String redirectionBase = locationStr.substring(0, suffixIndex); String destinationStr = destination.getValue(); String destinationPath = destinationStr.substring(mBaseUri.toString().length()); String redirectedDestination = redirectionBase + destinationPath; destination.setValue(redirectedDestination); method.setRequestHeader(destination); } status = super.executeMethod(method); redirectionsCount++; } else { Log_OC.d(TAG + " #" + mInstanceNumber, "No location to redirect!"); status = HttpStatus.SC_NOT_FOUND; } } return status; }
@Test public void testRequiredRole() throws HttpException, IOException { HttpMethod method = doRequest("http://localhost:9191/secure/requireRole"); int code = method.getStatusCode(); Header location = method.getResponseHeader("Location"); System.out.println("code:" + code); System.out.println("location:" + location.getValue()); Assert.assertEquals(code, 302); Assert.assertEquals(location.getValue(), "http://localhost:9191/secure/errorPage"); }
/** * Get a response header value string, or <code>defaultValue</code> if the header is undefined or * empty. */ public String getResponseHeaderValue(String name, String defaultValue) { Header header = m_method.getResponseHeader(name); if (header == null) { return defaultValue; } else { String value = header.getValue(); if (value == null || value.length() == 0) { return defaultValue; } else { return header.getValue(); } } }
protected Exception populateHttpOperationFailedException( Exchange exchange, HttpMethod method, int responseCode) throws IOException, ClassNotFoundException { Exception answer; String uri = method.getURI().toString(); String statusText = method.getStatusLine() != null ? method.getStatusLine().getReasonPhrase() : null; Map<String, String> headers = extractResponseHeaders(method.getResponseHeaders()); Object responseBody = extractResponseBody(method, exchange); if (transferException && responseBody != null && responseBody instanceof Exception) { // if the response was a serialized exception then use that return (Exception) responseBody; } // make a defensive copy of the response body in the exception so its detached from the cache String copy = null; if (responseBody != null) { copy = exchange.getContext().getTypeConverter().convertTo(String.class, exchange, responseBody); } if (responseCode >= 300 && responseCode < 400) { String redirectLocation; Header locationHeader = method.getResponseHeader("location"); if (locationHeader != null) { redirectLocation = locationHeader.getValue(); answer = new HttpOperationFailedException( uri, responseCode, statusText, redirectLocation, headers, copy); } else { // no redirect location answer = new HttpOperationFailedException(uri, responseCode, statusText, null, headers, copy); } } else { // internal server error (error code 500) answer = new HttpOperationFailedException(uri, responseCode, statusText, null, headers, copy); } return answer; }
/** * Load the image with a http-get * * @param url The url to the image * @param user username * @param pass password * @return The image * @throws IOException if any * @throws Exception if any */ protected BufferedImage loadImage(String url, String user, String pass) throws IOException, Exception { HttpMethod method = null; try { method = new GetMethod(url); int statusCode = client.executeMethod(method); if (statusCode != HttpStatus.SC_OK) { throw new Exception("Error connecting to server. HTTP status code: " + statusCode); } String mime = method.getResponseHeader("Content-Type").getValue(); return ImageTool.readImage(method, mime); } finally { if (method != null) { method.releaseConnection(); } } }
// ---------- util methods -------------// private String getResponseEncoding(HttpMethod method) { Header header = method.getResponseHeader("Content-Type"); String encoding = DEFAULT_ENCODING; if (header != null) { if (logger.isDebugEnabled()) { logger.debug("Content-Type=" + header.getValue()); } if (header != null) { String value = header.getValue(); int idx1 = value.indexOf("charset="); if (idx1 > -1) { encoding = value.substring(idx1 + 8); if (logger.isDebugEnabled()) { logger.debug("Response Encoding=" + encoding); } } } } return encoding; }
private String post(final HttpMethod method) throws IOException, ForbiddenException { method.getParams().setCookiePolicy(CookiePolicy.IGNORE_COOKIES); method.setRequestHeader("Accept-Encoding", "gzip"); InputStream is = null; try { this.m_clientManager.executeMethod(method); final int statusCode = method.getStatusCode(); final StatusLine statusLine = method.getStatusLine(); final Header encoding = method.getResponseHeader("Content-Encoding"); if (encoding != null && encoding.getValue().equals("gzip")) { m_log.debug("Unzipping body..."); is = new GZIPInputStream(method.getResponseBodyAsStream()); } else { is = method.getResponseBodyAsStream(); } final String body = IOUtils.toString(is); if (StringUtils.isBlank(body)) { // Could easily be a post request, which would not have a body. m_log.debug("No response body. Post request?"); } if (statusCode == HttpStatus.SC_FORBIDDEN) { final String msg = "NO 200 OK: " + method.getURI() + "\n" + statusLine + "\n" + body; m_log.warn(msg); throw new ForbiddenException(msg); } if (statusCode != HttpStatus.SC_OK) { final String msg = "NO 200 OK: " + method.getURI() + "\n" + statusLine + "\n" + body; m_log.warn(msg); throw new IOException(msg); } else { m_log.debug("Got 200 response..."); } return body; } finally { IOUtils.closeQuietly(is); method.releaseConnection(); } }
/** * Executes the {@link HttpMethod} passed in and sends the proxy response back to the client via * the given {@link HttpServletResponse} * * @param httpMethodProxyRequest An object representing the proxy request to be made * @param httpServletResponse An object by which we can send the proxied response back to the * client * @throws IOException Can be thrown by the {@link HttpClient}.executeMethod * @throws ServletException Can be thrown to indicate that another error has occurred */ private void executeProxyRequest( HttpMethod httpMethodProxyRequest, HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws IOException, ServletException { // Create a default HttpClient HttpClient httpClient = new HttpClient(); httpMethodProxyRequest.setFollowRedirects(false); // Execute the request int intProxyResponseCode = httpClient.executeMethod(httpMethodProxyRequest); // Check if the proxy response is a redirect // The following code is adapted from org.tigris.noodle.filters.CheckForRedirect // Hooray for open source software if (intProxyResponseCode >= HttpServletResponse.SC_MULTIPLE_CHOICES /* 300 */ && intProxyResponseCode < HttpServletResponse.SC_NOT_MODIFIED /* 304 */) { String stringStatusCode = Integer.toString(intProxyResponseCode); String stringLocation = httpMethodProxyRequest.getResponseHeader(STRING_LOCATION_HEADER).getValue(); if (stringLocation == null) { throw new ServletException( "Recieved status code: " + stringStatusCode + " but no " + STRING_LOCATION_HEADER + " header was found in the response"); } // Modify the redirect to go to this proxy servlet rather that the proxied host String stringMyHostName = httpServletRequest.getServerName(); if (httpServletRequest.getServerPort() != 80) { stringMyHostName += ":" + httpServletRequest.getServerPort(); } stringMyHostName += httpServletRequest.getContextPath(); httpServletResponse.sendRedirect( stringLocation.replace(getProxyHostAndPort() + this.getProxyPath(), stringMyHostName)); return; } else if (intProxyResponseCode == HttpServletResponse.SC_NOT_MODIFIED) { // 304 needs special handling. See: // http://www.ics.uci.edu/pub/ietf/http/rfc1945.html#Code304 // We get a 304 whenever passed an 'If-Modified-Since' // header and the data on disk has not changed; server // responds w/ a 304 saying I'm not going to send the // body because the file has not changed. httpServletResponse.setIntHeader(STRING_CONTENT_LENGTH_HEADER_NAME, 0); httpServletResponse.setStatus(HttpServletResponse.SC_NOT_MODIFIED); return; } // Pass the response code back to the client httpServletResponse.setStatus(intProxyResponseCode); // Pass response headers back to the client Header[] headerArrayResponse = httpMethodProxyRequest.getResponseHeaders(); for (Header header : headerArrayResponse) { httpServletResponse.setHeader(header.getName(), header.getValue()); } // Send the content to the client InputStream inputStreamProxyResponse = httpMethodProxyRequest.getResponseBodyAsStream(); BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStreamProxyResponse); OutputStream outputStreamClientResponse = httpServletResponse.getOutputStream(); int intNextByte; while ((intNextByte = bufferedInputStream.read()) != -1) { outputStreamClientResponse.write(intNextByte); } }
protected byte[] URLtoByteArray( String location, Http.Method method, Map<String, String> headers, Cookie[] cookies, Http.Auth auth, Http.Body body, List<Http.FilePart> fileParts, Map<String, String> parts, Http.Response response, boolean followRedirects) throws IOException { byte[] bytes = null; HttpMethod httpMethod = null; HttpState httpState = null; try { _cookies.set(null); if (location == null) { return null; } else if (!location.startsWith(Http.HTTP_WITH_SLASH) && !location.startsWith(Http.HTTPS_WITH_SLASH)) { location = Http.HTTP_WITH_SLASH + location; } HostConfiguration hostConfiguration = getHostConfiguration(location); HttpClient httpClient = getClient(hostConfiguration); if (method.equals(Http.Method.POST) || method.equals(Http.Method.PUT)) { if (method.equals(Http.Method.POST)) { httpMethod = new PostMethod(location); } else { httpMethod = new PutMethod(location); } if (body != null) { RequestEntity requestEntity = new StringRequestEntity(body.getContent(), body.getContentType(), body.getCharset()); EntityEnclosingMethod entityEnclosingMethod = (EntityEnclosingMethod) httpMethod; entityEnclosingMethod.setRequestEntity(requestEntity); } else if (method.equals(Http.Method.POST)) { PostMethod postMethod = (PostMethod) httpMethod; processPostMethod(postMethod, fileParts, parts); } } else if (method.equals(Http.Method.DELETE)) { httpMethod = new DeleteMethod(location); } else if (method.equals(Http.Method.HEAD)) { httpMethod = new HeadMethod(location); } else { httpMethod = new GetMethod(location); } if (headers != null) { for (Map.Entry<String, String> header : headers.entrySet()) { httpMethod.addRequestHeader(header.getKey(), header.getValue()); } } if ((method.equals(Http.Method.POST) || method.equals(Http.Method.PUT)) && ((body != null) || ((fileParts != null) && !fileParts.isEmpty()) | ((parts != null) && !parts.isEmpty()))) { } else if (!hasRequestHeader(httpMethod, HttpHeaders.CONTENT_TYPE)) { httpMethod.addRequestHeader( HttpHeaders.CONTENT_TYPE, ContentTypes.APPLICATION_X_WWW_FORM_URLENCODED); } if (!hasRequestHeader(httpMethod, HttpHeaders.USER_AGENT)) { httpMethod.addRequestHeader(HttpHeaders.USER_AGENT, _DEFAULT_USER_AGENT); } httpState = new HttpState(); if ((cookies != null) && (cookies.length > 0)) { org.apache.commons.httpclient.Cookie[] commonsCookies = toCommonsCookies(cookies); httpState.addCookies(commonsCookies); HttpMethodParams httpMethodParams = httpMethod.getParams(); httpMethodParams.setCookiePolicy(CookiePolicy.BROWSER_COMPATIBILITY); } if (auth != null) { httpMethod.setDoAuthentication(true); httpState.setCredentials( new AuthScope(auth.getHost(), auth.getPort(), auth.getRealm()), new UsernamePasswordCredentials(auth.getUsername(), auth.getPassword())); } proxifyState(httpState, hostConfiguration); httpClient.executeMethod(hostConfiguration, httpMethod, httpState); Header locationHeader = httpMethod.getResponseHeader("location"); if ((locationHeader != null) && !locationHeader.equals(location)) { String redirect = locationHeader.getValue(); if (followRedirects) { return URLtoByteArray( redirect, Http.Method.GET, headers, cookies, auth, body, fileParts, parts, response, followRedirects); } else { response.setRedirect(redirect); } } InputStream inputStream = httpMethod.getResponseBodyAsStream(); if (inputStream != null) { Header contentLength = httpMethod.getResponseHeader(HttpHeaders.CONTENT_LENGTH); if (contentLength != null) { response.setContentLength(GetterUtil.getInteger(contentLength.getValue())); } Header contentType = httpMethod.getResponseHeader(HttpHeaders.CONTENT_TYPE); if (contentType != null) { response.setContentType(contentType.getValue()); } bytes = FileUtil.getBytes(inputStream); } for (Header header : httpMethod.getResponseHeaders()) { response.addHeader(header.getName(), header.getValue()); } return bytes; } finally { try { if (httpState != null) { _cookies.set(toServletCookies(httpState.getCookies())); } } catch (Exception e) { _log.error(e, e); } try { if (httpMethod != null) { httpMethod.releaseConnection(); } } catch (Exception e) { _log.error(e, e); } } }
/** Get a specific response header. */ public Header getResponseHeader(String name) { return m_method.getResponseHeader(name); }
public NamedList<Object> request(final SolrRequest request, ResponseParser processor) throws SolrServerException, IOException { HttpMethod method = null; InputStream is = null; SolrParams params = request.getParams(); Collection<ContentStream> streams = requestWriter.getContentStreams(request); String path = requestWriter.getPath(request); if (path == null || !path.startsWith("/")) { path = "/select"; } ResponseParser parser = request.getResponseParser(); if (parser == null) { parser = _parser; } // The parser 'wt=' and 'version=' params are used instead of the original params ModifiableSolrParams wparams = new ModifiableSolrParams(); wparams.set(CommonParams.WT, parser.getWriterType()); wparams.set(CommonParams.VERSION, parser.getVersion()); if (params == null) { params = wparams; } else { params = new DefaultSolrParams(wparams, params); } if (_invariantParams != null) { params = new DefaultSolrParams(_invariantParams, params); } int tries = _maxRetries + 1; try { while (tries-- > 0) { // Note: since we aren't do intermittent time keeping // ourselves, the potential non-timeout latency could be as // much as tries-times (plus scheduling effects) the given // timeAllowed. try { if (SolrRequest.METHOD.GET == request.getMethod()) { if (streams != null) { throw new SolrException( SolrException.ErrorCode.BAD_REQUEST, "GET can't send streams!"); } method = new GetMethod(_baseURL + path + ClientUtils.toQueryString(params, false)); } else if (SolrRequest.METHOD.POST == request.getMethod()) { String url = _baseURL + path; boolean isMultipart = (streams != null && streams.size() > 1); if (streams == null || isMultipart) { PostMethod post = new PostMethod(url); post.getParams().setContentCharset("UTF-8"); if (!this.useMultiPartPost && !isMultipart) { post.addRequestHeader( "Content-Type", "application/x-www-form-urlencoded; charset=UTF-8"); } List<Part> parts = new LinkedList<Part>(); Iterator<String> iter = params.getParameterNamesIterator(); while (iter.hasNext()) { String p = iter.next(); String[] vals = params.getParams(p); if (vals != null) { for (String v : vals) { if (this.useMultiPartPost || isMultipart) { parts.add(new StringPart(p, v, "UTF-8")); } else { post.addParameter(p, v); } } } } if (isMultipart) { int i = 0; for (ContentStream content : streams) { final ContentStream c = content; String charSet = null; String transferEncoding = null; parts.add( new PartBase(c.getName(), c.getContentType(), charSet, transferEncoding) { @Override protected long lengthOfData() throws IOException { return c.getSize(); } @Override protected void sendData(OutputStream out) throws IOException { InputStream in = c.getStream(); try { IOUtils.copy(in, out); } finally { in.close(); } } }); } } if (parts.size() > 0) { post.setRequestEntity( new MultipartRequestEntity( parts.toArray(new Part[parts.size()]), post.getParams())); } method = post; } // It is has one stream, it is the post body, put the params in the URL else { String pstr = ClientUtils.toQueryString(params, false); PostMethod post = new PostMethod(url + pstr); // Single stream as body // Using a loop just to get the first one final ContentStream[] contentStream = new ContentStream[1]; for (ContentStream content : streams) { contentStream[0] = content; break; } if (contentStream[0] instanceof RequestWriter.LazyContentStream) { post.setRequestEntity( new RequestEntity() { public long getContentLength() { return -1; } public String getContentType() { return contentStream[0].getContentType(); } public boolean isRepeatable() { return false; } public void writeRequest(OutputStream outputStream) throws IOException { ((RequestWriter.LazyContentStream) contentStream[0]).writeTo(outputStream); } }); } else { is = contentStream[0].getStream(); post.setRequestEntity( new InputStreamRequestEntity(is, contentStream[0].getContentType())); } method = post; } } else { throw new SolrServerException("Unsupported method: " + request.getMethod()); } } catch (NoHttpResponseException r) { // This is generally safe to retry on method.releaseConnection(); method = null; if (is != null) { is.close(); } // If out of tries then just rethrow (as normal error). if ((tries < 1)) { throw r; } // log.warn( "Caught: " + r + ". Retrying..." ); } } } catch (IOException ex) { throw new SolrServerException("error reading streams", ex); } method.setFollowRedirects(_followRedirects); method.addRequestHeader("User-Agent", AGENT); if (_allowCompression) { method.setRequestHeader(new Header("Accept-Encoding", "gzip,deflate")); } try { // Execute the method. // System.out.println( "EXECUTE:"+method.getURI() ); int statusCode = _httpClient.executeMethod(method); if (statusCode != HttpStatus.SC_OK) { StringBuilder msg = new StringBuilder(); msg.append(method.getStatusLine().getReasonPhrase()); msg.append("\n\n"); msg.append(method.getStatusText()); msg.append("\n\n"); msg.append("request: " + method.getURI()); throw new SolrException(statusCode, java.net.URLDecoder.decode(msg.toString(), "UTF-8")); } // Read the contents String charset = "UTF-8"; if (method instanceof HttpMethodBase) { charset = ((HttpMethodBase) method).getResponseCharSet(); } InputStream respBody = method.getResponseBodyAsStream(); // Jakarta Commons HTTPClient doesn't handle any // compression natively. Handle gzip or deflate // here if applicable. if (_allowCompression) { Header contentEncodingHeader = method.getResponseHeader("Content-Encoding"); if (contentEncodingHeader != null) { String contentEncoding = contentEncodingHeader.getValue(); if (contentEncoding.contains("gzip")) { // log.debug( "wrapping response in GZIPInputStream" ); respBody = new GZIPInputStream(respBody); } else if (contentEncoding.contains("deflate")) { // log.debug( "wrapping response in InflaterInputStream" ); respBody = new InflaterInputStream(respBody); } } else { Header contentTypeHeader = method.getResponseHeader("Content-Type"); if (contentTypeHeader != null) { String contentType = contentTypeHeader.getValue(); if (contentType != null) { if (contentType.startsWith("application/x-gzip-compressed")) { // log.debug( "wrapping response in GZIPInputStream" ); respBody = new GZIPInputStream(respBody); } else if (contentType.startsWith("application/x-deflate")) { // log.debug( "wrapping response in InflaterInputStream" ); respBody = new InflaterInputStream(respBody); } } } } } return processor.processResponse(respBody, charset); } catch (HttpException e) { throw new SolrServerException(e); } catch (IOException e) { throw new SolrServerException(e); } finally { method.releaseConnection(); if (is != null) { is.close(); } } }
/** * Executes the {@link HttpMethod} passed in and sends the proxy response back to the client via * the given {@link HttpServletResponse}. * * @param httpMethodProxyRequest An object representing the proxy request to be made * @param httpServletResponse An object by which we can send the proxied response back to the * client * @throws IOException Can be thrown by the {@link HttpClient}.executeMethod * @throws ServletException Can be thrown to indicate that another error has occurred */ private void executeProxyRequest( HttpMethod httpMethodProxyRequest, HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws IOException, ServletException { // Create a default HttpClient HttpClient httpClient; httpClient = createClientWithLogin(); httpMethodProxyRequest.setFollowRedirects(false); // Execute the request int intProxyResponseCode = httpClient.executeMethod(httpMethodProxyRequest); // String response = httpMethodProxyRequest.getResponseBodyAsString(); // Check if the proxy response is a redirect // The following code is adapted from org.tigris.noodle.filters.CheckForRedirect // Hooray for open source software if (intProxyResponseCode >= HttpServletResponse.SC_MULTIPLE_CHOICES /* 300 */ && intProxyResponseCode < HttpServletResponse.SC_NOT_MODIFIED /* 304 */) { String stringStatusCode = Integer.toString(intProxyResponseCode); String stringLocation = httpMethodProxyRequest.getResponseHeader(HEADER_LOCATION).getValue(); if (stringLocation == null) { throw new ServletException( "Received status code: " + stringStatusCode + " but no " + HEADER_LOCATION + " header was found in the response"); } // Modify the redirect to go to this proxy servlet rather that the proxied host String stringMyHostName = httpServletRequest.getServerName(); if (httpServletRequest.getServerPort() != 80) { stringMyHostName += ":" + httpServletRequest.getServerPort(); } stringMyHostName += httpServletRequest.getContextPath(); if (followRedirects) { httpServletResponse.sendRedirect( stringLocation.replace(getProxyHostAndPort() + proxyPath, stringMyHostName)); return; } } else if (intProxyResponseCode == HttpServletResponse.SC_NOT_MODIFIED) { // 304 needs special handling. See: // http://www.ics.uci.edu/pub/ietf/http/rfc1945.html#Code304 // We get a 304 whenever passed an 'If-Modified-Since' // header and the data on disk has not changed; server // responds w/ a 304 saying I'm not going to send the // body because the file has not changed. httpServletResponse.setIntHeader(HEADER_CONTENT_LENGTH, 0); httpServletResponse.setStatus(HttpServletResponse.SC_NOT_MODIFIED); return; } // Pass the response code back to the client httpServletResponse.setStatus(intProxyResponseCode); // Pass response headers back to the client Header[] headerArrayResponse = httpMethodProxyRequest.getResponseHeaders(); for (Header header : headerArrayResponse) { if (header.getName().equals("Transfer-Encoding") && header.getValue().equals("chunked") || header.getName().equals("Content-Encoding") && header.getValue().equals("gzip")) { // proxy servlet does not support chunked encoding } else { httpServletResponse.setHeader(header.getName(), header.getValue()); } } List<Header> responseHeaders = Arrays.asList(headerArrayResponse); // FIXME We should handle both String and bytes response in the same way: String response = null; byte[] bodyBytes = null; if (isBodyParameterGzipped(responseHeaders)) { LOGGER.trace("GZipped: true"); if (!followRedirects && intProxyResponseCode == HttpServletResponse.SC_MOVED_TEMPORARILY) { response = httpMethodProxyRequest.getResponseHeader(HEADER_LOCATION).getValue(); httpServletResponse.setStatus(HttpServletResponse.SC_OK); intProxyResponseCode = HttpServletResponse.SC_OK; httpServletResponse.setHeader(HEADER_LOCATION, response); httpServletResponse.setContentLength(response.length()); } else { bodyBytes = ungzip(httpMethodProxyRequest.getResponseBody()); httpServletResponse.setContentLength(bodyBytes.length); } } if (httpServletResponse.getContentType() != null && httpServletResponse.getContentType().contains("text")) { LOGGER.trace("Received status code: {} Response: {}", intProxyResponseCode, response); } else { LOGGER.trace("Received status code: {} [Response is not textual]", intProxyResponseCode); } // Send the content to the client if (response != null) { httpServletResponse.getWriter().write(response); } else if (bodyBytes != null) { httpServletResponse.getOutputStream().write(bodyBytes); } else { IOUtils.copy( httpMethodProxyRequest.getResponseBodyAsStream(), httpServletResponse.getOutputStream()); } }