diff --git a/foundation/org.eclipse.persistence.core/src/main/java/org/eclipse/persistence/internal/localization/i18n/LoggingLocalizationResource.java b/foundation/org.eclipse.persistence.core/src/main/java/org/eclipse/persistence/internal/localization/i18n/LoggingLocalizationResource.java index 1de9ac1d8b4..625ce2cf07e 100644 --- a/foundation/org.eclipse.persistence.core/src/main/java/org/eclipse/persistence/internal/localization/i18n/LoggingLocalizationResource.java +++ b/foundation/org.eclipse.persistence.core/src/main/java/org/eclipse/persistence/internal/localization/i18n/LoggingLocalizationResource.java @@ -475,10 +475,7 @@ public class LoggingLocalizationResource extends ListResourceBundle { { "dbws_oxm_metadata_read_error", "The [{0}] OXM metadata could not be read."}, { "dbws_no_wsdl_inline_schema", "The [{0}] WSDL inline schema could not be read."}, // JPA 3.2 - { "unknown_cacheRetrieveMode_type", "Unknown {0} type of jakarta.persistence.cache.retrieveMode property"}, - { "unknown_cacheStoreMode_type", "Unknown {0} type of jakarta.persistence.cache.storeMode property"}, - { "unknown_queryTimeoutUnit_type", "Unknown {0} type of eclipselink.query.timeout.unit property"}, - { "unknown_queryTimeout_type", "Unknown {0} type of jakarta.persistence.query.timeout property"}, + { "unknown_property_type", "Unknown {0} type of {1} persistence property"}, { "error_queryTimeoutParse", "Could not parse jakarta.persistence.query.timeout property value {0}: {1}"}, { "validate_object_space", "validate object space." }, diff --git a/jpa/eclipselink.jpa.test.jse/src/it/java/org/eclipse/persistence/jpa/test/query/model/TestQueryEqualTo.java b/jpa/eclipselink.jpa.test.jse/src/it/java/org/eclipse/persistence/jpa/test/query/model/TestQueryEqualTo.java new file mode 100644 index 00000000000..073452ccf6a --- /dev/null +++ b/jpa/eclipselink.jpa.test.jse/src/it/java/org/eclipse/persistence/jpa/test/query/model/TestQueryEqualTo.java @@ -0,0 +1,245 @@ +/* + * Copyright (c) 1998, 2023 Oracle and/or its affiliates. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v. 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0, + * or the Eclipse Distribution License v. 1.0 which is available at + * http://www.eclipse.org/org/documents/edl-v10.php. + * + * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause + */ + +// Contributors: +// 10/25/2023: Tomas Kraus +// - New Jakarta Persistence 3.2 Features +package org.eclipse.persistence.jpa.test.query.model; + +import java.util.List; + +import jakarta.persistence.EntityManager; +import jakarta.persistence.EntityManagerFactory; +import jakarta.persistence.TypedQuery; +import jakarta.persistence.criteria.CriteriaBuilder; +import jakarta.persistence.criteria.CriteriaQuery; +import jakarta.persistence.criteria.ParameterExpression; +import jakarta.persistence.criteria.Root; +import org.eclipse.persistence.jpa.test.framework.DDLGen; +import org.eclipse.persistence.jpa.test.framework.Emf; +import org.eclipse.persistence.jpa.test.framework.EmfRunner; +import org.eclipse.persistence.jpa.test.framework.Property; +import org.junit.Test; +import org.junit.runner.RunWith; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertTrue; + +@RunWith(EmfRunner.class) +public class TestQueryEqualTo { + + @Emf(createTables = DDLGen.DROP_CREATE, classes = { EntityTbl01.class }, + properties = { @Property(name="eclipselink.logging.level", value="FINE")}) + private EntityManagerFactory emf; + + private static boolean POPULATED = false; + + @Test + public void testQueryEqualToExpression() { + if (!POPULATED) + populate(); + + EntityManager em = emf.createEntityManager(); + + try { + TypedQuery query = em.createQuery( + "SELECT t.KeyString FROM EntityTbl01 t " + + "WHERE t.KeyString = ?1", String.class); + query.setParameter(1, "EqualTo_1"); + List dto01 = query.getResultList(); + assertNotNull(dto01); + assertEquals(1, dto01.size()); + + // equivalent CriteriaBuilder + CriteriaBuilder cb = em.getCriteriaBuilder(); + CriteriaQuery cquery = cb.createQuery(String.class); + Root root = cquery.from(EntityTbl01.class); + ParameterExpression strParam1 = cb.parameter(String.class); + cquery.multiselect(root.get(EntityTbl01_.KeyString)); + cquery.where(root.get(EntityTbl01_.KeyString).equalTo(strParam1)); + query = em.createQuery(cquery); + query.setParameter(strParam1, "EqualTo_1"); + dto01 = query.getResultList(); + assertNotNull(dto01); + assertEquals(1, dto01.size()); + } finally { + if (em.getTransaction().isActive()) { + em.getTransaction().rollback(); + } + if(em.isOpen()) { + em.close(); + } + } + } + + @Test + public void testQueryEqualToObject() { + if (!POPULATED) + populate(); + + EntityManager em = emf.createEntityManager(); + + try { + TypedQuery query = em.createQuery( + "SELECT t.KeyString FROM EntityTbl01 t " + + "WHERE t.KeyString = 'EqualTo_2'", String.class); + List dto01 = query.getResultList(); + assertNotNull(dto01); + assertEquals(1, dto01.size()); + + // equivalent CriteriaBuilder + CriteriaBuilder cb = em.getCriteriaBuilder(); + CriteriaQuery cquery = cb.createQuery(String.class); + Root root = cquery.from(EntityTbl01.class); + cquery.multiselect(root.get(EntityTbl01_.KeyString)); + cquery.where(root.get(EntityTbl01_.KeyString).equalTo("EqualTo_2")); + query = em.createQuery(cquery); + dto01 = query.getResultList(); + assertNotNull(dto01); + assertEquals(1, dto01.size()); + } finally { + if (em.getTransaction().isActive()) { + em.getTransaction().rollback(); + } + if(em.isOpen()) { + em.close(); + } + } + } + + @Test + public void testQueryNotEqualToExpression() { + if (!POPULATED) + populate(); + + EntityManager em = emf.createEntityManager(); + + try { + TypedQuery query = em.createQuery( + "SELECT t.KeyString FROM EntityTbl01 t " + + "WHERE t.KeyString <> ?1", String.class); + query.setParameter(1, "EqualTo_3"); + List dto01 = query.getResultList(); + assertNotNull(dto01); + assertTrue(dto01.size() > 1); + + // equivalent CriteriaBuilder + CriteriaBuilder cb = em.getCriteriaBuilder(); + CriteriaQuery cquery = cb.createQuery(String.class); + Root root = cquery.from(EntityTbl01.class); + ParameterExpression strParam1 = cb.parameter(String.class); + cquery.multiselect(root.get(EntityTbl01_.KeyString)); + cquery.where(root.get(EntityTbl01_.KeyString).notEqualTo(strParam1)); + query = em.createQuery(cquery); + query.setParameter(strParam1, "EqualTo_3"); + dto01 = query.getResultList(); + assertNotNull(dto01); + assertTrue(dto01.size() > 1); + } finally { + if (em.getTransaction().isActive()) { + em.getTransaction().rollback(); + } + if(em.isOpen()) { + em.close(); + } + } + } + + @Test + public void testQueryNotEqualToObject() { + if (!POPULATED) + populate(); + + EntityManager em = emf.createEntityManager(); + + try { + TypedQuery query = em.createQuery( + "SELECT t.KeyString FROM EntityTbl01 t " + + "WHERE t.KeyString <> 'EqualTo_4'", String.class); + List dto01 = query.getResultList(); + assertNotNull(dto01); + assertTrue(dto01.size() > 1); + + // equivalent CriteriaBuilder + CriteriaBuilder cb = em.getCriteriaBuilder(); + CriteriaQuery cquery = cb.createQuery(String.class); + Root root = cquery.from(EntityTbl01.class); + cquery.multiselect(root.get(EntityTbl01_.KeyString)); + cquery.where(root.get(EntityTbl01_.KeyString).notEqualTo("EqualTo_4")); + query = em.createQuery(cquery); + dto01 = query.getResultList(); + assertNotNull(dto01); + assertTrue(dto01.size() > 1); + } finally { + if (em.getTransaction().isActive()) { + em.getTransaction().rollback(); + } + if(em.isOpen()) { + em.close(); + } + } + } + + private void populate() { + EntityManager em = emf.createEntityManager(); + try { + em.getTransaction().begin(); + + EntityTbl01 tbl1 = new EntityTbl01(); + tbl1.setKeyString("EqualTo_1"); + tbl1.setItemString1("A"); + tbl1.setItemString2(null); + tbl1.setItemString3("C"); + tbl1.setItemString4("D"); + tbl1.setItemInteger1(45); + em.persist(tbl1); + + EntityTbl01 tbl2 = new EntityTbl01(); + tbl2.setKeyString("EqualTo_2"); + tbl2.setItemString1("A"); + tbl2.setItemString2("B"); + tbl2.setItemString3("C"); + tbl2.setItemString4(null); + tbl2.setItemInteger1(83); + em.persist(tbl2); + + EntityTbl01 tbl3 = new EntityTbl01(); + tbl3.setKeyString("EqualTo_3"); + tbl3.setItemString1(null); + tbl3.setItemString2("B"); + tbl3.setItemString3("C"); + tbl3.setItemString4("D"); + tbl3.setItemInteger1(17); + em.persist(tbl3); + + EntityTbl01 tbl4 = new EntityTbl01(); + tbl4.setKeyString("EqualTo_4"); + tbl4.setItemString1("A"); + tbl4.setItemString2("B"); + tbl4.setItemString3("C"); + tbl4.setItemString4(null); + tbl4.setItemInteger1(29); + em.persist(tbl4); + + em.getTransaction().commit(); + + POPULATED = true; + } finally { + if(em.isOpen()) { + em.close(); + } + } + } + + +} diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EJBQueryImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EJBQueryImpl.java index 8953db3049d..a47f1d8c4f8 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EJBQueryImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EJBQueryImpl.java @@ -41,10 +41,7 @@ import jakarta.persistence.Parameter; import jakarta.persistence.PersistenceException; import jakarta.persistence.TemporalType; -import jakarta.persistence.Timeout; import jakarta.persistence.TypedQuery; - -import org.eclipse.persistence.config.QueryHints; import org.eclipse.persistence.exceptions.QueryException; import org.eclipse.persistence.expressions.Expression; import org.eclipse.persistence.internal.databaseaccess.DatasourcePlatform; @@ -56,8 +53,6 @@ import org.eclipse.persistence.internal.queries.JPQLCallQueryMechanism; import org.eclipse.persistence.internal.sessions.AbstractSession; import org.eclipse.persistence.jpa.JpaQuery; -import org.eclipse.persistence.logging.AbstractSessionLog; -import org.eclipse.persistence.logging.SessionLog; import org.eclipse.persistence.queries.Cursor; import org.eclipse.persistence.queries.DataReadQuery; import org.eclipse.persistence.queries.DatabaseQuery; @@ -309,7 +304,7 @@ public EJBQueryImpl setLockMode(LockModeType lockMode) { // Based on EntityManagerImpl#getQueryHints(Object,OperationType) @Override public CacheRetrieveMode getCacheRetrieveMode() { - return FindOptionUtils.getCacheRetrieveMode(getDatabaseQuery().getProperties()); + return FindOptionUtils.getCacheRetrieveMode(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } @Override @@ -320,7 +315,7 @@ public TypedQuery setCacheRetrieveMode(CacheRetrieveMode cacheRetrieveMode) { @Override public CacheStoreMode getCacheStoreMode() { - return FindOptionUtils.getCacheStoreMode(getDatabaseQuery().getProperties()); + return FindOptionUtils.getCacheStoreMode(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } @Override @@ -331,7 +326,7 @@ public TypedQuery setCacheStoreMode(CacheStoreMode cacheStoreMode) { @Override public Integer getTimeout() { - return FindOptionUtils.getTimeout(getDatabaseQuery().getProperties()); + return FindOptionUtils.getTimeout(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } @Override diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EntityManagerImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EntityManagerImpl.java index c20f1c3668e..9eaae4575f5 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EntityManagerImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/EntityManagerImpl.java @@ -2918,7 +2918,7 @@ public LockModeType getLockMode(Object entity) { @Override public CacheRetrieveMode getCacheRetrieveMode() { - return FindOptionUtils.getCacheRetrieveMode(properties); + return FindOptionUtils.getCacheRetrieveMode(getAbstractSession(), properties); } @Override @@ -2928,7 +2928,7 @@ public void setCacheRetrieveMode(CacheRetrieveMode cacheRetrieveMode) { @Override public CacheStoreMode getCacheStoreMode() { - return FindOptionUtils.getCacheStoreMode(properties); + return FindOptionUtils.getCacheStoreMode(getAbstractSession(), properties); } @Override diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/FindOptionUtils.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/FindOptionUtils.java index ffd9ddab344..a32dbf475f9 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/FindOptionUtils.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/FindOptionUtils.java @@ -27,12 +27,9 @@ import jakarta.persistence.LockModeType; import jakarta.persistence.PessimisticLockScope; import jakarta.persistence.Timeout; -import jakarta.persistence.TypedQuery; import org.eclipse.persistence.config.QueryHints; import org.eclipse.persistence.internal.sessions.AbstractSession; -import org.eclipse.persistence.logging.AbstractSessionLog; import org.eclipse.persistence.logging.SessionLog; -import org.eclipse.persistence.queries.DatabaseQuery; /** * {@link FindOption} processing tools. @@ -151,16 +148,17 @@ static Options parse(Map properties, FindOption... options) { } // Based on EntityManagerImpl#getQueryHints(Object,OperationType) - static CacheRetrieveMode getCacheRetrieveMode(Map properties) { + static CacheRetrieveMode getCacheRetrieveMode(AbstractSession session, Map properties) { // QueryHints property Object propertyValue = properties.get(QueryHints.CACHE_RETRIEVE_MODE); if (propertyValue instanceof CacheRetrieveMode) { return (CacheRetrieveMode) propertyValue; } else if (propertyValue != null) { - AbstractSessionLog.getLog().log(SessionLog.WARNING, - SessionLog.QUERY, - "unknown_cacheRetrieveMode_type", - propertyValue.getClass().getName()); + session.log(SessionLog.WARNING, + SessionLog.QUERY, + "unknown_property_type", + propertyValue.getClass().getName(), + QueryHints.CACHE_RETRIEVE_MODE); } // Default value according to JPA spec. return CacheRetrieveMode.USE; @@ -171,16 +169,17 @@ static void setCacheRetrieveMode(Map properties, CacheRetrieveMode ca ((Map)properties).put(QueryHints.CACHE_RETRIEVE_MODE, cacheRetrieveMode); } - static CacheStoreMode getCacheStoreMode(Map properties) { + static CacheStoreMode getCacheStoreMode(AbstractSession session, Map properties) { // QueryHints property Object propertyValue = properties.get(QueryHints.CACHE_STORE_MODE); if (propertyValue instanceof CacheStoreMode) { return (CacheStoreMode) propertyValue; } else if (propertyValue != null) { - AbstractSessionLog.getLog().log(SessionLog.WARNING, - SessionLog.QUERY, - "unknown_cacheStoreMode_type", - propertyValue.getClass().getName()); + session.log(SessionLog.WARNING, + SessionLog.QUERY, + "unknown_property_type", + propertyValue.getClass().getName(), + QueryHints.CACHE_STORE_MODE); } // Default value according to JPA spec. return CacheStoreMode.USE; @@ -191,17 +190,18 @@ static void setCacheStoreMode(Map properties, CacheStoreMode cacheSto ((Map)properties).put(QueryHints.CACHE_STORE_MODE, cacheStoreMode); } - static Integer getTimeout(Map properties) { + static Integer getTimeout(AbstractSession session, Map properties) { // QueryHints.QUERY_TIMEOUT_UNIT may contain TimeUnit TimeUnit timeUnit = TimeUnit.MILLISECONDS; Object propertyValue = properties.get(QueryHints.QUERY_TIMEOUT_UNIT); if (propertyValue instanceof TimeUnit) { timeUnit = (TimeUnit)propertyValue; } else if (propertyValue != null) { - AbstractSessionLog.getLog().log(SessionLog.WARNING, - SessionLog.QUERY, - "unknown_queryTimeoutUnit_type", - propertyValue.getClass().getName()); + session.log(SessionLog.WARNING, + SessionLog.QUERY, + "unknown_property_type", + propertyValue.getClass().getName(), + QueryHints.QUERY_TIMEOUT_UNIT); } // QueryHints.QUERY_TIMEOUT must be converted from actual units to milliseconds propertyValue = properties.get(QueryHints.QUERY_TIMEOUT); @@ -212,17 +212,17 @@ static Integer getTimeout(Map properties) { long value = Long.parseLong(s); return (int)TimeUnit.MILLISECONDS.convert(value, timeUnit); } catch (NumberFormatException e) { - AbstractSessionLog.getLog().log(SessionLog.WARNING, - SessionLog.QUERY, - "error_queryTimeoutParse", - s, - e.getLocalizedMessage()); + session.log(SessionLog.WARNING, + SessionLog.QUERY, + "error_queryTimeoutParse", + s, e.getLocalizedMessage()); } } else { - AbstractSessionLog.getLog().log(SessionLog.WARNING, - SessionLog.QUERY, - "unknown_queryTimeout_type", - propertyValue.getClass().getName()); + session.log(SessionLog.WARNING, + SessionLog.QUERY, + "unknown_property_type", + propertyValue.getClass().getName(), + QueryHints.QUERY_TIMEOUT); } // Return default value (means no timeout was set) return null; diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/StoredProcedureQueryImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/StoredProcedureQueryImpl.java index 2d7a23caec6..a2602feec29 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/StoredProcedureQueryImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/StoredProcedureQueryImpl.java @@ -880,39 +880,33 @@ public StoredProcedureQueryImpl setFlushMode(FlushModeType flushMode) { return (StoredProcedureQueryImpl) super.setFlushMode(flushMode); } - // TODO-API-3.2 @Override public CacheRetrieveMode getCacheRetrieveMode() { - return FindOptionUtils.getCacheRetrieveMode(getDatabaseQuery().getProperties()); + return FindOptionUtils.getCacheRetrieveMode(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } - // TODO-API-3.2 @Override public StoredProcedureQueryImpl setCacheRetrieveMode(CacheRetrieveMode cacheRetrieveMode) { FindOptionUtils.setCacheRetrieveMode(getDatabaseQuery().getProperties(), cacheRetrieveMode); return this; } - // TODO-API-3.2 @Override public CacheStoreMode getCacheStoreMode() { - return FindOptionUtils.getCacheStoreMode(getDatabaseQuery().getProperties()); + return FindOptionUtils.getCacheStoreMode(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } - // TODO-API-3.2 @Override public StoredProcedureQueryImpl setCacheStoreMode(CacheStoreMode cacheStoreMode) { FindOptionUtils.setCacheStoreMode(getDatabaseQuery().getProperties(), cacheStoreMode); return this; } - // TODO-API-3.2 @Override public Integer getTimeout() { - return FindOptionUtils.getTimeout(getDatabaseQuery().getProperties()); + return FindOptionUtils.getTimeout(entityManager.getAbstractSession(), getDatabaseQuery().getProperties()); } - // TODO-API-3.2 @Override public StoredProcedureQueryImpl setTimeout(Integer timeout) { FindOptionUtils.setTimeout(getDatabaseQuery().getProperties(), timeout); diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/metamodel/MetamodelImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/metamodel/MetamodelImpl.java index e63e1900974..2eef995a3f8 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/metamodel/MetamodelImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/metamodel/MetamodelImpl.java @@ -205,8 +205,6 @@ private void entityEmbeddableManagedTypeNotFound(Map typeMap, Object aType, Stri } } - - // TODO-API-3.2 @Override public EntityType entity(String entityName) { EntityTypeImpl aType = this.entities.get(entityName); diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/FromImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/FromImpl.java index 08a28e15233..d584c53e629 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/FromImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/FromImpl.java @@ -564,7 +564,7 @@ public Join join(Class entityClass, JoinType joinType) { Expression keyExpr = get(singularAttribute); equalPredicates.add(new CompoundExpressionImpl(metamodel, ExpressionImpl.currentNode(keyExpr) - .notEqual(ExpressionImpl.currentNode(join)), + .equal(ExpressionImpl.currentNode(join)), CriteriaBuilderImpl.buildList(keyExpr, join))); } } diff --git a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/SubQueryImpl.java b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/SubQueryImpl.java index cfd3948f3a4..b56910b883f 100644 --- a/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/SubQueryImpl.java +++ b/jpa/org.eclipse.persistence.jpa/src/main/java/org/eclipse/persistence/internal/jpa/querydef/SubQueryImpl.java @@ -494,28 +494,40 @@ public Predicate isNotNull() { return new CompoundExpressionImpl(this.metamodel, this.currentNode.notNull(), list, "not null"); } - // TODO-API-3.2 @Override - public Predicate equalTo(Expression expression) { - throw new UnsupportedOperationException("Jakarta Persistence 3.2 API was not implemented yet"); + public Predicate equalTo(Expression value) { + return new CompoundExpressionImpl( + this.metamodel, + this.currentNode.equal(value), + List.of(this, value), + "equals"); } - // TODO-API-3.2 @Override - public Predicate equalTo(Object o) { - throw new UnsupportedOperationException("Jakarta Persistence 3.2 API was not implemented yet"); + public Predicate equalTo(Object value) { + return new CompoundExpressionImpl( + this.metamodel, + this.currentNode.equal(value), + List.of(this, ExpressionImpl.createLiteral(value, metamodel)), + "equals"); } - // TODO-API-3.2 @Override - public Predicate notEqualTo(Expression expression) { - throw new UnsupportedOperationException("Jakarta Persistence 3.2 API was not implemented yet"); + public Predicate notEqualTo(Expression value) { + return new CompoundExpressionImpl( + this.metamodel, + this.currentNode.equal(value), + List.of(this, value), + "not equal"); } - // TODO-API-3.2 @Override - public Predicate notEqualTo(Object o) { - throw new UnsupportedOperationException("Jakarta Persistence 3.2 API was not implemented yet"); + public Predicate notEqualTo(Object value) { + return new CompoundExpressionImpl( + this.metamodel, + this.currentNode.equal(value), + List.of(this, ExpressionImpl.createLiteral(value, metamodel)), + "not equal"); } @Override