getResourceAsStream возвращает HttpInputStream не для всего файла - PullRequest
0 голосов
/ 20 мая 2010

У меня есть веб-приложение с апплетом, которое скопирует файл, упакованный с апплетом, на клиентский компьютер.

Когда я развертываю его на веб-сервере и использую: InputStream in = getClass (). GetResourceAsStream ("filename");

Функция in.available () всегда возвращает размер 8192 байта для каждого файла, который я пробовал, что означает, что файл поврежден при копировании на клиентский компьютер.

InputStream имеет тип HttpInputStream (sun.net.protocol.http.HttpUrlConnection $ httpInputStream). Но в то время как я тестирую апплет в средстве просмотра апплета, файлы копируются нормально, возвращенный InputStream имеет тип BufferedInputStream, который имеет байтовые размеры файла. Я предполагаю, что когда getResourceStream в файловой системе будет использоваться BufferedInputStream, а при протоколе http будет использоваться HttpInputStream.

Как мне полностью скопировать файл, ограничен ли размер для HttpInputStream? Большое спасибо.

Ответы [ 2 ]

3 голосов
/ 20 мая 2010

in.available() показывает, сколько байтов вы можете прочитать без блокировки, а не общее количество байтов, которые вы можете прочитать из потока.

Вот пример копирования InputStream в OutputStream из org.apache.commons.io.IOUtils:

public static long copyLarge(InputStream input, OutputStream output)
        throws IOException {
    byte[] buffer = new byte[DEFAULT_BUFFER_SIZE];
    long count = 0;
    int n = 0;
    while (-1 != (n = input.read(buffer))) {
        output.write(buffer, 0, n);
        count += n;
    }
    return count;
}
1 голос
/ 20 мая 2010

Функция in.available () всегда возвращает размер 8192 байта для каждого файла, который я пробовал, что означает, что файл поврежден при копировании на клиентский компьютер.

Это совсем не значит!

Метод in.available() возвращает количество символов, которые можно прочитать без блокировки. Это не длина потока. В общем случае невозможно определить длину InputStream, кроме чтения (или пропуска) всех байтов в потоке.

(Возможно, вы заметили, что new FileInputStream("someFile").available() обычно дает вам размер файла. Но такое поведение не гарантировано спецификацией и, безусловно, не соответствует действительности для некоторых типов файлов, а возможно и для некоторых файловой системы. Лучший способ получить размер файла - это new File("someFile").length(), но даже в некоторых случаях это не работает.)

См. Ответ @tdavies, например, код для копирования содержимого всего потока. Есть также сторонние библиотеки, которые могут делать такие вещи; например org.apache.commons.net.io.Util .

...