0
我有一個工作代碼庫,它服務於包裝在HTTP狀態206中的Chunks<byte[]>
。代碼將.mp3文件傳輸到瀏覽器。如何在Play Framework(Java)v2.4.x中爲反應性字節塊提供服務
public class ChunksController extends Controller {
private static byte[] song;
private static RangeWrapper range;
private static Chunks<byte[]> chunks;
@With(MP3Headers.class)
public static F.Promise<Result> handler() {
return F.Promise.promise(new Function0<Result>() {
public Result apply() throws Throwable {
// Now we are serving a Promise of a Result
// Is there a way to serve a Promise of Chunks<byte[]>?
song = Files.readAllBytes(Paths.get("public/mp3/song.mp3"));
range = new RangeWrapper(request().getHeader("Range"), song.length);
chunks = new ByteChunks() {
public void onReady(Chunks.Out<byte[]> out) {
out.write(Arrays.copyOfRange(song, range.getFrom(), range.getTo()));
out.close();
}
};
// Set response headers so that the browser knows the content
response().setHeader("Content-Range", String.format("bytes %d-%d/%d", range.getFrom(), range.getTo(), song.length));
response().setHeader("X-Content-Length", Integer.toString(range.getContentLength()));
response().setHeader("Content-Length", Integer.toString(range.getContentLength()));
// I am very much wondering if this is the blocking part of the program...
return status(206, chunks);
}
});
}
}
在代碼示例中,MP3Headers
和RangeWrapper
是便利類,定義如下。
public class MP3Headers extends Action.Simple {
public F.Promise<Result> call(Http.Context ctx) throws Throwable {
ctx.response().setContentType("audio/mpeg");
ctx.response().setHeader("Accept-Ranges", "bytes");
return delegate.call(ctx);
}
}
和RangeWrapper
只存儲從和請求。
public class RangeWrapper {
private int from;
private int to;
public RangeWrapper(String range, int totalLength) {
// check range header for content
if (range != null) {
String[] intermediary = range.split("=")[1].split("-");
this.from = Integer.parseInt(intermediary[0]);
if (intermediary.length > 1) {
this.to = Integer.parseInt(intermediary[1]);
} else {
this.to = totalLength - 1;
}
} else {
this.from = 0;
this.to = totalLength - 1;
}
}
/** Getters */
public int getFrom() {
return this.from;
}
public int getTo() {
return this.to;
}
public int getContentLength() {
return this.to - this.from + 1;
}
}
現在的實際問題。 Play Server可以處理的實例數量似乎非常有限,我認爲這與ByteChunks
的同步性質有關。在下面的圖片中,您可以看到只有五個請求正在滿足數據。其餘的似乎沒有得到任何內容。有人有解決這個問題的辦法嗎?
問候,蒂姆
感謝您指出getContentLength()錯誤!至於靜態字段,我今天要測試它,並且會回到接受你的答案。 –