From 34d5925393f2fae9b0edee790a24563422acbfae Mon Sep 17 00:00:00 2001 From: Gary Graham Date: Tue, 25 Feb 2020 09:37:57 -0500 Subject: [PATCH] Move common work to DateUtils. Rename function for clarity. --- .../uhn/fhir/rest/param/DateRangeParam.java | 42 +++++++++---------- .../main/java/ca/uhn/fhir/util/DateUtils.java | 24 +++++++++++ .../dao/predicate/PredicateBuilderDate.java | 22 +++++----- 3 files changed, 54 insertions(+), 34 deletions(-) diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/param/DateRangeParam.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/param/DateRangeParam.java index 8b9a6245b16..d5f491a0f07 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/param/DateRangeParam.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/rest/param/DateRangeParam.java @@ -6,7 +6,7 @@ import ca.uhn.fhir.model.api.TemporalPrecisionEnum; import ca.uhn.fhir.parser.DataFormatException; import ca.uhn.fhir.rest.api.QualifiedParamList; import ca.uhn.fhir.rest.server.exceptions.InvalidRequestException; -import org.apache.commons.lang3.time.DateUtils; +import ca.uhn.fhir.util.DateUtils; import org.hl7.fhir.instance.model.api.IPrimitiveType; import java.util.*; @@ -262,21 +262,29 @@ public class DateRangeParam implements IQueryParameterAnd { validateAndSet(myLowerBound, new DateParam(ParamPrefixEnum.LESSTHAN, theUpperBound)); return this; } - public Integer getLowerBoundAsDateOrdinal() { + + /** + * Return the current lower bound as an integer representative of the date. + * + * e.g. 2019-02-22T04:22:00-0500 -> 20120922 + */ + public Integer getLowerBoundAsDateInteger() { if (myLowerBound == null || myLowerBound.getValue() == null) { return null; } - Calendar cal = DateUtils.toCalendar(myLowerBound.getValue()); - String s = new StringBuilder().append(cal.get(Calendar.YEAR)).append(cal.get(Calendar.MONTH)).append(cal.get(Calendar.DAY_OF_MONTH)).toString(); - return Integer.parseInt(s); + return DateUtils.convertDatetoDayInteger(myLowerBound.getValue()); } - public Integer getUpperBoundAsDateOrdinal() { + + /** + * Return the current upper bound as an integer representative of the date + * + * e.g. 2019-02-22T04:22:00-0500 -> 2019122 + */ + public Integer getUpperBoundAsDateInteger() { if (myUpperBound == null || myUpperBound.getValue() == null) { return null; } - Calendar cal = DateUtils.toCalendar(myUpperBound.getValue()); - String s = new StringBuilder().append(cal.get(Calendar.YEAR)).append(cal.get(Calendar.MONTH)).append(cal.get(Calendar.DAY_OF_MONTH)).toString(); - return Integer.parseInt(s); + return DateUtils.convertDatetoDayInteger(myUpperBound.getValue()); } public Date getLowerBoundAsInstant() { @@ -286,10 +294,7 @@ public class DateRangeParam implements IQueryParameterAnd { Date retVal = myLowerBound.getValue(); if (myLowerBound.getPrecision().ordinal() <= TemporalPrecisionEnum.DAY.ordinal()) { - Calendar cal = DateUtils.toCalendar(retVal); - cal.setTimeZone(TimeZone.getTimeZone("GMT-11:30")); - cal = DateUtils.truncate(cal, Calendar.DATE); - retVal = cal.getTime(); + retVal = DateUtils.getLowestInstantFromDate(retVal); } if (myLowerBound.getPrefix() != null) { @@ -350,17 +355,8 @@ public class DateRangeParam implements IQueryParameterAnd { Date retVal = myUpperBound.getValue(); - - //if (myUpperBound.getPrecision().ordinal() == TemporalPrecisionEnum.DAY.ordinal()) { - // DateUtils.setHours(retVal, 23); - // DateUtils.setMinutes(retVal, 59); -// DateUtils.setSeconds(retVal, 59); -// } if (myUpperBound.getPrecision().ordinal() <= TemporalPrecisionEnum.DAY.ordinal()) { - Calendar cal = DateUtils.toCalendar(retVal); - cal.setTimeZone(TimeZone.getTimeZone("GMT+11:30")); - cal = DateUtils.truncate(cal, Calendar.DATE); - retVal = cal.getTime(); + retVal = DateUtils.getHighestInstantFromDate(retVal); } if (myUpperBound.getPrefix() != null) { diff --git a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/DateUtils.java b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/DateUtils.java index f99ea685652..70b742452f2 100644 --- a/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/DateUtils.java +++ b/hapi-fhir-base/src/main/java/ca/uhn/fhir/util/DateUtils.java @@ -153,6 +153,30 @@ public final class DateUtils { return null; } + + public static Date getHighestInstantFromDate(Date theDateValue) { + return getInstantFromDateWithTimezone(theDateValue, TimeZone.getTimeZone("GMT+11:30")); + + } + public static Date getLowestInstantFromDate(Date theDateValue) { + return getInstantFromDateWithTimezone(theDateValue, TimeZone.getTimeZone("GMT-11:30")); + } + + public static Date getInstantFromDateWithTimezone(Date theDateValue, TimeZone theTimezone) { + Calendar cal = org.apache.commons.lang3.time.DateUtils.toCalendar(theDateValue); + cal.setTimeZone(theTimezone); + cal = org.apache.commons.lang3.time.DateUtils.truncate(cal, Calendar.DATE); + return cal.getTime(); + } + + + public static int convertDatetoDayInteger(final Date theDateValue) { + notNull(theDateValue, "Date value"); + Calendar cal = org.apache.commons.lang3.time.DateUtils.toCalendar(theDateValue); + String s = String.valueOf(cal.get(Calendar.YEAR)) + cal.get(Calendar.MONTH) + cal.get(Calendar.DAY_OF_MONTH); + return Integer.parseInt(s); + } + /** * Formats the given date according to the RFC 1123 pattern. * diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/predicate/PredicateBuilderDate.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/predicate/PredicateBuilderDate.java index b269d4b787f..a04c8a674f5 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/predicate/PredicateBuilderDate.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/dao/predicate/PredicateBuilderDate.java @@ -152,7 +152,7 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi } //im like 80% sure this should be ub and not lb, as it is an UPPER bound. if (isOrdinalComparison) { - lb = theBuilder.lessThan(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateOrdinal()); + lb = theBuilder.lessThan(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateInteger()); } else { lb = theBuilder.lessThan(theFrom.get("myValueLow"), lowerBoundInstant); } @@ -162,7 +162,7 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi } //im like 80% sure this should be ub and not lb, as it is an UPPER bound. if (isOrdinalComparison) { - lb = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateOrdinal()); + lb = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateInteger()); } else { lb = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHigh"), upperBoundInstant); } @@ -171,7 +171,7 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi throw new InvalidRequestException("upperBound value not correctly specified for compare operation"); } if (isOrdinalComparison) { - lb = theBuilder.greaterThan(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateOrdinal()); + lb = theBuilder.greaterThan(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateInteger()); } else { lb = theBuilder.greaterThan(theFrom.get("myValueHigh"), upperBoundInstant); } @@ -180,7 +180,7 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi throw new InvalidRequestException("lowerBound value not correctly specified for compare operation"); } if (isOrdinalComparison) { - lb = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateOrdinal()); + lb = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateInteger()); } else { lb = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueLow"), lowerBoundInstant); } @@ -190,8 +190,8 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi throw new InvalidRequestException("lowerBound and/or upperBound value not correctly specified for compare operation"); } if (isOrdinalComparison){ - lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateOrdinal()); - gt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateOrdinal()); + lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateInteger()); + gt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateInteger()); } else { lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLow"), lowerBoundInstant); gt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueHigh"), upperBoundInstant); @@ -201,8 +201,8 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi } else if ((operation == SearchFilterParser.CompareOperation.eq) || (operation == null)) { if (lowerBoundInstant != null) { if (isOrdinalComparison) { - gt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateOrdinal()); - lt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getLowerBoundAsDateOrdinal()); + gt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getLowerBoundAsDateInteger()); + lt = theBuilder.greaterThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getLowerBoundAsDateInteger()); //also try a strict equality here. } else { @@ -218,8 +218,8 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi if (upperBoundInstant != null) { if (isOrdinalComparison) { - gt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getUpperBoundAsDateOrdinal()); - lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateOrdinal()); + gt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLowDateOrdinal"), theRange.getUpperBoundAsDateInteger()); + lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHighDateOrdinal"), theRange.getUpperBoundAsDateInteger()); } else { gt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueLow"), upperBoundInstant); lt = theBuilder.lessThanOrEqualTo(theFrom.get("myValueHigh"), upperBoundInstant); @@ -235,7 +235,7 @@ public class PredicateBuilderDate extends BasePredicateBuilder implements IPredi operation.name())); } if (isOrdinalComparison) { - ourLog.trace("Ordinal date range is {} - {} ", theRange.getLowerBoundAsDateOrdinal(), theRange.getUpperBoundAsDateOrdinal()); + ourLog.trace("Ordinal date range is {} - {} ", theRange.getLowerBoundAsDateInteger(), theRange.getUpperBoundAsDateInteger()); } ourLog.trace("Date range is {} - {}", lowerBoundInstant, upperBoundInstant);