2014-10-08 1 views
1

apache httpcore components을 사용하여 HTTP 요청을 구문 분석하려고하는데 요청 본문을 가져 오려고합니다. 기본값 인 DefaultHttpRequestParser이 입력 스트림에서 본문/엔터티를 구문 분석하지 않는 것 같습니다. 이것을 할 수업이 있습니까?HttpRequest가 null 엔티티를 반환하고 서버에서 본문을 추출 할 수 없습니다.

전체 스택을 사용할 수 없어서이 입력 스트림에서 요청을 직접 가져와야합니다.

내 파싱 코드는 아래와 같습니다. 다른 답변 중 일부를 살펴보면 요청 본문이 엔티티로 사용 가능해야합니다. 그러나 엔티티에 도달하려고 할 때마다 null입니다.

디버깅 버퍼가 읽었지만 본문을 사용하지 않았으며 그 바로 DefaultHttpRequestParser이 헤더를 읽은 것 같습니다. 전체 입력을 구문 분석하기 위해 사용해야하는 구문 분석이 있습니까?

InputStream is = socket.getInputStream(); 
    HttpTransportMetricsImpl metrics = new HttpTransportMetricsImpl(); 
    SessionInputBufferImpl buf = new SessionInputBufferImpl(metrics, 2048); 
    buf.bind(is); 

    DefaultHttpRequestParser reqParser = new DefaultHttpRequestParser(buf); 
    HttpRequest req = reqParser.parse(); 
    if (req instanceof HttpEntityEnclosingRequest) { 
     entity = ((HttpEntityEnclosingRequest)query).getEntity(); 
     //... entity is always null 

내가 끝낼 입력 스트림을 읽을 경우

POST/HTTP/1.1 
User-Agent: curl/Q.XX.0 (linux-gnu) libcurl/Q.XX.0 OpenSSL/X.Y.Z zlib/A.B.C.D libidn/E.FF librtmp/G.H 
Host: localhost:8088 
Accept: */* 
Content-Length: 333 
Content-Type: multipart/form-data; boundary=----------------------------39203c7982df 

------------------------------39203c7982df 
Content-Disposition: form-data; name="fileupload"; filename="grun.sh" 
Content-Type: application/octet-stream 

#!/bin/bash -x 
java -classpath lib/antlr-4.4-complete.jar:build/classes org.antlr.v4.runtime.misc.TestRig Typegroup "AHI" -tree 

------------------------------39203c7982df-- 

[업데이트] 올렉은 좋은 대답을 가지고 있지만, 내가 필요 지금 을하거나 요청에 몸을 연결할 수 있습니다 시체와 시내 두 곳을 지나쳐? 내가 조사 할게

나는 다음과 같이 작동하지만 다음 릴리스에서는 더 이상 사용되지 않을 예정이다. 내가 함께 결국 위의와 올렉의 솔루션을 결합

 ... 
     HttpEntityEnclosingRequest ereq = (HttpEntityEnclosingRequest) req; 
     @SuppressWarnings("deprecation") 
     EntityDeserializer ed = 
      new EntityDeserializer(new LaxContentLengthStrategy()); 
     @SuppressWarnings("deprecation")//ack! 
     HttpEntity ent = ed.deserialize(buf, req); 
     ereq.setEntity(ent); 
     return ereq; 

: HttpCore 구문 분석 메시지

  HttpEntityEnclosingRequest ereq = (HttpEntityEnclosingRequest) req; 

      ContentLengthStrategy contentLengthStrategy = 
         StrictContentLengthStrategy.INSTANCE; 
      long len = contentLengthStrategy.determineLength(req); 
      InputStream contentStream = null; 
      if (len == ContentLengthStrategy.CHUNKED) { 
       contentStream = new ChunkedInputStream(buf); 
      } else if (len == ContentLengthStrategy.IDENTITY) { 
       contentStream = new IdentityInputStream(buf); 
      } else { 
       contentStream = new ContentLengthInputStream(buf, len); 
      } 
      BasicHttpEntity ent = new BasicHttpEntity(); 
      ent.setContent(contentStream); 
      ereq.setEntity(ent); 
      return ereq; 

답변

3
InputStream is = socket.getInputStream(); 
HttpTransportMetricsImpl metrics = new HttpTransportMetricsImpl(); 
SessionInputBufferImpl buf = new SessionInputBufferImpl(metrics, 2048); 
buf.bind(is); 

DefaultHttpRequestParser reqParser = new DefaultHttpRequestParser(buf); 
HttpRequest req = reqParser.parse(); 
InputStream contentStream = null; 
if (req instanceof HttpEntityEnclosingRequest) { 
    ContentLengthStrategy contentLengthStrategy = StrictContentLengthStrategy.INSTANCE; 
    long len = contentLengthStrategy.determineLength(req); 
    if (len == ContentLengthStrategy.CHUNKED) { 
     contentStream = new ChunkedInputStream(buf); 
    } else if (len == ContentLengthStrategy.IDENTITY) { 
     contentStream = new IdentityInputStream(buf); 
    } else { 
     contentStream = new ContentLengthInputStream(buf, len); 
    } 
} 
// Do something useful with the content stream (if non null) 

메시지 파서는 머리. 그러나 세션 입력 버퍼에서 읽기를 계속하고 메시지 본문 내용을 읽을 때까지 사용합니다 (사용 된 구분자에 따라 다름)