Polished codebase and added architecture management.

Added Sonargraph architecture description. Removed cyclic package dependency. Introduced JpaEntityInformationSupport to contain common getEntityName() method and serving as factory for JpaEntityInformation instances.
This commit is contained in:
Oliver Gierke
2011-07-21 12:18:37 +02:00
parent 14e8bd6955
commit 00ece2c25e
13 changed files with 430 additions and 137 deletions

216
Spring Data JPA.sonargraph Normal file
View File

@@ -0,0 +1,216 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<context version="7.0.3.1152">
<scope name="spring-data-jpa" type="Project">
<element name="Filter" type="TypeFilterReferenceOverridden">
<element name="org.springframework.data.jpa.**" type="IncludeTypePattern"/>
</element>
<architecture>
<element name="Domain" type="Layer">
<element name="Assignment" type="TypeFilter">
<element name="**.domain.**" type="IncludeTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<element name="Repository" type="Layer">
<element name="Assignment" type="TypeFilter">
<element name="**.repository.**" type="IncludeTypePattern"/>
</element>
<element name="Configuration" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="**.config.**" type="IncludeTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<element name="Query" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="**.query.**" type="IncludeTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<element name="Core" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="**.support.**" type="IncludeTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<element name="Util" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="**.utils.**" type="IncludeTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<stereotype name="Unrestricted"/>
</element>
<element name="Support" type="Layer">
<element name="Assignment" type="TypeFilter">
<element name="**.support.**" type="WeakTypePattern"/>
</element>
<stereotype name="Unrestricted"/>
</element>
</architecture>
<workspace>
<element name="src/main/java" type="JavaRootDirectory">
<reference name="Project|spring-data-jpa::BuildUnit|spring-data-jpa"/>
</element>
<element name="target/classes" type="JavaRootDirectory">
<reference name="Project|spring-data-jpa::BuildUnit|spring-data-jpa"/>
</element>
<element name="target/generated-sources/main" type="JavaRootDirectory">
<reference name="Project|spring-data-jpa::BuildUnit|spring-data-jpa"/>
</element>
</workspace>
<physical>
<element name="spring-data-jpa" type="BuildUnit"/>
</physical>
</scope>
<scope name="External" type="External">
<element name="Filter" type="TypeFilter">
<element name="**" type="IncludeTypePattern"/>
<element name="java.io.*" type="ExcludeTypePattern"/>
<element name="java.lang.*" type="ExcludeTypePattern"/>
<element name="java.lang.annotation.*" type="ExcludeTypePattern"/>
<element name="java.lang.ref.*" type="ExcludeTypePattern"/>
<element name="java.math.*" type="ExcludeTypePattern"/>
<element name="java.nio.*" type="ExcludeTypePattern"/>
<element name="java.nio.channels.*" type="ExcludeTypePattern"/>
<element name="java.nio.channels.spi.*" type="ExcludeTypePattern"/>
<element name="java.nio.charset.*" type="ExcludeTypePattern"/>
<element name="java.nio.charset.spi.*" type="ExcludeTypePattern"/>
<element name="java.text.*" type="ExcludeTypePattern"/>
<element name="java.util.*" type="ExcludeTypePattern"/>
<element name="java.util.jar.*" type="ExcludeTypePattern"/>
<element name="java.util.prefs.*" type="ExcludeTypePattern"/>
<element name="java.util.regex.*" type="ExcludeTypePattern"/>
<element name="java.util.zip.*" type="ExcludeTypePattern"/>
</element>
<architecture>
<element name="Querydsl" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="com.mysema.query.**" type="IncludeTypePattern"/>
</element>
</element>
<element name="Spring" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="org.springframework.**" type="WeakTypePattern"/>
</element>
</element>
<element name="Spring Data Commons" type="Subsystem">
<element name="Assignment" type="TypeFilter">
<element name="org.springframework.data.**" type="IncludeTypePattern"/>
</element>
</element>
</architecture>
</scope>
<scope name="Global" type="Global">
<element name="Configuration" type="Configuration"/>
<element name="Filter" type="TypeFilter">
<element name="**" type="IncludeTypePattern"/>
</element>
<itemDefinition>
<item type="ThresholdItem">
<property name="AttributeId" value="NumberOfNotAssignedTypes"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Project"/>
<property name="UpperValue" value="0"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="NumberOfParameters"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Method"/>
<property name="UpperValue" value="7"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="NumberOfAccessibleTypes"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Namespace"/>
<property name="UpperValue" value="30"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="NormalizedCumulativeComponentDependency"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Project"/>
<property name="UpperValue" value="7"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="LinesOfCode"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="SourceFile"/>
<property name="UpperValue" value="700"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="NumberOfInternalTypes"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Namespace"/>
<property name="UpperValue" value="50"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="NumberOfMethods"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Type"/>
<property name="UpperValue" value="50"/>
</item>
<item type="ThresholdItem">
<property name="AttributeId" value="ModifiedCyclomaticComplexity"/>
<property name="LowerValue" value=""/>
<property name="NamedElementGroup" value="Method"/>
<property name="UpperValue" value="20"/>
</item>
</itemDefinition>
</scope>
<attributeConfiguration type="AttributeConfiguration">
<property name="ExtendedCyclomaticComplexity" value="disabled"/>
<property name="MaxExtendedCyclomaticComplexityPerMethod" value="disabled"/>
<property name="NumberOfWarnings" value="disabled"/>
<property name="AverageCyclomaticComplexityPerMethod" value="disabled"/>
<property name="NumberOfAbstractTypes" value="disabled"/>
<property name="JdkVersion" value="disabled"/>
<property name="NumberOfCyclicDirectories" value="disabled"/>
<property name="CyclomaticComplexity" value="disabled"/>
<property name="NumberOfMethodsWithImplementation" value="disabled"/>
<property name="NumberOfIgnoredWarnings" value="disabled"/>
<property name="NumberOfNamedInterfaces" value="disabled"/>
<property name="NumberOfCyclicProjects" value="disabled"/>
<property name="NumberOfRefactorings" value="disabled"/>
<property name="DependsUpon" value="disabled"/>
<property name="NumberOfVerticalSliceGroups" value="disabled"/>
<property name="DistributedOverPathContainers" value="disabled"/>
<property name="AverageExtendedCyclomaticComplexityPerMethod" value="disabled"/>
<property name="AverageTypeDependency" value="disabled"/>
<property name="NumberOfDuplicateCodeBlocksWarnings" value="disabled"/>
<property name="RelativeAverageTypeDependency" value="disabled"/>
<property name="AverageAccumulatedExtendedCyclomaticComplexityPerType" value="disabled"/>
<property name="NumberOfLayerGroups" value="disabled"/>
<property name="NumberOfIgnoredViolations" value="disabled"/>
<property name="NumberOfFixWarnings" value="disabled"/>
<property name="NumberOfExcludedSourceFiles" value="disabled"/>
<property name="NumberOfVerticalSlices" value="disabled"/>
<property name="AverageAccumulatedCyclomaticComplexityPerType" value="disabled"/>
<property name="Timestamp" value="disabled"/>
<property name="AverageAssertionUsage" value="disabled"/>
<property name="NumberOfCyclicSubsystems" value="disabled"/>
<property name="NumberOfCyclicNamespaces" value="disabled"/>
<property name="NumberOfExcludedTargetFiles" value="disabled"/>
<property name="NumberOfCyclicVerticalSliceGroups" value="disabled"/>
<property name="AccumulatedExtendedCyclomaticComplexity" value="disabled"/>
<property name="NumberOfLayers" value="disabled"/>
<property name="NumberOfCyclicSourceFiles" value="disabled"/>
<property name="MaxAccumulatedCyclomaticComplexityPerType" value="disabled"/>
<property name="MaxAccumulatedExtendedCyclomaticComplexityPerType" value="disabled"/>
<property name="NumberOfCyclicLayerGroups" value="disabled"/>
<property name="NumberOfAssertions" value="disabled"/>
<property name="NumberOfCyclicVerticalSlices" value="disabled"/>
<property name="NormalizedCumulativeTypeDependency" value="disabled"/>
<property name="AccumulatedCyclomaticComplexity" value="disabled"/>
<property name="NumberOfCyclicWarnings" value="disabled"/>
<property name="NumberOfMetricWarnings" value="disabled"/>
<property name="NumberOfNameParts" value="disabled"/>
<property name="NumberOfTasks" value="disabled"/>
<property name="NumberOfWorkspaceWarnings" value="disabled"/>
<property name="NumberOfAbstractMethods" value="disabled"/>
<property name="NumberOfTypesWithImplementation" value="disabled"/>
<property name="Level" value="disabled"/>
<property name="NumberOfSubsystems" value="disabled"/>
<property name="NumberOfCyclicLayers" value="disabled"/>
<property name="MaxCyclomaticComplexityPerMethod" value="disabled"/>
</attributeConfiguration>
</context>

