6

I want to check progress of downloading file by URLconnection. Is it possible or should I use another library? This is my urlconnection function:

public static String sendPostRequest(String httpURL, String data) throws UnsupportedEncodingException, MalformedURLException, IOException {
    URL url = new URL(httpURL);

    URLConnection conn = url.openConnection();
    //conn.addRequestProperty("Content-Type", "text/html; charset=iso-8859-2");
    conn.setDoOutput(true);
    OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
    wr.write(data);
    wr.flush();

    BufferedReader rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), "ISO-8859-2"));
    String line, all = "";
    while ((line = rd.readLine()) != null) {
        all = all + line;
    }
    wr.close();
    rd.close();
    return all;
}

I understand that whole file is downloaded in this line (or worng)?:

BufferedReader rd = new BufferedReader(new InputStreamReader(conn.getInputStream(), "ISO-8859-2"));

So is it possible to do this in this code?

latata
  • 1,673
  • 5
  • 26
  • 54
  • I posted a class that reports read bytes from an `InputStream` using `ChangeListener`. It is transparent and independent of encoding. http://stackoverflow.com/a/10071341/893578 – Sheepy Apr 16 '15 at 02:35

3 Answers3

11

Just check if the HTTP Content-Length header is present in the response.

int contentLength = connection.getContentLength();

if (contentLength != -1) {
    // Just do (readBytes / contentLength) * 100 to calculate the percentage.
} else {
    // You're lost. Show "Progress: unknown"
}

Update as per your update, you're wrapping the InputStream inside a BufferedReader and reading inside a while loop. You can count the bytes as follows:

int readBytes = 0;

while ((line = rd.readLine()) != null) {
    readBytes += line.getBytes("ISO-8859-2").length + 2; // CRLF bytes!!
    // Do something with line.
}

The + 2 is to cover the CRLF (carriage return and linefeed) bytes which are eaten by BufferedReader#readLine(). More clean approach would be to just read it by InputStream#read(buffer) so that you don't need to massage the bytes forth and back from characters to calculate the read bytes.

See also:

Community
  • 1
  • 1
BalusC
  • 992,635
  • 352
  • 3,478
  • 3,452
  • 2
    Uhm, how are you reading the bytes then? I'd expect that you just read the `connection.getInputStream()` inside a `for` or `while` loop. You just count the read bytes inside this loop. Primary school maths and so on. – BalusC Mar 01 '11 at 23:19
  • Do you have any idea how i can make the same but using `HttpURLConnection` when i upload a file to server? Thanks! – Aleksey Timoshchenko May 02 '16 at 11:05
0
    BufferedReader rd = new BufferedReader(new InputStreamReader(new FilterInputStream(conn.getInputStream())
    {
        public int read(byte[] buffer, int byteOffset, int byteCount) throws IOException
        {
            int count = super.read(buffer, byteOffset, byteCount);
            // do whatever with count, i.e. mDownloaded += count;
            return count;
        }
    }, "ISO-8859-2"));
sherpya
  • 4,598
  • 2
  • 28
  • 48
0

Wrap it in a javax.swing.ProgressMonitorInputStream. But note that Java may buffer the entire response before it starts delivering it to the stream ...

user207421
  • 289,834
  • 37
  • 266
  • 440