use of cn.taketoday.http.HttpRange in project today-infrastructure by TAKETODAY.
the class DefaultClientResponseTests method header.
@Test
public void header() {
long contentLength = 42L;
httpHeaders.setContentLength(contentLength);
MediaType contentType = MediaType.TEXT_PLAIN;
httpHeaders.setContentType(contentType);
InetSocketAddress host = InetSocketAddress.createUnresolved("localhost", 80);
httpHeaders.setHost(host);
List<HttpRange> range = Collections.singletonList(HttpRange.createByteRange(0, 42));
httpHeaders.setRange(range);
given(mockResponse.getHeaders()).willReturn(httpHeaders);
ClientResponse.Headers headers = defaultClientResponse.headers();
assertThat(headers.contentLength()).isEqualTo(OptionalLong.of(contentLength));
assertThat(headers.contentType()).isEqualTo(Optional.of(contentType));
assertThat(headers.asHttpHeaders()).isEqualTo(httpHeaders);
}
use of cn.taketoday.http.HttpRange in project today-infrastructure by TAKETODAY.
the class ResourceRegionHttpMessageConverterTests method partialContentMultipleByteRangesInRandomOrderAndOverlapping.
@Test
public void partialContentMultipleByteRangesInRandomOrderAndOverlapping() throws Exception {
MockHttpOutputMessage outputMessage = new MockHttpOutputMessage();
Resource body = new ClassPathResource("byterangeresource.txt", getClass());
List<HttpRange> rangeList = HttpRange.parseRanges("bytes=7-15,0-5,17-20,20-29");
List<ResourceRegion> regions = new ArrayList<>();
for (HttpRange range : rangeList) {
regions.add(range.toResourceRegion(body));
}
converter.write(regions, MediaType.TEXT_PLAIN, outputMessage);
HttpHeaders headers = outputMessage.getHeaders();
assertThat(headers.getContentType().toString()).startsWith("multipart/byteranges;boundary=");
String boundary = "--" + headers.getContentType().toString().substring(30);
String content = outputMessage.getBodyAsString(StandardCharsets.UTF_8);
String[] ranges = StringUtils.tokenizeToStringArray(content, "\r\n", false, true);
assertThat(ranges[0]).isEqualTo(boundary);
assertThat(ranges[1]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[2]).isEqualTo("Content-Range: bytes 7-15/39");
assertThat(ranges[3]).isEqualTo("Framework");
assertThat(ranges[4]).isEqualTo(boundary);
assertThat(ranges[5]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[6]).isEqualTo("Content-Range: bytes 0-5/39");
assertThat(ranges[7]).isEqualTo("Spring");
assertThat(ranges[8]).isEqualTo(boundary);
assertThat(ranges[9]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[10]).isEqualTo("Content-Range: bytes 17-20/39");
assertThat(ranges[11]).isEqualTo("test");
assertThat(ranges[12]).isEqualTo(boundary);
assertThat(ranges[13]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[14]).isEqualTo("Content-Range: bytes 20-29/39");
assertThat(ranges[15]).isEqualTo("t resource");
}
use of cn.taketoday.http.HttpRange in project today-infrastructure by TAKETODAY.
the class ResourceRegionHttpMessageConverterTests method applicationOctetStreamDefaultContentType.
// SPR-15041
@Test
public void applicationOctetStreamDefaultContentType() throws Exception {
MockHttpOutputMessage outputMessage = new MockHttpOutputMessage();
ClassPathResource body = Mockito.mock(ClassPathResource.class);
BDDMockito.given(body.getName()).willReturn("spring.dat");
BDDMockito.given(body.contentLength()).willReturn(12L);
BDDMockito.given(body.getInputStream()).willReturn(new ByteArrayInputStream("Spring Framework".getBytes()));
HttpRange range = HttpRange.createByteRange(0, 5);
ResourceRegion resourceRegion = range.toResourceRegion(body);
converter.write(Collections.singletonList(resourceRegion), null, outputMessage);
assertThat(outputMessage.getHeaders().getContentType()).isEqualTo(MediaType.APPLICATION_OCTET_STREAM);
assertThat(outputMessage.getHeaders().getFirst(HttpHeaders.CONTENT_RANGE)).isEqualTo("bytes 0-5/12");
assertThat(outputMessage.getBodyAsString(StandardCharsets.UTF_8)).isEqualTo("Spring");
}
use of cn.taketoday.http.HttpRange in project today-framework by TAKETODAY.
the class ResourceRegionHttpMessageConverterTests method partialContentMultipleByteRangesInRandomOrderAndOverlapping.
@Test
public void partialContentMultipleByteRangesInRandomOrderAndOverlapping() throws Exception {
MockHttpOutputMessage outputMessage = new MockHttpOutputMessage();
Resource body = new ClassPathResource("byterangeresource.txt", getClass());
List<HttpRange> rangeList = HttpRange.parseRanges("bytes=7-15,0-5,17-20,20-29");
List<ResourceRegion> regions = new ArrayList<>();
for (HttpRange range : rangeList) {
regions.add(range.toResourceRegion(body));
}
converter.write(regions, MediaType.TEXT_PLAIN, outputMessage);
HttpHeaders headers = outputMessage.getHeaders();
assertThat(headers.getContentType().toString()).startsWith("multipart/byteranges;boundary=");
String boundary = "--" + headers.getContentType().toString().substring(30);
String content = outputMessage.getBodyAsString(StandardCharsets.UTF_8);
String[] ranges = StringUtils.tokenizeToStringArray(content, "\r\n", false, true);
assertThat(ranges[0]).isEqualTo(boundary);
assertThat(ranges[1]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[2]).isEqualTo("Content-Range: bytes 7-15/39");
assertThat(ranges[3]).isEqualTo("Framework");
assertThat(ranges[4]).isEqualTo(boundary);
assertThat(ranges[5]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[6]).isEqualTo("Content-Range: bytes 0-5/39");
assertThat(ranges[7]).isEqualTo("Spring");
assertThat(ranges[8]).isEqualTo(boundary);
assertThat(ranges[9]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[10]).isEqualTo("Content-Range: bytes 17-20/39");
assertThat(ranges[11]).isEqualTo("test");
assertThat(ranges[12]).isEqualTo(boundary);
assertThat(ranges[13]).isEqualTo("Content-Type: text/plain");
assertThat(ranges[14]).isEqualTo("Content-Range: bytes 20-29/39");
assertThat(ranges[15]).isEqualTo("t resource");
}
use of cn.taketoday.http.HttpRange in project today-framework by TAKETODAY.
the class ResourceHttpMessageWriter method write.
// Server-side only: single Resource or sub-regions...
@Override
public Mono<Void> write(Publisher<? extends Resource> inputStream, @Nullable ResolvableType actualType, ResolvableType elementType, @Nullable MediaType mediaType, ServerHttpRequest request, ServerHttpResponse response, Map<String, Object> hints) {
HttpHeaders headers = response.getHeaders();
headers.set(HttpHeaders.ACCEPT_RANGES, "bytes");
List<HttpRange> ranges;
try {
ranges = request.getHeaders().getRange();
} catch (IllegalArgumentException ex) {
response.setStatusCode(HttpStatus.REQUESTED_RANGE_NOT_SATISFIABLE);
return response.setComplete();
}
return Mono.from(inputStream).flatMap(resource -> {
if (ranges.isEmpty()) {
return writeResource(resource, elementType, mediaType, response, hints);
}
response.setStatusCode(HttpStatus.PARTIAL_CONTENT);
List<ResourceRegion> regions = HttpRange.toResourceRegions(ranges, resource);
MediaType resourceMediaType = getResourceMediaType(mediaType, resource, hints);
if (regions.size() == 1) {
ResourceRegion region = regions.get(0);
headers.setContentType(resourceMediaType);
long contentLength = lengthOf(resource);
if (contentLength != -1) {
long start = region.getPosition();
long end = start + region.getCount() - 1;
end = Math.min(end, contentLength - 1);
headers.add("Content-Range", "bytes " + start + '-' + end + '/' + contentLength);
headers.setContentLength(end - start + 1);
}
return writeSingleRegion(region, response, hints);
} else {
String boundary = MimeTypeUtils.generateMultipartBoundaryString();
MediaType multipartType = MediaType.parseMediaType("multipart/byteranges;boundary=" + boundary);
headers.setContentType(multipartType);
Map<String, Object> allHints = Hints.merge(hints, ResourceRegionEncoder.BOUNDARY_STRING_HINT, boundary);
return encodeAndWriteRegions(Flux.fromIterable(regions), resourceMediaType, response, allHints);
}
});
}
Aggregations