Skip to content

Commit

Permalink
Limit timestamp string length (#4382)
Browse files Browse the repository at this point in the history
* Limit timestamp string length

* Add test
  • Loading branch information
dagnir committed Sep 1, 2023
1 parent 712ce7b commit a22b527
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 0 deletions.
11 changes: 11 additions & 0 deletions utils/src/main/java/software/amazon/awssdk/utils/DateUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,8 @@ public static Instant parseUnixTimestampInstant(String dateString) throws Number
if (dateString == null) {
return null;
}

validateTimestampLength(dateString);
BigDecimal dateValue = new BigDecimal(dateString);
return Instant.ofEpochMilli(dateValue.scaleByPowerOfTen(MILLI_SECOND_PRECISION).longValue());
}
Expand All @@ -225,4 +227,13 @@ public static String formatUnixTimestampInstant(Instant instant) {
return dateValue.scaleByPowerOfTen(0 - MILLI_SECOND_PRECISION)
.toPlainString();
}

private static void validateTimestampLength(String timestamp) {
// Helps avoid BigDecimal parsing unnecessarily large numbers, since it's unbounded
// Long has a max value of 9,223,372,036,854,775,807, which is 19 digits. Assume that a valid timestamp is no
// no longer than 20 characters long (+1 for decimal)
if (timestamp.length() > 20) {
throw new RuntimeException("Input timestamp string must be no longer than 20 characters");
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import static java.time.format.DateTimeFormatter.ISO_OFFSET_DATE_TIME;
import static java.time.format.DateTimeFormatter.RFC_1123_DATE_TIME;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import static software.amazon.awssdk.utils.DateUtils.ALTERNATE_ISO_8601_DATE_FORMAT;
Expand All @@ -39,6 +40,8 @@
import java.util.Locale;
import java.util.TimeZone;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import org.junit.Test;

public class DateUtilsTest {
Expand Down Expand Up @@ -295,4 +298,12 @@ public void testUnixTimestampRoundtrip() throws Exception {
});
}

@Test
public void parseUnixTimestampInstant_longerThan20Char_throws() {
String largeNum = Stream.generate(() -> "9").limit(21).collect(Collectors.joining());
assertThatThrownBy(() -> DateUtils.parseUnixTimestampInstant(largeNum))
.isInstanceOf(RuntimeException.class)
.hasMessageContaining("20");
}

}

0 comments on commit a22b527

Please sign in to comment.