![](/img/trans.png)
[英]How to extract response header & status code from Spring 5 WebClient ClientResponse
[英]How to best get a byte array from a ClientResponse from Spring WebClient?
我正在使用響應式編程的代碼庫中嘗試使用 Spring 5 (5.0.0.RC2) 中的新WebClient
,並且我已經成功地將 JSON 響應從端點映射到我的應用程序中的 DTO,效果非常好:
WebClient client = WebClient.create(baseURI);
Mono<DTO> dto = client.get()
.uri(uri)
.accept(MediaType.APPLICATION_JSON)
.exchange()
.flatMap(response -> response.bodyToMono(DTO.class));
但是,現在我正在嘗試從使用協議緩沖區(二進制數據用作application/octet-stream
)的端點獲取響應正文,因此我想從響應中獲取原始字節,然后將其映射自己一個對象。
我使用來自 Google Guava 的Bytes
讓它像這樣工作:
Mono<byte[]> bytes = client.get()
.uri(uri)
.accept(MediaType.APPLICATION_OCTET_STREAM)
.exchange()
.flatMapMany(response -> response.body(BodyExtractors.toDataBuffers()))
.map(dataBuffer -> {
ByteBuffer byteBuffer = dataBuffer.asByteBuffer();
byte[] byteArray = new byte[byteBuffer.remaining()];
byteBuffer.get(byteArray, 0, bytes.length);
return byteArray;
})
.reduce(Bytes::concat)
這是有效的,但是有沒有更簡單、更優雅的方法來獲取這些字節?
ClientResponse.bodyToMono()
最終使用了一些聲稱支持指定類的org.springframework.core.codec.Decoder
。
所以我們應該檢查Decoder
的類層次結構,特別是decodeToMono()
方法的實現位置和方式。
有一個StringDecoder
支持解碼為String
,一堆與 Jackson 相關的解碼器(在你的 DTO 示例中使用),還有一個ResourceDecoder
是特別有趣的。
ResourceDecoder
支持org.springframework.core.io.InputStreamResource
和org.springframework.core.io.ByteArrayResource
。 ByteArrayResource
本質上是byte[]
的包裝器,因此以下代碼將提供對作為字節數組的響應主體的訪問:
Mono<byte[]> mono = client.get()
...
.exchange()
.flatMap(response -> response.bodyToMono(ByteArrayResource.class))
.map(ByteArrayResource::getByteArray);
Oleg Estekhin 的回答為 OP 提供了他所要求的內容,但它將整個響應內容加載到內存中,這對於大型響應來說是一個問題。 要一次獲取一大塊字節,我們可以執行以下操作:
client.get()
.uri("uri")
.exchange()
.flatMapMany { it.body(BodyExtractors.toDataBuffers()) }
默認情況下,這些緩沖區的大小為 8192 kb; 如果需要,請參閱此答案以進行更改。
請注意,如果ByteBuffer
不受數組支持,則嘗試執行dataBuffer.asByteBuffer().array()
會引發異常。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.