Skip to content

Commit

Permalink
Fixed Blazebit#120 - Implemented treat support.
Browse files Browse the repository at this point in the history
  • Loading branch information
beikov committed Mar 31, 2017
1 parent 7fee38d commit cc28250
Show file tree
Hide file tree
Showing 34 changed files with 1,318 additions and 565 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ Not yet released
* Various performance improvements
* Support referring to `this` in all mapping types for putting values in embedded objects
* Relaxed strict requirements for `@IdMapping` and removed `@EmbeddableEntityView`
* Full support for `TREAT` operator. Note that EclipseLink and DataNucleus only support very few basic usages

### Bug fixes

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -687,6 +687,7 @@ public boolean isEmpty() {
!fromClassExplicitelySet
&& joinManager.getRoots().size() == 1
&& joinManager.getRoots().get(0).getNodes().isEmpty()
&& joinManager.getRoots().get(0).getTreatedJoinNodes().isEmpty()
&& joinManager.getRoots().get(0).getEntityJoinNodes().isEmpty()
)
;
Expand Down Expand Up @@ -1570,7 +1571,7 @@ protected List<EntityFunctionNode> getEntityFunctionNodes(Query baseQuery) {
String valuesAliases = node.getValuesAliases();

String valuesTableSqlAlias = cbf.getExtendedQuerySupport().getSqlAlias(em, baseQuery, node.getAlias());
entityFunctionNodes.add(new EntityFunctionNode(valuesClause, valuesAliases, node.getPropertyClass(), valuesTableSqlAlias, node.getValueQuery()));
entityFunctionNodes.add(new EntityFunctionNode(valuesClause, valuesAliases, node.getType(), valuesTableSqlAlias, node.getValueQuery()));
}
return entityFunctionNodes;
}
Expand Down Expand Up @@ -1785,7 +1786,7 @@ protected void prepareAndCheck() {
joinManager.acceptVisitor(new JoinNodeVisitor() {
@Override
public void visit(JoinNode node) {
Class<?> cteType = node.getPropertyClass();
Class<?> cteType = node.getType();
// Except for VALUES clause from nodes, every cte type must be defined
if (node.getValueQuery() == null && mainQuery.metamodel.getCte(cteType) != null) {
if (mainQuery.cteManager.getCte(cteType) == null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ private void checkEntityId(Object entityId) {
throw new IllegalArgumentException("Invalid null entity id given");
}

EntityType<?> entityType = mainQuery.metamodel.entity(joinManager.getRootNodeOrFail("Paginated queries do not support multiple from clause elements!").getPropertyClass());
EntityType<?> entityType = mainQuery.metamodel.entity(joinManager.getRootNodeOrFail("Paginated queries do not support multiple from clause elements!").getType());
Attribute<?, ?> idAttribute = JpaUtils.getIdAttribute(entityType);
Class<?> idType = JpaUtils.resolveFieldClass(entityType.getJavaType(), idAttribute);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.metamodel.Attribute;
import javax.persistence.metamodel.BasicType;
import javax.persistence.metamodel.EmbeddableType;
import javax.persistence.metamodel.EntityType;
import javax.persistence.metamodel.ManagedType;
Expand All @@ -37,6 +38,8 @@
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;

/**
* This is a wrapper around the JPA {@link Metamodel} allows additionally efficient access by other attributes than a Class.
Expand All @@ -50,7 +53,8 @@ public class EntityMetamodelImpl implements EntityMetamodel {
private final Map<String, EntityType<?>> entityNameMap;
private final Map<String, Class<?>> entityTypes;
private final Map<String, Class<Enum<?>>> enumTypes;
private final Map<Class<?>, ManagedType<?>> classMap;
private final Map<Class<?>, Type<?>> classMap;
private final ConcurrentMap<Class<?>, Type<?>> basicTypeMap = new ConcurrentHashMap<>();
private final Map<Class<?>, ManagedType<?>> cteMap;
private final Map<Class<?>, Map<String, Map.Entry<AttributePath, String[]>>> typeAttributeColumnNameMap;
private final Map<Class<?>, Map<String, Map.Entry<AttributePath, String[]>>> typeAttributeColumnTypeMap;
Expand All @@ -61,7 +65,7 @@ public EntityMetamodelImpl(EntityManagerFactory emf, ExtendedQuerySupport extend
Map<String, EntityType<?>> nameToType = new HashMap<>(managedTypes.size());
Map<String, Class<?>> entityTypes = new HashMap<>(managedTypes.size());
Map<String, Class<Enum<?>>> enumTypes = new HashMap<>(managedTypes.size());
Map<Class<?>, ManagedType<?>> classToType = new HashMap<>(managedTypes.size());
Map<Class<?>, Type<?>> classToType = new HashMap<>(managedTypes.size());
Map<Class<?>, ManagedType<?>> cteToType = new HashMap<>(managedTypes.size());
Map<Class<?>, Map<String, Map.Entry<AttributePath, String[]>>> typeAttributeColumnNames = new HashMap<>(managedTypes.size());
Map<Class<?>, Map<String, Map.Entry<AttributePath, String[]>>> typeAttributeColumnTypeNames = new HashMap<>(managedTypes.size());
Expand Down Expand Up @@ -200,6 +204,14 @@ public <X> EntityType<X> entity(Class<X> cls) {
return delegate.entity(cls);
}

public EntityType<?> entity(String name) {
EntityType<?> type = entityNameMap.get(name);
if (type == null) {
throw new IllegalArgumentException("Invalid entity type: " + name);
}
return type;
}

@Override
public EntityType<?> getEntity(String name) {
return entityNameMap.get(name);
Expand All @@ -223,6 +235,22 @@ public <X> ManagedType<X> managedType(Class<X> cls) {
return delegate.managedType(cls);
}

@Override
@SuppressWarnings({ "unchecked" })
public <X> Type<X> type(Class<X> cls) {
Type<?> type = classMap.get(cls);
if (type != null) {
return (Type<X>) type;
}

type = new BasicTypeImpl<>(cls);
Type<?> oldType = basicTypeMap.putIfAbsent(cls, type);
if (oldType != null) {
type = oldType;
}
return (Type<X>) type;
}

@Override
public ManagedType<?> managedType(String name) {
ManagedType<?> t = entityNameMap.get(name);
Expand All @@ -233,15 +261,16 @@ public ManagedType<?> managedType(String name) {
return t;
}

@SuppressWarnings({ "unchecked" })
@Override
@SuppressWarnings({ "unchecked" })
public <X> ManagedType<X> getManagedType(Class<X> cls) {
return (ManagedType<X>) classMap.get(cls);
}

@Override
@SuppressWarnings({ "unchecked" })
public <X> EntityType<X> getEntity(Class<X> cls) {
ManagedType<?> type = classMap.get(cls);
Type<?> type = classMap.get(cls);
if (type == null || !(type instanceof EntityType<?>)) {
return null;
}
Expand Down Expand Up @@ -273,4 +302,23 @@ public Set<EntityType<?>> getEntities() {
public Set<EmbeddableType<?>> getEmbeddables() {
return delegate.getEmbeddables();
}

private static class BasicTypeImpl<T> implements BasicType<T> {

private final Class<T> cls;

public BasicTypeImpl(Class<T> cls) {
this.cls = cls;
}

@Override
public PersistenceType getPersistenceType() {
return PersistenceType.BASIC;
}

@Override
public Class<T> getJavaType() {
return cls;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ public void visit(PathExpression expression) {
* selects here
*/
JoinNode baseNode = ((JoinNode) expression.getBaseNode());
EntityType<?> entityType = m.getEntity(baseNode.getPropertyClass());
EntityType<?> entityType = m.getEntity(baseNode.getType());
if (entityType == null) {
// ignore if the expression is not an entity
return;
Expand Down Expand Up @@ -101,7 +101,7 @@ public int compare(Attribute<?, ?> o1, Attribute<?, ?> o2) {

if (resolve) {
PathExpression attrPath = new PathExpression(new ArrayList<PathElementExpression>(expression.getExpressions()));
attrPath.setPathReference(new SimplePathReference(baseNode, attr.getName(), null, JpaUtils.resolveFieldClass(entityClass, attr)));
attrPath.setPathReference(new SimplePathReference(baseNode, attr.getName(), JpaUtils.resolveFieldClass(entityClass, attr)));
pathExpressions.add(attrPath);
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,10 @@ public String getAbsolutePath() {
}
}

public void render(StringBuilder sb) {
sb.append(alias);
}

public boolean isImplicit() {
return implicit;
}
Expand Down
Loading

0 comments on commit cc28250

Please sign in to comment.