View File

@@ -22,11 +22,11 @@ import javax.persistence.EntityManager;
import org.springframework.data.domain.Sort;
import org.springframework.data.repository.PagingAndSortingRepository;
import org.springframework.data.repository.CrudRepository;
/**
* JPA specific extension of {@link Repository}.
* JPA specific extension of
* {@link org.springframework.data.repository.Repository}.
*
* @author Oliver Gierke
*/

View File

@@ -34,7 +34,6 @@ import javax.persistence.criteria.Root;
import org.springframework.data.domain.Sort;
import org.springframework.data.repository.query.Parameter;
import org.springframework.data.repository.query.ParameterAccessor;
import org.springframework.data.repository.query.Parameters;
import org.springframework.data.repository.query.parser.AbstractQueryCreator;
import org.springframework.data.repository.query.parser.Part;

View File

@@ -16,7 +16,6 @@
package org.springframework.data.jpa.repository.query;
import static java.util.regex.Pattern.*;
import static org.springframework.data.jpa.repository.utils.JpaClassUtils.*;
import java.util.ArrayList;
import java.util.Iterator;
@@ -91,33 +90,18 @@ public abstract class QueryUtils {
}
/**
* Returns the query string for the given class.
*
* @return
*/
public static String getQueryString(String template, Class<?> clazz) {
if (null == clazz) {
throw new IllegalArgumentException("Class must not be null!");
}
return getQueryString(template, getEntityName(clazz));
}
/**
* Returns the query string for the given class name.
*
* @param template
* @param clazzName
* @param entityName
* @return
*/
private static String getQueryString(String template, String clazzName) {
public static String getQueryString(String template, String entityName) {
Assert.hasText(clazzName, "Classname must not be null or empty!");
Assert.hasText(entityName, "Entity name must not be null or empty!");
return String.format(template, clazzName);
return String.format(template, entityName);
}

View File

@@ -37,4 +37,12 @@ public interface JpaEntityInformation<T, ID extends Serializable> extends
* @return
*/
SingularAttribute<? super T, ?> getIdAttribute();
/**
* Returns the JPA entity name.
*
* @return
*/
String getEntityName();
}

