blob: aae2da0b87ec7fd5db177091f8b2e53f9ed8600e [file] [log] [blame]
package org.apache.rya.api.resolver.impl;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import java.util.Date;
import java.util.GregorianCalendar;
import javax.xml.datatype.DatatypeFactory;
import javax.xml.datatype.XMLGregorianCalendar;
import org.apache.rya.api.domain.RyaType;
import org.apache.rya.api.resolver.RdfToRyaConversions;
import org.apache.rya.api.resolver.RyaTypeResolverException;
import org.eclipse.rdf4j.model.IRI;
import org.eclipse.rdf4j.model.Literal;
import org.eclipse.rdf4j.model.ValueFactory;
import org.eclipse.rdf4j.model.impl.SimpleValueFactory;
import org.eclipse.rdf4j.model.vocabulary.XMLSchema;
import org.junit.Test;
/**
* Test serializing and deserializing.
* Notes:
* The serialization, deserialization fills in some information:
* If preserving uncertainty, or preserving the source timezone, then don't use XML type tag.
* - uncertainty: missing time hh:mm:ss becomes 00:00:00
* - uncertainty: missing milliseconds (.123) become .000.
* - uncertainty: missing timezone becomes the system local timezone.
* - timezone: converted to the equivalent Z timezone.
* - a type XMLSchema.DATE become XMLSchema.DATETIME after deserialized
*
* ex: run in timezone eastern time (GMT-5:00):
* before= 2000-02-02 type = XMLSchema.DATE
* deserialized= 2000-02-02T05:00:00.000Z type = XMLSchema.DATETIME
*/
public class DateTimeRyaTypeResolverTest {
private static final ValueFactory VF = SimpleValueFactory.getInstance();
@Test
public void testDateTime() throws Exception {
long currentTime = 1342182689285l;
Date date = new Date(currentTime);
GregorianCalendar gc = new GregorianCalendar();
gc.setTimeInMillis(date.getTime());
XMLGregorianCalendar xmlGregorianCalendar = DatatypeFactory.newInstance().newXMLGregorianCalendar(gc);
Literal literal = VF.createLiteral(xmlGregorianCalendar);
byte[] serialize = new DateTimeRyaTypeResolver().serialize(RdfToRyaConversions.convertLiteral(literal));
RyaType deserialize = new DateTimeRyaTypeResolver().deserialize(serialize);
assertEquals("2012-07-13T12:31:29.285Z", deserialize.getData());
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
@Test
public void testFull() throws Exception {
String currentTime = "2000-01-01T00:00:01.111Z";
assertSerializeAndDesDateTime("2000-01-01T00:00:01.111Z");
}
@Test
public void testNoMilliSeconds() throws Exception {
assertSerializeAndDesDateTime("2000-01-01T00:00:01Z","2000-01-01T00:00:01.000Z");
}
@Test
public void testDateNoTimeNoZone() throws Exception {
String beforeDate = "2000-02-02";
String afterDate="2000-02-0(1|2|3)T\\d\\d:\\d\\d:00\\.000Z";
RyaType deserialize = serializeAndDeserialize(beforeDate, XMLSchema.DATE);
final String afterActual = deserialize.getData();
assertTrue("Before='"+beforeDate+"'; Expected should match actual regex after='"+afterDate+"' deserialized:"+afterActual, afterActual.matches(afterDate));
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
@Test
public void testDateZoneNoTime() throws Exception {
// if you see this:
//java.lang.IllegalArgumentException: Invalid format: "2000-02-02Z" is malformed at "Z"
// use this: "2000-02-02TZ";
String currentTime = "2000-02-02TZ";
RyaType deserialize = serializeAndDeserialize(currentTime, XMLSchema.DATE);
assertEquals("Before expected should match after actual deserialized:","2000-02-02T00:00:00.000Z", deserialize.getData());
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
@Test
public void testNoZone() throws Exception {
String beforeDate = "2000-01-02T00:00:01";
String afterDate="2000-01-0(1|2|3)T\\d\\d:\\d\\d:01\\.000Z";
RyaType deserialize = serializeAndDeserialize(beforeDate, XMLSchema.DATE);
final String afterActual = deserialize.getData();
assertTrue("Before='"+beforeDate+"'; Expected should match actual regex after='"+afterDate+"' deserialized:"+afterActual, afterActual.matches(afterDate));
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
@Test
public void testMilliSecondsNoZone() throws Exception {
String beforeDate="2002-02-02T02:02:02.222";
String afterDate="2002-02-0(1|2|3)T\\d\\d:\\d\\d:02\\.222.*";
RyaType deserialize = serializeAndDeserialize(beforeDate, XMLSchema.DATETIME);
final String afterActual = deserialize.getData();
assertTrue("Before='"+beforeDate+"'; Expected should match actual regex after='"+afterDate+"' deserialized:"+afterActual, afterActual.matches(afterDate));
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
@Test
public void testHistoryAndFuture() throws Exception {
assertSerializeAndDesDateTime("-2000-01-01T00:00:01Z","-2000-01-01T00:00:01.000Z");
assertSerializeAndDesDateTime("111-01-01T00:00:01Z","0111-01-01T00:00:01.000Z");
assertSerializeAndDesDateTime("12345-01-01T00:00:01Z","12345-01-01T00:00:01.000Z");
}
@Test
public void testTimeZone() throws Exception {
assertSerializeAndDesDateTime( "2000-01-01T00:00:01+01:00", "1999-12-31T23:00:01.000Z");
assertSerializeAndDesDateTime( "2000-01-01T00:00:01+02:30", "1999-12-31T21:30:01.000Z");
assertSerializeAndDesDateTime("2000-01-01T00:00:01.123-02:00", "2000-01-01T02:00:01.123Z");
assertSerializeAndDesDateTime( "111-01-01T00:00:01+14:00", "0110-12-31T10:00:01.000Z" );
assertSerializeAndDesDateTime( "12345-01-01T00:00:01-14:00","12345-01-01T14:00:01.000Z");
assertSerializeAndDesDateTime( "1-01-01T00:00:01+14:00", "0000-12-31T10:00:01.000Z" );
}
@Test
public void testGarbageIn() throws Exception {
String currentTime = "Blablabla";
RyaType ryaType = new RyaType(XMLSchema.DATETIME, currentTime );
Throwable threw=null;
try {
new DateTimeRyaTypeResolver().serialize(ryaType);
} catch (java.lang.IllegalArgumentException exception) {
threw = exception;
}
assertNotNull("Expected to catch bad format message.",threw);
assertEquals("Caught bad format message.","Invalid format: \"Blablabla\"", threw.getMessage());
}
/**
* Do the test on the DateTime
* @param dateTimeString
* @throws RyaTypeResolverException
*/
private void assertSerializeAndDesDateTime(String dateTimeString) throws RyaTypeResolverException {
assertSerializeAndDesDateTime(dateTimeString, dateTimeString);
}
private void assertSerializeAndDesDateTime(String beforeDate, String afterDate ) throws RyaTypeResolverException {
RyaType deserialize = serializeAndDeserialize(beforeDate, XMLSchema.DATETIME);
assertEquals("Before='"+beforeDate+"'; Expected should match actual after deserialized:",afterDate, deserialize.getData());
assertEquals(XMLSchema.DATETIME, deserialize.getDataType());
}
/**
* Serialize a datetime string, then deserialize as a ryaType.
* @param dateTimeString
* @param type if null , use default: XMLSchema.DATETIME
* @return
* @throws RyaTypeResolverException
*/
private RyaType serializeAndDeserialize(String dateTimeString, IRI type ) throws RyaTypeResolverException {
if (type == null)
type = XMLSchema.DATETIME;
RyaType ryaType = new RyaType(type, dateTimeString );
byte[] serialize = new DateTimeRyaTypeResolver().serialize(ryaType);
return new DateTimeRyaTypeResolver().deserialize(serialize);
}
}