Skip to content

Commit

Permalink
Merge pull request #829 from 52North/fix/allow_null_result_time_db
Browse files Browse the repository at this point in the history
Add support for resultTime to be null in the database
  • Loading branch information
CarstenHollmann authored May 27, 2020
2 parents 274250e + 9b575be commit 5f9c1f0
Show file tree
Hide file tree
Showing 19 changed files with 2,069 additions and 466 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -43,4 +43,12 @@ public UnsupportedTimeException(Time time) {
withMessage("Time %s is not supported", time);
}

public UnsupportedTimeException(TimeType referenced, TimeType requested) {
withMessage("%s is not supported with %s", referenced.name(), requested.name());
}

public enum TimeType {
TimePeriod, TimeInstant
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -86,24 +86,25 @@ public final class SosTemporalRestrictions {
* @see DataEntity#PROPERTY_SAMPLING_TIME_START
* @see DataEntity#PROPERTY_SAMPLING_TIME_END
*/
public static final TimePrimitiveFieldDescriptor PHENOMENON_TIME_FIELDS = new TimePrimitiveFieldDescriptor(
public static final AbstractTimePrimitiveFieldDescriptor PHENOMENON_TIME_FIELDS = new TimePrimitiveFieldDescriptor(
DataEntity.PROPERTY_SAMPLING_TIME_START, DataEntity.PROPERTY_SAMPLING_TIME_END);

/**
* Fields describing the result time of a {@code Observation}.
*
* @see DataEntity#PROPERTY_RESULT_TIME
*/
public static final TimePrimitiveFieldDescriptor RESULT_TIME_FIELDS =
new TimePrimitiveFieldDescriptor(DataEntity.PROPERTY_RESULT_TIME);
public static final AbstractTimePrimitiveFieldDescriptor RESULT_TIME_FIELDS =
new TimePrimitiveNullableFieldDescriptor(DataEntity.PROPERTY_RESULT_TIME,
new TimePrimitiveFieldDescriptor(DataEntity.PROPERTY_SAMPLING_TIME_END));

/**
* Fields describing the valid time of a {@code Observation}.
*
* @see DataEntity#PROPERTY_VALID_TIME_START
* @see DataEntity#PROPERTY_VALID_TIME_END
*/
public static final TimePrimitiveFieldDescriptor VALID_TIME_FIELDS =
public static final AbstractTimePrimitiveFieldDescriptor VALID_TIME_FIELDS =
new TimePrimitiveFieldDescriptor(DataEntity.PROPERTY_VALID_TIME_START, DataEntity.PROPERTY_VALID_TIME_END);

/**
Expand All @@ -112,7 +113,7 @@ public final class SosTemporalRestrictions {
* @see ProcedureHistoryEntity#START_TIME
* @see ProcedureHistoryEntity#END_TIME
*/
public static final TimePrimitiveFieldDescriptor VALID_TIME_DESCRIBE_SENSOR_FIELDS =
public static final AbstractTimePrimitiveFieldDescriptor VALID_TIME_DESCRIBE_SENSOR_FIELDS =
new TimePrimitiveFieldDescriptor(ProcedureHistoryEntity.START_TIME, ProcedureHistoryEntity.END_TIME);

/**
Expand Down Expand Up @@ -263,7 +264,7 @@ private static Collection<Disjunction> getDisjunctionHql(Iterable<TemporalFilter
* @throws UnsupportedValueReferenceException
* if the {@code valueReference} can not be decoded
*/
public static TimePrimitiveFieldDescriptor getFields(String valueReference)
public static AbstractTimePrimitiveFieldDescriptor getFields(String valueReference)
throws UnsupportedValueReferenceException {
if (valueReference.contains(TemporalRestrictions.PHENOMENON_TIME_VALUE_REFERENCE)) {
return PHENOMENON_TIME_FIELDS;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,36 +28,34 @@
*/
package org.n52.sos.ds.hibernate.util;

/**
* Test with instant as temporal filter
*
* @author <a href="mailto:c.hollman@52north.org">Carsten Hollmann</a>
*
* @since 4.4.0
*/
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.MatcherAssert.assertThat;

import org.hibernate.criterion.Criterion;
import org.joda.time.DateTime;
import org.junit.Test;
import org.n52.shetland.ogc.filter.FilterConstants;
import org.n52.shetland.ogc.filter.TemporalFilter;
import org.n52.shetland.ogc.gml.time.TimeInstant;
import org.n52.shetland.ogc.ows.exception.OwsExceptionReport;
import org.n52.sos.ds.hibernate.ExtendedHibernateTestCase;
import org.n52.sos.ds.hibernate.util.SosTemporalRestrictions;
import org.n52.sos.exception.ows.concrete.UnsupportedOperatorException;
import org.n52.sos.exception.ows.concrete.UnsupportedTimeException;
import org.n52.sos.exception.ows.concrete.UnsupportedValueReferenceException;

public class TemporalRestrictionHqlInstantInstantTest extends ExtendedHibernateTestCase
implements TemporalRestrictionTestConstants {
/**
* Test with instant as temporal filter
*
* @author <a href="mailto:c.hollman@52north.org">Carsten Hollmann</a>
*
* @since 4.4.0
*/
public class TemporalRestrictionHqlInstantInstantTest implements TemporalRestrictionTestConstants {

private static final String STE_LT_INSTANT = "samplingTimeEnd<:instant1";

private static final String STS_GT_INSTANT_AND_STE_LT_INSTANT =
"samplingTimeStart>:instant1 and samplingTimeEnd<:instant1";

private static final String RT_GT_INSTANT_AND_RT_LT_INSTANT = "resultTime>:instant1 and resultTime<:instant1";

@Test
public void testAfterPhenomenonTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
Expand All @@ -66,14 +64,6 @@ public void testAfterPhenomenonTime()
assertThat(filterHql.toString(), equalTo("samplingTimeStart>:instant1"));
}

@Test
public void testAfterResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_After, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("resultTime>:instant1"));
}

@Test
public void testBeforePhenomenonTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
Expand All @@ -82,14 +72,6 @@ public void testBeforePhenomenonTime()
assertThat(filterHql.toString(), equalTo("samplingTimeEnd<:instant1"));
}

@Test
public void testBeforeResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Before, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("resultTime<:instant1"));
}

@Test
public void testEqualsPhenomenonTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
Expand All @@ -98,29 +80,13 @@ public void testEqualsPhenomenonTime()
assertThat(filterHql.toString(), equalTo("samplingTimeStart=:instant1 and samplingTimeEnd=:instant1"));
}

