提问人:Luke 提问时间:12/6/2022 最后编辑:Luke 更新时间:12/6/2022 访问量:111
Spring Boot 导出 即使在单独的线程中,PipedInputStream 也被锁定
Spring boot export PipedInputStream is getting locked even in separated thread
问:
我正在使用 PipedOutputStream 将 spring boot 应用程序与 REST API 导出 csv 文件一起使用。 但是当我到达 REST API 端点时,它会毫无例外地锁定在第 100 行,直到我强制重新加载应用程序 (java.io.PipedInputStream.awaitSpace)。日志如下。
我所知道的是它必须在单独的线程中,因此我决定将@Async注释放在 exportCsv() 方法中。所以我认为这应该在单独的线程中执行。
问题
- 如何在 try catch 块中强制处理此操作?
- 为什么它在单独的线程中时会被锁定?我的理解是否正确,即在写入处理期间,当 pin 作为 PipedOutputStream 连接到 pout 时,它只会返回给最终用户?
下面是示例代码
End point class
public ResponseEntity<InputStreamResource> exportCsv(Long id) {
PipedInputSTream pin = new PipedInputSTream();
PipedOutputStream pout = new PipedOutputStream(pin);
service.exportCsv(pout, id);
return ResponseEntity.ok().headers(headers).contentType(mediaType).body(new InputStreamResource(pin));
}
---
Service class
@Async
void exportCsv(OutputStream outputStream, Long id) {
BeanWriter writer = StreamFactory.newInstance().createWriter("output", new OutputStreamWriter(outputStream));
AtomicInteger index = new AtomicInteger();
try (Stream<Data> stream = repository.streamData(id)) {
stream.filter(Objects::nonNull).forEach(e -> {
writer.write(e);
int i = index.incrementAndGet();
if (i % FLUSH_SIZE == 0) writer.flush(); System.gc();
});
}
writer.flush(); writer.close();
}
这是日志
main" prio=10 tid=0x08066000 nid=0x48d2 in Object.wait() [0xb7fd2000..0xb7fd31e8]
java.lang.Thread.State: TIMED_WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0xa5c28be8> (a java.io.PipedInputStream)
at java.io.PipedInputStream.awaitSpace(PipedInputStream.java:257)
at java.io.PipedInputStream.receive(PipedInputStream.java:215)
答: 暂无答案
评论