Pessoal, alguém pode me ajudar.
Estou fazendo o download de um arquivo para o meu app (android) de um servidor web (Tomcat) e no meio do download dá o erro abaixo:
java.io.IOException: unexpected end of stream
at libcore.net.http.FixedLengthInputStream.read(FixedLengthInputStream.java:48)
at java.io.InputStream.read(InputStream.java:163)
at java.io.BufferedInputStream.fillbuf(BufferedInputStream.java:142)
at java.io.BufferedInputStream.read(BufferedInputStream.java:309)
at java.io.InputStream.read(InputStream.java:163)
Ninguem???
Estou a dias com esse problema.
Gilson, esse é o código que faz o download. O problema ocorre no While.
Cara já faz uma semana que estou com esse problema, estou até pensando em mudar a forma de download e puder me ajudar ficarei muito grato.
Pq se tivesse q mudar a forma de download, vou ter q alterar muito estrutura do programa
[code]
private String downloadArquivo(String sUrl, Comunica vo) {
String MainUrl = sUrl+"/Arquivos/Liberado/"+vo.getUsuario()+"/"+vo.getUsuario()+".zip";
InputStream input = null;
OutputStream output = null;
try {
URL url = new URL(MainUrl);
connection = (HttpURLConnection) url.openConnection();
connection.setInstanceFollowRedirects(false);
// connection.setReadTimeout(setReadTimeout);
// connection.setConnectTimeout(setConnectTimeout);
connection.setDoInput(true);
connection.setDoOutput(true);
connection.setUseCaches(false);
connection.setChunkedStreamingMode(0);
connection.setRequestMethod(“POST”);
connection.setRequestProperty(“Connection”, “Keep-Alive”);
connection.setRequestProperty(“http.keepAlive”, “false”);
connection.setRequestProperty ( “User-Agent” , “” );
connection.setRequestProperty(“Keep-Alive”, “header”);
connection.setRequestProperty(“Content-Type”,“multipart/zip’; charset = UTF-8”);
connection.setRequestProperty (“Accept-Encoding”, “”);
if (Build.VERSION.SDK != null && Build.VERSION.SDK_INT > 13) {
connection.setRequestProperty(“Connection”, “close”);
}
controlSessionClienteServer();
if (connection.getResponseCode() == 200){
String fileName = "";
String disposition = connection.getHeaderField("Content-Disposition");
if (disposition != null) {
int index = disposition.indexOf("filename=");
if (index > 0) {
fileName = disposition.substring(index + 10, disposition.length() - 1);
}
} else {
fileName = MainUrl.substring(MainUrl.lastIndexOf("/") + 1, MainUrl.length());
}
input = new BufferedInputStream(connection.getInputStream());
output = new FileOutputStream(Constantes.DIR_RECEB + File.separator + fileName);
byte buffer[] = new byte[1024];
long downloadedSize = 0;
int bufferLength;
int totalSize = connection.getContentLength();
ci.pbSetMaxProgressBar(totalSize); //Barra de Progresso
while ((bufferLength = input.read(buffer)) != -1) {
downloadedSize += bufferLength;
output.write(buffer, 0, bufferLength);
publishProgress("","",String.valueOf(downloadedSize),String.valueOf(totalSize+"/"+downloadedSize).toString()+" bytes - Download");
}
return "0";
}else{
return "1";
}
} catch (Throwable e) {
ExceptionAFV.setMsgErro(e, cxt, false);
_MSGCOM = e.getMessage().toString();
return "1";
} finally {
try {
if (output != null)
output.close();
if (input != null)
input.close();
} catch (IOException ioe) {}
if (connection != null)
connection.disconnect();
}
}[/code]
Obrigado.
tente assim:
pode ter algum erro de sintaxe, visto q não tenho como testar aki, não uso java.
[code]int totalSize = connection.getContentLength();
ci.pbSetMaxProgressBar(totalSize); //Barra de Progresso
int restante = totalSize;
while (restante > 0){
bufferLength = restante;
if (bufferLength > buffer.length) //no maximo 1024
bufferLength = buffer.length;
bufferLength = input.read(buffer, 0, bufferLength);
if (bufferLength == -1)
break;
downloadedSize += bufferLength;
output.write(buffer, 0, bufferLength);
restante -= bufferLength; //p saber qto falta
publishProgress("","",String.valueOf(downloadedSize),String.valueOf(totalSize+"/"+downloadedSize).toString()+" bytes - Download");
} [/code]
Gilson, continua dando o mesmo erro:
O erro acontece na linha abaixo no codigo que me passou:
Não sei o que fazer, pelo jeito vou ter q alterar toda a estrutura de donwload do programa.
Uma coisa que eu não disse é:
Esse erro só acontece depois que estou o pacote de dados contratado 30mb onde a velocidade de navegação será reduzida e não bloqueada, ou seja, fica mais lento a transmissão de da esse erro.
Pela sua experiencia, será que consigo fazer um try/catch para pegar esse erro e reconectar connection.getInputStream() para continuar o donwload de onde deu o problema?
Valeu.
mude essa linha
[code] input = new BufferedInputStream(connection.getInputStream());[/code]
para
input = connection.getInputStream();
se não funcionar, vou tentar instalar o eclipse aki pra eu testar.
Gilson, estava assim antes e já dava este erro.
Mas mesmo assim, fiz a alteração e o erro continua.
Acho que deve ter muito timeout por a conexão 3g reduzir a velocidade apos estourar o pacote de dados, é inacreditável que é só estourar o pacote de dados q da esse problema.
Tenho que achar uma solução para reconectar e continuar o download de onde deu esse problema, acho que assim vou ter uma solução.
Valeu.
ele lança a exceção pq os dados ainda não estão disponíveis. mas é so ver como configura pra ele retonar q não conseguiu ler, é assim q sockets funcionam.
Gilson, desculpe não entendi. Você pode me dar uma ajuda para resolver esse problema?
At.
Gilson, só completando a msg anterior
Iniciar o download e esse erro acontece no meio do download quando fica oscilando o rede de dados da operadora.
Acho que vai ser difícil achar uma solução, se pelo menos eu pudesse tratar um try/catch para iniciar o download de onde acontecesse este erro.
At.
Olha eu de novo, e que não sei mais o que fazer com esse problema. Quem puder me ajude,
Gilson, estou aqui fazendo outros testes para fazer o download e agora estou utilizando as classes: ReadableByteChannel e FileChannel.
O arquivo que estou fazendo download tem 1324309 bytes e sempre quando o quando o downlodas chega 131071 bytes encerra a conexão e dá o erro o mesmo erro:
Segue o erro e o código que faz o download.
java.io.IOException: unexpected end of stream
at libcore.net.http.FixedLengthInputStream.read(FixedLengthInputStream.java:48)
at java.io.InputStream.read(InputStream.java:163)
at java.nio.channels.Channels$InputStreamChannel.read(Channels.java:306)
at java.nio.FileChannelImpl.transferFrom(FileChannelImpl.java:387)
[code] private String downloadArquivo(String sUrl, Comunica vo) {
String MainUrl = sUrl+"/Arquivos/Liberado/"+vo.getUsuario()+"/"+vo.getUsuario()+".zip";
ReadableByteChannel in = null;
FileChannel out = null;
try {
File output = new File (Constantes.DIR_RECEB + File.separator + vo.getUsuario()+".zip");
URL url = new URL(MainUrl);
connection = (HttpURLConnection) url.openConnection();
if (connection.getResponseCode() == 200){
long length = connection.getContentLength();
ci.pbSetMaxProgressBar(length);
in = Channels.newChannel(connection.getInputStream());
out = new FileOutputStream(output).getChannel();
long pos = 0;
while (pos < length){
Log.v(“Script”, String.valueOf(length - pos));
pos += out.transferFrom(in, pos, length - pos);
publishProgress("","",String.valueOf(pos).toString(),String.valueOf(length+"/"+pos).toString()+" bytes - Download");
}
return "0";
}else{
return "1";
}
} catch (Exception e) {
ExceptionAFV.setMsgErro(e, cxt, false);
_MSGCOM = e.getMessage().toString();
return "1";
} finally {
try {
if (in != null){
in.close();
}
if (out != null){
out.close();
}
} catch (IOException e) {
ExceptionAFV.setMsgErro(e, cxt, false);
_MSGCOM = e.getMessage().toString();
}
}
}[/code]
Valeu.
eu testei o codigo aki e funcionou normalmente. ma não em mobile
Esse problema do FileChannel que publiquei, o engracado que se o arquivo for menor que 131071 bytes faz o donwload certinho no 3G e no Wifi.
Agora se for maior somente faz o donwload no wifi no 3G da esse erro.
Vai saber e vai entender!!!
Como resolver isso?
KKKK
Outro detalhe:
O erro “Unexpected end of stream” só ocorre quando o pacote de dados é estourado, por exemplo:
A operadora que utilizamos é a Vivo e o pacote de dados contratado é de 30mb, quando estoura o pacote de dados contratado a operadora reduz a velocidade e aí já não consigo fazer download dos arquivos maiores 100kb.
Caso não estoura o pacote de dados tudo funciona direitinho.
Tá complicado!
At.
o q ocorre é q qdo não tem dado disponível, o inputstream lança uma exceção.
ele poderia retornar q não leu (return = 0)
provavelmente tem algum maneira de saber se tem dado disponivel.
pq ele ta tratando como stream de arquivo, por exemplo, nesse caso qdo não tem dado disponível, é pq chegou ao fim, mas um socket já não é assim, só indica q o dado ainda não chegou.
Valeu Gilson!
Mais não consegui encontrar uma solução, vou repensar o processo e verificar uma forma para fazer download do dados no android.
Que coisa!
Mais de 15 dias em cima e nada.