Ejemplo n.º 1
0
  /**
   * 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;
    }
  }
Ejemplo n.º 2
0
 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;
 }
Ejemplo n.º 3
0
  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;
  }
Ejemplo n.º 4
0
  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);
  }
Ejemplo n.º 5
0
  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"));
  }
Ejemplo n.º 6
0
  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;
  }
Ejemplo n.º 7
0
 @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();
     }
   }
 }
Ejemplo n.º 11
0
  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;
  }
Ejemplo n.º 12
0
  /**
   * 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();
      }
    }
  }
Ejemplo n.º 13
0
 // ---------- 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();
    }
  }
Ejemplo n.º 15
0
  /**
   * 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);
    }
  }
Ejemplo n.º 16
0
  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();
      }
    }
  }
Ejemplo n.º 19
0
  /**
   * 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());
    }
  }