Я прошел через все вопросы, связанные с этим, и все же, я не нашел решения, которое работает для меня.
Я использую 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.219.110.9:8085, proxy=DIRECT hostAddress=/34.219.110.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 , У меня нет доступа к коду сервера. И я сомневаюсь, что в полученном ответе есть некоторые символы мусора, вызывающие ошибку. Я не знаю, как записать необработанный ответ перед чтением с помощью retrofit / okhttp.
EDIT 2:
Я выполнил команду Curl с подробным описанием, и это что я получил.
- Пустой ответ от сервера
- Соединение № 0 с хостом xx.xxx.xxx.9 левый нетронутый локон: (52) Пустой ответ с сервера