2011-12-21 60 views
3

我在通过https(HttpsURLConnection)上传文件时遇到问题。 对HttpURLConnection使用相同的代码就像一个魅力。在HTTPS上传文件时发生Android OutOfMemoryException

这里是堆栈:

ERROR/dalvikvm-heap(29984): Out of memory on a 20932172-byte allocation. 
INFO/dalvikvm(29984): "UploadingManager" prio=5 tid=9 RUNNABLE 
INFO/dalvikvm(29984): | group="main" sCount=0 dsCount=0 obj=0x2b085018 self=0x3d4de8 
INFO/dalvikvm(29984): | sysTid=30027 nice=0 sched=0/0 cgrp=[fopen-error:2] handle=3868056 
INFO/dalvikvm(29984): at java.io.ByteArrayOutputStream.expand(ByteArrayOutputStream.java:~91) 
INFO/dalvikvm(29984): at java.io.ByteArrayOutputStream.write(ByteArrayOutputStream.java:216) 
INFO/dalvikvm(29984): at org.apache.harmony.luni.internal.net.www.protocol.http.RetryableOutputStream.write(RetryableOutputStream.java:60) 
INFO/dalvikvm(29984): at java.io.DataOutputStream.write(DataOutputStream.java:99) 
INFO/dalvikvm(29984): at com.my.app.utils.UploadingManager$UploadingThread.run(UploadingManager.java:568) 

这里是代码: 初始化连接:

URL url = new URL(url_to_send); 
trustAllHosts(); 
connection = (HttpsURLConnection) url.openConnection(); 
connection.setHostnameVerifier(DO_NOT_VERIFY); 
connection.setChunkedStreamingMode(maxBufferSize); 

我使用相同的代码,在这里所说的建立“trustall” SSL连接: ssl on android strange issue(我知道他们面临类似的问题,但我想确保在上传过程中我没有犯任何错误)

这里是上传代码:

File uploaded_file = new File(pathToOurFile); 
file_input = new FileInputStream(uploaded_file); 

output_byte = new DataOutputStream(connection.getOutputStream()); 

int maxBufferSize = 20 * 1024; 
bytesAvailable = file_input.available(); 
bufferSize = Math.min(bytesAvailable, maxBufferSize); 
buffer = new byte[bufferSize]; 

// Read file 
bytesRead = file_input.read(buffer, 0, bufferSize); 
already_send += bytesRead; 

while (bytesRead > 0) { 

    output_byte.write(buffer, 0, bufferSize); < ----Exception occurs here 
    bytesAvailable = file_input.available(); 
    bufferSize = Math.min(bytesAvailable, maxBufferSize); 
    bytesRead = file_input.read(buffer, 0, bufferSize); 
    already_send += bytesRead; 

} 

output_byte.writeBytes(endBoundary); 
output_byte.flush(); 

你有任何想法,为什么我收到OutOfMemoryException异常?

问候, 彼得

EDIT1: 我注意到,如果我忽略:

connection.setChunkedStreamingMode(maxBufferSize); 

使用工作HttpURLConnection的我陷入同样的​​问题。 我知道,送使用SSL会产生较长的内容长度相同的消息,所以我已经改变的块大小2 * MAXBUFFERSIZE甚至20 * MAXBUFFERSIZE但是这使得对我来说没有什么区别:/

回答

1

有多大您正在上传的文件是?看来你正在试图写入~20MB到output_byte缓冲区。

此外,您正在写入错误的字节数到您的输出。

read(buffer, 0, bufferSize);行不保证bufferSize字节数量将被读取。阅读量从调用返回上述这样:

output_byte.write(buffer, 0, bufferSize); 

应改为:

output_byte.write(buffer, 0, bytesRead); 

因此,例如,如果你读1024bytes并尝试写每次20个* 1024字节,一个1MB文件你将有20倍的输出字节。这可能会导致OutOfMemory错误。

+0

感谢您的回复! 无论如何,我很肯定bufferSize == bytesRead,请注意,我使用这段代码: bytesAvailable = file_input.available(); bufferSize = Math.min(bytesAvailable,maxBufferSize); 以确保bufferSize == bytesRead。 文件大小约为15-50 MB – Shaar 2011-12-21 12:32:18

+1

好的,这就解释了它。看来你以20 * 1024的块读取文件,但是以1块的形式发送它。你应该把它发送到更小的部分。 Android应用程序大约有16-64 MB的内存限制被操作系统强制执行。你不能改变它。 – Caner 2011-12-21 12:36:19

+1

谷歌“android文件上传多部分”的详细 – Caner 2011-12-21 12:37:26

相关问题