提交 5d1787bd 编写于 作者: J Juergen Hoeller

Avoid expensive assertions in HttpRange

Closes gh-22742
上级 f328bfc1
/* /*
* Copyright 2002-2018 the original author or authors. * Copyright 2002-2019 the original author or authors.
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
...@@ -62,24 +62,11 @@ public abstract class HttpRange { ...@@ -62,24 +62,11 @@ public abstract class HttpRange {
Assert.isTrue(resource.getClass() != InputStreamResource.class, Assert.isTrue(resource.getClass() != InputStreamResource.class,
"Cannot convert an InputStreamResource to a ResourceRegion"); "Cannot convert an InputStreamResource to a ResourceRegion");
long contentLength = getLengthFor(resource); long contentLength = getLengthFor(resource);
Assert.isTrue(contentLength > 0, "Resource content length should be > 0");
long start = getRangeStart(contentLength); long start = getRangeStart(contentLength);
long end = getRangeEnd(contentLength); long end = getRangeEnd(contentLength);
return new ResourceRegion(resource, start, end - start + 1); return new ResourceRegion(resource, start, end - start + 1);
} }
private static long getLengthFor(Resource resource) {
long contentLength;
try {
contentLength = resource.contentLength();
Assert.isTrue(contentLength > 0, "Resource content length should be > 0");
}
catch (IOException ex) {
throw new IllegalArgumentException("Failed to obtain Resource content length", ex);
}
return contentLength;
}
/** /**
* Return the start of the range given the total length of a representation. * Return the start of the range given the total length of a representation.
* @param length the length of the representation * @param length the length of the representation
...@@ -131,8 +118,8 @@ public abstract class HttpRange { ...@@ -131,8 +118,8 @@ public abstract class HttpRange {
* <p>This method can be used to parse an {@code Range} header. * <p>This method can be used to parse an {@code Range} header.
* @param ranges the string to parse * @param ranges the string to parse
* @return the list of ranges * @return the list of ranges
* @throws IllegalArgumentException if the string cannot be parsed, or if * @throws IllegalArgumentException if the string cannot be parsed
* the number of ranges is greater than 100. * or if the number of ranges is greater than 100
*/ */
public static List<HttpRange> parseRanges(String ranges) { public static List<HttpRange> parseRanges(String ranges) {
if (!StringUtils.hasLength(ranges)) { if (!StringUtils.hasLength(ranges)) {
...@@ -144,7 +131,9 @@ public abstract class HttpRange { ...@@ -144,7 +131,9 @@ public abstract class HttpRange {
ranges = ranges.substring(BYTE_RANGE_PREFIX.length()); ranges = ranges.substring(BYTE_RANGE_PREFIX.length());
String[] tokens = StringUtils.tokenizeToStringArray(ranges, ","); String[] tokens = StringUtils.tokenizeToStringArray(ranges, ",");
Assert.isTrue(tokens.length <= MAX_RANGES, "Too many ranges " + tokens.length); if (tokens.length > MAX_RANGES) {
throw new IllegalArgumentException("Too many ranges: " + tokens.length);
}
List<HttpRange> result = new ArrayList<HttpRange>(tokens.length); List<HttpRange> result = new ArrayList<HttpRange>(tokens.length);
for (String token : tokens) { for (String token : tokens) {
result.add(parseRange(token)); result.add(parseRange(token));
...@@ -158,7 +147,7 @@ public abstract class HttpRange { ...@@ -158,7 +147,7 @@ public abstract class HttpRange {
if (dashIdx > 0) { if (dashIdx > 0) {
long firstPos = Long.parseLong(range.substring(0, dashIdx)); long firstPos = Long.parseLong(range.substring(0, dashIdx));
if (dashIdx < range.length() - 1) { if (dashIdx < range.length() - 1) {
Long lastPos = Long.parseLong(range.substring(dashIdx + 1, range.length())); Long lastPos = Long.parseLong(range.substring(dashIdx + 1));
return new ByteRange(firstPos, lastPos); return new ByteRange(firstPos, lastPos);
} }
else { else {
...@@ -180,9 +169,8 @@ public abstract class HttpRange { ...@@ -180,9 +169,8 @@ public abstract class HttpRange {
* @param ranges the list of ranges * @param ranges the list of ranges
* @param resource the resource to select the regions from * @param resource the resource to select the regions from
* @return the list of regions for the given resource * @return the list of regions for the given resource
* @throws IllegalArgumentException if the sum of all ranges exceeds the resource length
* @since 4.3 * @since 4.3
* @throws IllegalArgumentException if the sum of all ranges exceeds the
* resource length.
*/ */
public static List<ResourceRegion> toResourceRegions(List<HttpRange> ranges, Resource resource) { public static List<ResourceRegion> toResourceRegions(List<HttpRange> ranges, Resource resource) {
if (CollectionUtils.isEmpty(ranges)) { if (CollectionUtils.isEmpty(ranges)) {
...@@ -198,12 +186,25 @@ public abstract class HttpRange { ...@@ -198,12 +186,25 @@ public abstract class HttpRange {
for (ResourceRegion region : regions) { for (ResourceRegion region : regions) {
total += region.getCount(); total += region.getCount();
} }
Assert.isTrue(total < length, "The sum of all ranges (" + total + ") " + if (total >= length) {
"should be less than the resource length (" + length + ")"); throw new IllegalArgumentException("The sum of all ranges (" + total +
") should be less than the resource length (" + length + ")");
}
} }
return regions; return regions;
} }
private static long getLengthFor(Resource resource) {
try {
long contentLength = resource.contentLength();
Assert.isTrue(contentLength > 0, "Resource content length should be > 0");
return contentLength;
}
catch (IOException ex) {
throw new IllegalArgumentException("Failed to obtain Resource content length", ex);
}
}
/** /**
* Return a string representation of the given list of {@code HttpRange} objects. * Return a string representation of the given list of {@code HttpRange} objects.
* <p>This method can be used to for an {@code Range} header. * <p>This method can be used to for an {@code Range} header.
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册