Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@
import org.eclipse.persistence.internal.expressions.SQLSelectStatement;
import org.eclipse.persistence.internal.helper.BasicTypeHelperImpl;
import org.eclipse.persistence.internal.helper.ClassConstants;
import org.eclipse.persistence.internal.helper.ConversionManager;
import org.eclipse.persistence.internal.helper.DatabaseField;
import org.eclipse.persistence.internal.helper.DatabaseTable;
import org.eclipse.persistence.internal.helper.Helper;
import org.eclipse.persistence.internal.sessions.AbstractRecord;
Expand All @@ -52,11 +54,15 @@
import org.eclipse.persistence.queries.ValueReadQuery;
import org.eclipse.persistence.tools.schemaframework.FieldDefinition;

import static java.sql.Types.TIMESTAMP;

import java.io.IOException;
import java.io.StringWriter;
import java.io.Writer;
import java.sql.Connection;
import java.sql.SQLException;
import java.time.OffsetDateTime;
import java.time.OffsetTime;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Hashtable;
Expand Down Expand Up @@ -338,14 +344,35 @@ protected Hashtable<Class<?>, FieldTypeDefinition> buildFieldTypes() {

fieldTypeMapping.put(java.time.LocalDate.class, new FieldTypeDefinition("DATE"));
fieldTypeMapping.put(java.time.LocalDateTime.class, new FieldTypeDefinition("TIMESTAMP"));
fieldTypeMapping.put(java.time.LocalTime.class, new FieldTypeDefinition("TIME"));
fieldTypeMapping.put(java.time.LocalTime.class, new FieldTypeDefinition("TIME", false));
fieldTypeMapping.put(java.time.OffsetDateTime.class, new FieldTypeDefinition("TIMESTAMP"));
fieldTypeMapping.put(java.time.OffsetTime.class, new FieldTypeDefinition("TIMESTAMP"));
fieldTypeMapping.put(java.time.Instant.class, new FieldTypeDefinition("TIMESTAMP", false));

return fieldTypeMapping;
}

@Override
public int getJDBCTypeForSetNull(DatabaseField field) {

Class<?> javaType = ConversionManager.getObjectClass(field.getType());

// Mirror the mappings for OffsetDateTime and OffsetTime
// as set above for fieldTypeMapping. These differ from the
// usual mapping to TIMESTAMP_WITH_TIMEZONE / TIME_WITH_TIMEZONE

if (javaType == OffsetDateTime.class) {
return TIMESTAMP;
}

if (javaType == OffsetTime.class) {
return TIMESTAMP;
}

return super.getJDBCTypeForSetNull(field);
}


/**
* INTERNAL: returns the maximum number of characters that can be used in a
* field name on this platform.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,17 +12,19 @@

package org.eclipse.persistence.testing.tests.jpa.ddlgeneration;

import jakarta.persistence.EntityManager;

import java.time.LocalDateTime;
import java.time.LocalTime;

import jakarta.persistence.EntityManager;
import junit.framework.Test;
import junit.framework.TestSuite;
import org.eclipse.persistence.internal.databaseaccess.DatabasePlatform;
import org.eclipse.persistence.internal.databaseaccess.Platform;
import org.eclipse.persistence.testing.framework.jpa.junit.JUnitTestCase;
import org.eclipse.persistence.testing.models.jpa.ddlgeneration.DateTimeEntity;

import junit.framework.Test;
import junit.framework.TestSuite;

public class FractionalSecondsPrecisionTest extends JUnitTestCase {

/** Default persistence unit name. */
Expand Down Expand Up @@ -69,56 +71,68 @@ public String getPersistenceUnitName() {
// Test that LocalDateTime returned from the database has precision set in @Column annotation.
// Event column timestamp has secondPrecision set to 5.
public void testLocalDateTimeCustomPrecision() {
// This test makes sense only when platform supports seconds precision in time SQL types
if (supportsFractionalTime()) {
try (EntityManager em = createEntityManager()) {
beginTransaction(em);
try {
em.persist(DATE_TIME_ENTITIES[1]);
commitTransaction(em);
} catch (Exception e) {
if (isTransactionActive(em)) {
rollbackTransaction(em);
}
throw e;
// This test makes sense only when platform supports seconds precision in time SQL type TIMESTAMP
if (!supportsFractionalTime()) {
return;
}

try (EntityManager em = createEntityManager()) {
beginTransaction(em);
try {
em.persist(DATE_TIME_ENTITIES[1]);
commitTransaction(em);
} catch (Exception e) {
if (isTransactionActive(em)) {
rollbackTransaction(em);
}
}
getEntityManagerFactory().getCache().evictAll();
try (EntityManager em = createEntityManager()) {
DateTimeEntity dateTimeEntity = em.createQuery("SELECT e FROM DateTimeEntity e WHERE e.id = :id",
DateTimeEntity.class)
.setParameter("id", 1L)
.getSingleResult();
assertEquals(12345_0000, dateTimeEntity.getLocalDateTime().getNano());
throw e;
}
}

getEntityManagerFactory().getCache().evictAll();

try (EntityManager em = createEntityManager()) {
DateTimeEntity dateTimeEntity =
em.createQuery("SELECT e FROM DateTimeEntity e WHERE e.id = :id", DateTimeEntity.class)
.setParameter("id", 1L)
.getSingleResult();

assertEquals(12345_0000, dateTimeEntity.getLocalDateTime().getNano());
}

}

// Test that LocalTime returned from the database has precision set in @Column annotation.
// Event column timestamp has secondPrecision set to 5.
public void testLocalTimeCustomPrecision() {
// This test makes sense only when platform supports seconds precision in time SQL types
if (supportsFractionalTime()) {
try (EntityManager em = createEntityManager()) {
beginTransaction(em);
try {
em.persist(DATE_TIME_ENTITIES[2]);
commitTransaction(em);
} catch (Exception e) {
if (isTransactionActive(em)) {
rollbackTransaction(em);
}
throw e;
// This test makes sense only when platform supports seconds precision in time SQL type TIME
if (!supportsFractionalTime() || getPlatform().isDB2()) {
// DB2 is a special case. It supports FractionalTime, but only for TIMESTAMP, not for TIME
return;
}

try (EntityManager em = createEntityManager()) {
beginTransaction(em);
try {
em.persist(DATE_TIME_ENTITIES[2]);
commitTransaction(em);
} catch (Exception e) {
if (isTransactionActive(em)) {
rollbackTransaction(em);
}
throw e;
}
getEntityManagerFactory().getCache().evictAll();
try (EntityManager em = createEntityManager()) {
DateTimeEntity dateTimeEntity = em.createQuery("SELECT e FROM DateTimeEntity e WHERE e.id = :id",
DateTimeEntity.class)
.setParameter("id", 2L)
.getSingleResult();
assertEquals(1234_00000, dateTimeEntity.getLocalTime().getNano());
}
}

getEntityManagerFactory().getCache().evictAll();

try (EntityManager em = createEntityManager()) {
DateTimeEntity dateTimeEntity =
em.createQuery("SELECT e FROM DateTimeEntity e WHERE e.id = :id", DateTimeEntity.class)
.setParameter("id", 2L)
.getSingleResult();

assertEquals(1234_00000, dateTimeEntity.getLocalTime().getNano());
}
}

Expand Down
Loading