Skip to content

Commit

Permalink
feature: adds OffsetDateTime converters for Hashes (#195)
Browse files Browse the repository at this point in the history
* OffsetDateTime converters for Hashes

* Adding Test Cases - OffsetDateTime converters for Hashes

---------

Co-authored-by: khushwinder <[email protected]>
  • Loading branch information
codingconquerors and khushwinder authored Feb 20, 2023
1 parent be2e10c commit 196da88
Show file tree
Hide file tree
Showing 6 changed files with 91 additions and 4 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.redis.om.spring.convert;

import org.springframework.core.convert.converter.Converter;
import org.springframework.data.convert.ReadingConverter;

import java.nio.charset.StandardCharsets;
import java.time.Instant;
import java.time.OffsetDateTime;
import java.time.ZoneId;

@ReadingConverter
public class BytesToOffsetDateTimeConverter implements Converter<byte[], OffsetDateTime> {

@Override
public OffsetDateTime convert(byte[] source) {
return OffsetDateTime.ofInstant(Instant.ofEpochMilli(Long.parseLong(toString(source))), ZoneId.systemDefault());
}
String toString(byte[] source) {
return new String(source, StandardCharsets.UTF_8);
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package com.redis.om.spring.convert;

import org.springframework.core.convert.converter.Converter;
import org.springframework.data.convert.WritingConverter;
import org.springframework.stereotype.Component;

import java.nio.charset.StandardCharsets;
import java.time.Instant;
import java.time.OffsetDateTime;
import java.time.ZoneId;

@Component
@WritingConverter
public class OffsetDateTimeToBytesConverter implements Converter<OffsetDateTime, byte[]> {
byte[] fromString(String source) {
return source.getBytes(StandardCharsets.UTF_8);
}

@Override
public byte[] convert(OffsetDateTime source) {
Instant instant = source.atZoneSameInstant(ZoneId.systemDefault()).toInstant();
long timeInMillis = instant.toEpochMilli();

return fromString(Long.toString(timeInMillis));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.redis.om.spring.convert;

import org.springframework.core.convert.converter.Converter;
import org.springframework.data.convert.WritingConverter;
import org.springframework.stereotype.Component;

import java.time.Instant;
import java.time.OffsetDateTime;
import java.time.ZoneId;

@Component
@WritingConverter
public class OffsetDateTimeToStringConverter implements Converter<OffsetDateTime, String> {
@Override
public String convert(OffsetDateTime source) {
Instant instant = source.atZoneSameInstant(ZoneId.systemDefault()).toInstant();
long unixTime = instant.getEpochSecond();
return Long.toString(unixTime);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,10 @@ public class RedisOMCustomConversions extends RedisCustomConversions {
omConverters.add(new LocalDateToBytesConverter());
omConverters.add(new BytesToLocalDateConverter());
omConverters.add(new LocalDateToStringConverter());
// OffsetDateTime
omConverters.add(new OffsetDateTimeToBytesConverter());
omConverters.add(new BytesToOffsetDateTimeConverter());
omConverters.add(new OffsetDateTimeToStringConverter());
// LocalDateTime
omConverters.add(new LocalDateTimeToBytesConverter());
omConverters.add(new BytesToLocalDateTimeConverter());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.OffsetDateTime;
import java.util.Date;
import java.util.List;
import java.util.Set;
Expand All @@ -33,6 +34,9 @@ public class KitchenSink {
private LocalDateTime localDateTime;
@NonNull
@Indexed
private OffsetDateTime localOffsetDateTime;
@NonNull
@Indexed
private Date date;
@NonNull
@Indexed
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,7 @@
import org.springframework.data.geo.Point;
import org.springframework.data.redis.core.StringRedisTemplate;

import java.time.Instant;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.time.*;
import java.time.temporal.ChronoUnit;
import java.util.*;

Expand All @@ -35,6 +32,7 @@

private LocalDate localDate;
private LocalDateTime localDateTime;
private OffsetDateTime localOffsetDateTime;
private Date date;
private Point point;
private Ulid ulid;
Expand All @@ -50,6 +48,7 @@ public void cleanUp() {

localDate = LocalDate.now();
localDateTime = LocalDateTime.now();
localOffsetDateTime = OffsetDateTime.now();
date = new Date();
point = new Point(-111.83592170193586,33.62826024782707);
ulid = UlidCreator.getMonotonicUlid();
Expand All @@ -67,6 +66,7 @@ public void cleanUp() {
ks = KitchenSink.builder() //
.localDate(localDate) //
.localDateTime(localDateTime) //
.localOffsetDateTime(localOffsetDateTime) //
.date(date) //
.point(point) //
.ulid(ulid) //
Expand All @@ -77,6 +77,7 @@ public void cleanUp() {
ks1 = KitchenSink.builder() //
.localDate(localDate) //
.localDateTime(localDateTime) //
.localOffsetDateTime(localOffsetDateTime) //
.date(date) //
.point(point) //
.ulid(ulid) //
Expand All @@ -87,6 +88,7 @@ public void cleanUp() {
ks2 = KitchenSink.builder() //
.localDate(localDate) //
.localDateTime(localDateTime) //
.localOffsetDateTime(localOffsetDateTime) //
.date(date) //
.point(point) //
.ulid(ulid) //
Expand All @@ -98,6 +100,7 @@ public void cleanUp() {
ks3 = KitchenSink.builder() //
.localDate(localDate) //
.localDateTime(localDateTime) //
.localOffsetDateTime(localOffsetDateTime) //
.date(date) //
.point(point) //
.ulid(ulid) //
Expand All @@ -109,6 +112,7 @@ public void cleanUp() {
ks4 = KitchenSink.builder() //
.localDate(localDate) //
.localDateTime(localDateTime) //
.localOffsetDateTime(localOffsetDateTime) //
.date(date) //
.point(point) //
.ulid(ulid) //
Expand All @@ -134,6 +138,11 @@ void testHashSerialization() {
long localDateTimeInMillis = localDateTimeInstant.toEpochMilli();
long rawLocalDateTime = Long.parseLong(Objects.requireNonNull(template.opsForHash().get(key, "localDateTime")).toString());

// OffsetDateTime
Instant localOffsetDateTimeInstant = localOffsetDateTime.atZoneSameInstant(ZoneId.systemDefault()).toInstant();
long localOffsetDateTimeInMillis = localOffsetDateTimeInstant.toEpochMilli();
long rawlocalOffsetDateTime = Long.parseLong(Objects.requireNonNull(template.opsForHash().get(key, "localOffsetDateTime")).toString());

// Date
long dateInMillis = date.getTime();
long rawDate = Long.parseLong(Objects.requireNonNull(template.opsForHash().get(key, "date")).toString());
Expand All @@ -150,6 +159,7 @@ void testHashSerialization() {

assertThat(rawLocalDate).isEqualTo(localDateAsUnixTS);
assertThat(rawLocalDateTime).isEqualTo(localDateTimeInMillis);
assertThat(rawlocalOffsetDateTime).isEqualTo(localOffsetDateTimeInMillis);
assertThat(rawDate).isEqualTo(dateInMillis);
assertThat(rawPoint).isEqualTo(redisGeo);
assertThat(rawUlid).isEqualTo(ulid.toString());
Expand All @@ -168,6 +178,7 @@ void testHashDeserialization() {
// NOTE: We lose nanosecond precision in order to store LocalDateTime as long in
// order to allow for RediSearch range queries
assertThat(fromDb.get().getLocalDateTime()).isEqualToIgnoringNanos(localDateTime);
assertThat(fromDb.get().getLocalOffsetDateTime()).isEqualToIgnoringNanos(localOffsetDateTime);
assertThat(fromDb.get().getSetThings()).isEqualTo(setThings);
assertThat(fromDb.get().getListThings()).isEqualTo(listThings);
}
Expand Down

0 comments on commit 196da88

Please sign in to comment.