JAVA:将任何文件正确地流式传输到浏览器

标签 java file stream server

所以我从头开始用 Java 创建了我自己的个人 HTTP 服务器。 到目前为止,它运行良好,但有一个主要缺陷。 当我尝试将大文件 传递给浏览器时,出现Java 堆空间错误。我知道如何通过 JVM 修复此错误,但我正在为此寻找长期解决方案。

//declare an integer for the byte length of the file
int length = (int) f.length();

//start the fileinput stream.
FileInputStream fis = new FileInputStream(f);

//byte array with the length of the file
byte[] bytes = new byte[length];

//write the file until the bytes is empty.

while ((length = fis.read(bytes)) != -1 ){
    write(bytes, 0, length);
}
flush();

//close the file input stream
fis.close();

这种方式将文件发送到浏览器成功并且完美地流式传输但问题是,因为我正在创建一个包含文件长度的字节数组。当文件很大时,我会收到堆空间错误。

我已经通过使用如下所示的缓冲区消除了这个问题,并且我不再收到堆空间错误。 但是 下面显示的方式不能正确地在浏览器中传输文件。就好像文件字节正在被打乱并一起发送到浏览器。

final int bufferSize = 4096;
byte buffer[] = new byte[bufferSize];

FileInputStream     fis = new FileInputStream(f);
BufferedInputStream bis = new BufferedInputStream(fis);

  while ( true )
  {
     int length = bis.read( buffer, 0, bufferSize );
     if ( length < 0 ) break;
     write( buffer, 0, length );
  }
 flush();
 bis.close();
 fis.close();

注意1:

所有正确的响应 header 都被完美地发送到浏览器。

注2:

两种方式在计算机浏览器上完美工作,但只有第一种方式在上工作智能手机的浏览器(但有时它会给我堆空间错误)。 如果有人知道如何正确地将文件发送到浏览器并正确地传输它们,我将是一个非常非常高兴的人。

提前致谢! :)

最佳答案

当从 BufferedInputStream 中读取时,您可以允许其缓冲区处理缓冲,没有理由将所有内容读入 byte[](当然也不是byte[] 整个文件)。一次读取一个字节,依赖于流的内部缓冲区。类似的东西,

FileInputStream fis = new FileInputStream(f);
BufferedInputStream bis = new BufferedInputStream(fis);
int abyte;
while ((abyte = bis.read()) != -1 ){
    write(abyte);
}

关于JAVA:将任何文件正确地流式传输到浏览器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36360848/

相关文章:

java - Android 上的身份验证

java - 运行 `mvn deploy` 时如何使用 Jenkins 凭据?

java - 在 Java 中检查新 XML 文件的最佳方法

javascript - 使用客户端 JavaScript 将文件附加到 PDF?

javascript - 在nodejs中与集群共享流

node.js - NodeJS Stream 通过 async/await 返回错误

python - 丢弃 T 形元件

java - 多个@Test、Selenium WebDriver 之间的 Get() 和 Set()

java - SpringBoot Kafka消费者 : Failed to start bean internalKafkaListenerEndpointRegistry TimeoutException

java - 比较两个文件时如何忽略空格?