@Test
public void testEqualsResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Equals, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("resultTime=:instant1"));
}

@Test
public void testContainsPhenomenonTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Contains, PHENOMENON_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testContainsResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Contains, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(RT_GT_INSTANT_AND_RT_LT_INSTANT));
}

@Test(expected = UnsupportedTimeException.class)
public void testDuringPhenomenonTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
Expand All @@ -129,26 +95,12 @@ public void testDuringPhenomenonTime()
assertThat(filterHql.toString(), equalTo(STS_GT_INSTANT_AND_STE_LT_INSTANT));
}

@Test(expected = UnsupportedTimeException.class)
public void testDuringResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_During, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("resultTime>:resultTime1 and resultTime<:resultTime1"));
}

@Test(expected = UnsupportedTimeException.class)
public void testBeginsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Begins, PHENOMENON_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testBeginsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Begins, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test
public void testBegunByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_BegunBy, PHENOMENON_TIME);
Expand All @@ -157,81 +109,130 @@ public void testBegunByPhenomenonTime() throws OwsExceptionReport {
}

@Test(expected = UnsupportedTimeException.class)
public void testBegunByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_BegunBy, RESULT_TIME);
public void testEndsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Ends, PHENOMENON_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test
public void testEndedByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_EndedBy, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("samplingTimeEnd=:instant1"));
}

@Test(expected = UnsupportedTimeException.class)
public void testEndsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Ends, PHENOMENON_TIME);
public void testOverlapsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Overlaps, PHENOMENON_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testEndsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Ends, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
public void testOverlappedByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_OverlappedBy, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STE_LT_INSTANT));
}

@Test(expected = UnsupportedTimeException.class)
public void testMeetsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Meets, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STS_GT_INSTANT_AND_STE_LT_INSTANT));
}

@Test(expected = UnsupportedTimeException.class)
public void testMetByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_MetBy, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STS_GT_INSTANT_AND_STE_LT_INSTANT));
}

@Test
public void testEndedByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_EndedBy, PHENOMENON_TIME);
public void testAfterResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_After, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo("samplingTimeEnd=:instant1"));
assertThat(filterHql.toString(), equalTo(
"((resultTime is not null and resultTime>:instant1) or (resultTime is null and samplingTimeEnd>:instant1))"));
}

@Test
public void testBeforeResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Before, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(
"((resultTime is not null and resultTime<:instant1) or (resultTime is null and samplingTimeEnd<:instant1))"));
}

@Test
public void testEqualsResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Equals, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(
"((resultTime is not null and resultTime=:instant1) or (resultTime is null and samplingTimeEnd=:instant1))"));
}

@Test(expected = UnsupportedTimeException.class)
public void testEndedByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_EndedBy, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
public void testContainsResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Contains, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(
"((resultTime is not null and resultTime>:instant1 and resultTime<:instant1) or (resultTime is null and samplingTimeEnd>:instant1 and samplingTimeEnd<:instant1))"));
}

@Test(expected = UnsupportedTimeException.class)
public void testOverlapsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Overlaps, PHENOMENON_TIME);
public void testDuringResultTime()
throws UnsupportedValueReferenceException, UnsupportedTimeException, UnsupportedOperatorException {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_During, RESULT_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(
"((resultTime is not null and resultTime>:resultTime1 and resultTime<:resultTime1) or (resultTime is null and samplingTimeEnd>:resultTime1 and samplingTimeEnd<:resultTime1))"));
}

@Test(expected = UnsupportedTimeException.class)
public void testBeginsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Begins, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testOverlapsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Overlaps, RESULT_TIME);
public void testBegunByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_BegunBy, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testOverlappedByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_OverlappedBy, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STE_LT_INSTANT));
public void testEndsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Ends, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testOverlappedByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_OverlappedBy, RESULT_TIME);
public void testEndedByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_EndedBy, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testMeetsPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Meets, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STS_GT_INSTANT_AND_STE_LT_INSTANT));
public void testOverlapsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Overlaps, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testMeetsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Meets, RESULT_TIME);
public void testOverlappedByResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_OverlappedBy, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
public void testMetByPhenomenonTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_MetBy, PHENOMENON_TIME);
Criterion filterHql = SosTemporalRestrictions.filterHql(tf, 1);
assertThat(filterHql.toString(), equalTo(STS_GT_INSTANT_AND_STE_LT_INSTANT));
public void testMeetsResultTime() throws OwsExceptionReport {
TemporalFilter tf = create(FilterConstants.TimeOperator.TM_Meets, RESULT_TIME);
SosTemporalRestrictions.filterHql(tf, 1);
}

@Test(expected = UnsupportedTimeException.class)
Expand Down
Loading

0 comments on commit 5f9c1f0

Please sign in to comment.