Skip to content
This repository has been archived by the owner on Dec 3, 2023. It is now read-only.

fix: fix conversion for pre-epoch timestamps #160

Merged
merged 3 commits into from Feb 25, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
14 changes: 13 additions & 1 deletion google-cloud-core/src/main/java/com/google/cloud/Timestamp.java
Expand Up @@ -119,7 +119,19 @@ public static Timestamp now() {
* @throws IllegalArgumentException if the timestamp is outside the representable range
*/
public static Timestamp of(java.sql.Timestamp timestamp) {
return ofTimeSecondsAndNanos(timestamp.getTime() / 1000, timestamp.getNanos());
int nanos = timestamp.getNanos();

// A pre-epoch timestamp will be off by one second because of the way that integer division
// works. For example, -1001 / 1000 == -1. In this case of timestamps, we want this result to be
// -2. This causes any pre-epoch timestamp to be off by 1 second - fix this by adjusting the
// seconds value by 1 if the timestamp < 0.
// TODO: replace with Math.floorDiv when we drop Java 7 support
long seconds = timestamp.getTime() / 1000;
if (seconds < 0) {
--seconds;
}

return Timestamp.ofTimeSecondsAndNanos(seconds, nanos);
}

/**
Expand Down
Expand Up @@ -80,6 +80,30 @@ public void ofDate() {
assertThat(timestamp.getNanos()).isEqualTo(expectedNanos);
}

@Test
public void ofSqlTimestamp() {
String expectedTimestampString = "1970-01-01T00:00:12.345000000Z";
java.sql.Timestamp input = new java.sql.Timestamp(12345);
Timestamp timestamp = Timestamp.of(input);
assertThat(timestamp.toString()).isEqualTo(expectedTimestampString);
}

@Test
public void ofSqlTimestampPreEpoch() {
String expectedTimestampString = "1969-12-31T23:59:47.655000000Z";
java.sql.Timestamp input = new java.sql.Timestamp(-12345);
Timestamp timestamp = Timestamp.of(input);
assertThat(timestamp.toString()).isEqualTo(expectedTimestampString);
}

@Test
public void ofSqlTimestampOnEpoch() {
String expectedTimestampString = "1970-01-01T00:00:00Z";
java.sql.Timestamp input = new java.sql.Timestamp(0);
Timestamp timestamp = Timestamp.of(input);
assertThat(timestamp.toString()).isEqualTo(expectedTimestampString);
}

@Test
public void ofDatePreEpoch() {
Timestamp timestamp = Timestamp.of(TEST_DATE_PRE_EPOCH);
Expand Down