View File

@@ -0,0 +1,92 @@
/*
* Copyright 2011 the original author or authors.
*
* Licensed 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.
*/
package org.springframework.data.jpa.repository.support;
import java.io.Serializable;
import javax.persistence.Entity;
import javax.persistence.EntityManager;
import javax.persistence.metamodel.Metamodel;
import org.springframework.data.domain.Persistable;
import org.springframework.data.repository.core.support.AbstractEntityInformation;
import org.springframework.util.StringUtils;
/**
* Base class for {@link JpaEntityInformation} implementations to share common
* method implementations.
*
* @author Oliver Gierke
*/
public abstract class JpaEntityInformationSupport<T, ID extends Serializable>
extends AbstractEntityInformation<T, ID> implements
JpaEntityInformation<T, ID> {
/**
* Creates a new {@link JpaEntityInformationSupport} with the given domain
* class.
*
* @param domainClass
*/
public JpaEntityInformationSupport(Class<T> domainClass) {
super(domainClass);
}
/**
* Creates a {@link JpaEntityInformation} for the given domain class and
* {@link EntityManager}.
*
* @param domainClass
* @param em
* @return
*/
@SuppressWarnings({ "rawtypes", "unchecked" })
public static <T> JpaEntityInformation<T, ?> getMetadata(
Class<T> domainClass, EntityManager em) {
Metamodel metamodel = em.getMetamodel();
if (Persistable.class.isAssignableFrom(domainClass)) {
return new JpaPersistableEntityInformation(domainClass, metamodel);
} else {
try {
return new JpaMetamodelEntityInformation(domainClass, metamodel);
} catch (IllegalArgumentException e) {
return null;
}
}
}
/*
* (non-Javadoc)
*
* @see
* org.springframework.data.jpa.repository.support.JpaEntityInformation#
* getEntityName()
*/
public String getEntityName() {
Class<?> domainClass = getJavaType();
Entity entity = domainClass.getAnnotation(Entity.class);
boolean hasName = null != entity && StringUtils.hasText(entity.name());
return hasName ? entity.name() : domainClass.getSimpleName();
}
}

View File

