【发布时间】:2020-08-08 19:57:34
【问题描述】:
我已经解决了与此相关的所有问题,但我还没有找到适合我的解决方案。
我正在使用retrofit 2.8.1 和OkHttp 4.5.0。
我的服务界面如下所示
public interface MlApiService
{
@POST
@Multipart
Call<List<PreprocessedDocument>> postDocument( @Url String apiUrl, @Part MultipartBody.Part document,
@Part ( "document_id") RequestBody documentId );
}
我构建客户端如下,requestTimeoutInSeconds 设置为 90 秒。
public void init()
{
GsonBuilder gson = new GsonBuilder();
gson.registerTypeAdapter( new TypeToken<List<PreprocessedDocument>>() {}.getType(), new CustomResponseDeserializer() );
HttpLoggingInterceptor logInterceptor = new HttpLoggingInterceptor();
logInterceptor.setLevel( HttpLoggingInterceptor.Level.HEADERS );
OkHttpClient client = new OkHttpClient.Builder().retryOnConnectionFailure( true ).addInterceptor( logInterceptor )
.readTimeout( requestTimeoutInSeconds, TimeUnit.SECONDS ).build();
//Dummy Base URL must be provided. otherwise client won't get initialized
Retrofit retrofit = new Retrofit.Builder().baseUrl( "http://thisIsJustDummyUrlForTheSakeOfAddingBaseUrl.com/" )
.client( client ).addConverterFactory( GsonConverterFactory.create( gson.setLenient().create() ) ).build();
mlApiService = retrofit.create( MlApiService.class );
}
请求到达服务器,当服务器响应时,我收到以下错误:
Caused by: java.io.IOException: unexpected end of stream on Connection{34.XXX.XXX.9:8085, proxy=DIRECT hostAddress=/34.XXX.XXX.9:8085 cipherSuite=none protocol=http/1.1}
at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:203)
at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45)
Caused by: java.io.EOFException: \n not found: limit=0 content=…
at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:227)
at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:211)
at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:187)
到目前为止我尝试过的几件事
- retryOnConnectionFailure(true)
- .addHeader("Connection","close")
- .header("Accept-Encoding", "identity")
API 在邮递员中运行良好,但在我从代码中尝试时失败。所以我尝试了邮递员发送的相同标题。还是没有运气。
几个观察:
- 它有时会起作用。不会总是失败。(邮递员总是可以使用同一个文件)
- 它始终适用于其他文件(从不存在问题)。
- 请求到达服务器并处理请求而没有任何错误并且也响应。服务器完成处理并响应客户端后,我立即收到错误消息。
编辑 1: 我点击的服务器由 gunicorn/20.0.4 支持并使用 Flask。我无权访问服务器代码。而且我怀疑收到的响应是否包含一些导致错误的垃圾字符。在被改造/okhttp 读取之前,我不知道如何记录原始响应。
编辑 2:
我以详细的方式运行 Curl 命令,这就是我得到的。
- 来自服务器的空回复
- 与主机 xx.xxx.xxx.9 的连接 #0 保持不变 curl: (52) 来自服务器的空回复
【问题讨论】:
-
如果它一直在 Postman 上工作,您最好的选择是将带有所有标头和正文的请求与您使用客户端生成的请求进行比较。您还可以查看文件内容是否有任何特殊或 Unicode 字符,因为您提到它是专门针对您收到此错误的文件的。有dos2unix类型的情况适用吗?
-
这是一个pdf文件@somshivam
-
@somshivam 见观察#3。此外,如果我们看到堆栈跟踪
at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:203)它会显示readResponseHeaders。这会留下线索吗?读取响应标头时出错?
标签: java retrofit2 gunicorn okhttp