@@ -25,7 +25,6 @@ import javax.persistence.metamodel.Metamodel;
import javax.persistence.metamodel.SingularAttribute;
import org.springframework.data.repository.core.EntityInformation;
import org.springframework.data.repository.core.support.AbstractEntityInformation;
import org.springframework.util.Assert;
import org.springframework.util.ReflectionUtils;
@@ -37,7 +36,8 @@ import org.springframework.util.ReflectionUtils;
* @author Oliver Gierke
*/
public class JpaMetamodelEntityInformation<T, ID extends Serializable> extends
AbstractEntityInformation<T, ID> implements JpaEntityInformation<T, ID> {
JpaEntityInformationSupport<T, ID> implements
JpaEntityInformation<T, ID> {
private final SingularAttribute<? super T, ?> attribute;

View File

@@ -21,9 +21,9 @@ import java.io.Serializable;
import javax.persistence.EntityManager;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy;
import org.springframework.data.jpa.repository.query.QueryExtractor;
import org.springframework.data.jpa.repository.utils.JpaClassUtils;
import org.springframework.data.querydsl.QueryDslPredicateExecutor;
import org.springframework.data.repository.core.RepositoryMetadata;
import org.springframework.data.repository.core.support.RepositoryFactorySupport;
@@ -71,7 +71,7 @@ public class JpaRepositoryFactory extends RepositoryFactorySupport {
/**
* Callback to create a {@link RepositorySupport} instance with the given
* Callback to create a {@link JpaRepository} instance with the given
* {@link EntityManager}
*
* @param <T>
@@ -81,7 +81,7 @@ public class JpaRepositoryFactory extends RepositoryFactorySupport {
* @return
*/
@SuppressWarnings({ "unchecked", "rawtypes" })
protected <T, ID extends Serializable> Object getTargetRepository(
protected <T, ID extends Serializable> JpaRepository<?, ?> getTargetRepository(
RepositoryMetadata metadata, EntityManager entityManager) {
Class<?> repositoryInterface = metadata.getRepositoryInterface();
@@ -156,7 +156,7 @@ public class JpaRepositoryFactory extends RepositoryFactorySupport {
public <T, ID extends Serializable> JpaEntityInformation<T, ID> getEntityInformation(
Class<T> domainClass) {
return (JpaEntityInformation<T, ID>) JpaClassUtils.getMetadata(
domainClass, entityManager);
return (JpaEntityInformation<T, ID>) JpaEntityInformationSupport
.getMetadata(domainClass, entityManager);
}
}

View File

@@ -36,15 +36,15 @@ import org.springframework.data.domain.Sort;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
import org.springframework.data.jpa.repository.utils.JpaClassUtils;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.data.repository.CrudRepository;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
/**
* Default implementation of the {@link CrudRepository} interface. This will offer
* you a more sophisticated interface than the plain {@link EntityManager} .
* Default implementation of the {@link CrudRepository} interface. This will
* offer you a more sophisticated interface than the plain {@link EntityManager}
* .
*
* @author Oliver Gierke
* @author Eberhard Wolff
@@ -88,7 +88,7 @@ public class SimpleJpaRepository<T, ID extends Serializable> implements
*/
public SimpleJpaRepository(Class<T> domainClass, EntityManager em) {
this(JpaClassUtils.getMetadata(domainClass, em), em);
this(JpaEntityInformationSupport.getMetadata(domainClass, em), em);
}
@@ -100,7 +100,8 @@ public class SimpleJpaRepository<T, ID extends Serializable> implements
private String getDeleteAllQueryString() {
return getQueryString(DELETE_ALL_QUERY_STRING, getDomainClass());
return getQueryString(DELETE_ALL_QUERY_STRING,
entityInformation.getEntityName());
}
@@ -110,7 +111,7 @@ public class SimpleJpaRepository<T, ID extends Serializable> implements
String.format(COUNT_QUERY_STRING,
provider.getCountQueryPlaceholder(), "%s");
return getQueryString(countQuery, getDomainClass());
return getQueryString(countQuery, entityInformation.getEntityName());
}
@@ -174,8 +175,10 @@ public class SimpleJpaRepository<T, ID extends Serializable> implements
return;
}
applyAndBind(getQueryString(DELETE_ALL_QUERY_STRING, getDomainClass()),
entities, em).executeUpdate();
applyAndBind(
getQueryString(DELETE_ALL_QUERY_STRING,
entityInformation.getEntityName()), entities, em)
.executeUpdate();
em.clear();
}

View File

@@ -15,15 +15,7 @@
*/
package org.springframework.data.jpa.repository.utils;
import javax.persistence.Entity;
import javax.persistence.EntityManager;
import javax.persistence.metamodel.Metamodel;
import org.springframework.data.domain.Persistable;
import org.springframework.data.jpa.repository.support.JpaEntityInformation;
import org.springframework.data.jpa.repository.support.JpaMetamodelEntityInformation;
import org.springframework.data.jpa.repository.support.JpaPersistableEntityInformation;
import org.springframework.util.StringUtils;
/**
@@ -64,46 +56,4 @@ public abstract class JpaClassUtils {
return false;
}
}
/**
* Returns the name ot the entity represented by this class. Used to build
* queries for that class.
*
* @param domainClass
* @return
*/
public static String getEntityName(Class<?> domainClass) {
Entity entity = domainClass.getAnnotation(Entity.class);
boolean hasName = null != entity && StringUtils.hasText(entity.name());
return hasName ? entity.name() : domainClass.getSimpleName();
}
/**
* Creates a {@link JpaEntityInformation} for the given domain class and
* {@link EntityManager}.
*
* @param domainClass
* @param em
* @return
*/
@SuppressWarnings({ "rawtypes", "unchecked" })
public static <T> JpaEntityInformation<T, ?> getMetadata(
Class<T> domainClass, EntityManager em) {
Metamodel metamodel = em.getMetamodel();
if (Persistable.class.isAssignableFrom(domainClass)) {
return new JpaPersistableEntityInformation(domainClass, metamodel);
} else {
try {
return new JpaMetamodelEntityInformation(domainClass, metamodel);
} catch (IllegalArgumentException e) {
return null;
}
}
}
}

View File

@@ -21,6 +21,7 @@ import java.io.Serializable;
import javax.persistence.EntityManager;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.support.JpaEntityInformation;
import org.springframework.data.jpa.repository.support.JpaRepositoryFactory;
import org.springframework.data.repository.core.RepositoryMetadata;
@@ -52,8 +53,8 @@ public class CustomGenericJpaRepositoryFactory extends JpaRepositoryFactory {
*/
@Override
@SuppressWarnings("unchecked")
protected Object getTargetRepository(RepositoryMetadata metadata,
EntityManager em) {
protected JpaRepository<?, ?> getTargetRepository(
RepositoryMetadata metadata, EntityManager em) {
JpaEntityInformation<Object, Serializable> entityMetadata =
mock(JpaEntityInformation.class);

View File

@@ -0,0 +1,86 @@
/*
* Copyright 2011 the original author or authors.
*
* Licensed 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.
*/
package org.springframework.data.jpa.repository.support;
import static org.junit.Assert.*;
import java.io.Serializable;
import javax.persistence.Entity;
import javax.persistence.metamodel.SingularAttribute;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.runners.MockitoJUnitRunner;
/**
* Unit tests for {@link AbstractJpaEntityInformation}.
*
* @author Oliver Gierke
*/
@RunWith(MockitoJUnitRunner.class)
public class JpaEntityInformationSupportUnitTests {
@Test
public void usesSimpleClassNameIfNoEntityNameGiven() throws Exception {
JpaEntityInformation<User, Long> information =
new DummyJpaEntityInformation<User, Long>(User.class);
assertEquals("User", information.getEntityName());
JpaEntityInformation<NamedUser, ?> second =
new DummyJpaEntityInformation<NamedUser, Serializable>(
NamedUser.class);
assertEquals("AnotherNamedUser", second.getEntityName());
}
static class User {
}
@Entity(name = "AnotherNamedUser")
public class NamedUser {
}
static class DummyJpaEntityInformation<T, ID extends Serializable> extends
JpaEntityInformationSupport<T, ID> {
public DummyJpaEntityInformation(Class<T> domainClass) {
super(domainClass);
}
public SingularAttribute<? super T, ?> getIdAttribute() {
return null;
}
public ID getId(T entity) {
return null;
}
public Class<ID> getIdType() {
return null;
}
}
}

View File

@@ -1,46 +0,0 @@
/*
* Copyright 2008-2011 the original author or authors.
*
* Licensed 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.
*/
package org.springframework.data.jpa.repository.util;
import static org.junit.Assert.*;
import static org.springframework.data.jpa.repository.utils.JpaClassUtils.*;
import javax.persistence.Entity;
import org.junit.Test;
/**
* @author Oliver Gierke
*/
public class JpaClassUtilsUnitTests {
@Test
public void usesSimpleClassNameIfNoEntityNameGiven() throws Exception {
assertEquals("User", getEntityName(User.class));
assertEquals("AnotherNamedUser", getEntityName(NamedUser.class));
}
static class User {
}
@Entity(name = "AnotherNamedUser")
public class NamedUser {
}
}