Java 如何使用JPA检查记录是否存在
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4374730/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to check if a record exists using JPA
提问by Balázs Németh
I want to know whether a given record is present in a database or not. so far I have achieved this by writing a JPA query and the running it by getSingleResult()
method. this would throw a NoResultException
if the record with the given parameter does not exist. Of course, it's not a must for the record to exist, so it's the normal behaviour sometimes, that's why I asked to myself, is it neccessary to throw an Exception which I have to handle by a catch block? As far as I know the cost of Exception handling is quite big, so I'm not very satisfied with this solution, also, I don't even need the object, I only need to know it's existence in the DB.
我想知道数据库中是否存在给定的记录。到目前为止,我已经通过编写 JPA 查询并按getSingleResult()
方法运行它来实现这一点。NoResultException
如果具有给定参数的记录不存在,这将抛出一个。当然,记录的存在并不是必须的,所以有时这是正常行为,这就是为什么我问自己,是否有必要抛出一个我必须由 catch 块处理的异常?据我所知,异常处理的成本相当大,所以我对这个解决方案不是很满意,而且,我什至不需要对象,我只需要知道它在数据库中的存在。
Is there a better way to check whether an object exist or not? eg. using getResultList()
and checking it's size maybe?
有没有更好的方法来检查对象是否存在?例如。使用getResultList()
并检查它的大小?
采纳答案by Aaron Digulla
If you just want to know whether the object exists, send a SELECT COUNT
to your database. That will return 0 or 1.
如果您只想知道对象是否存在,请将 a 发送SELECT COUNT
到您的数据库。那将返回 0 或 1。
The cost of the exception handling isn't that big (unless you do that millions of times during a normal operation), so I wouldn't bother.
异常处理的成本并没有那么大(除非您在正常操作期间这样做数百万次),所以我不会打扰。
But the code doesn't really reflect your intention. Since getSingleResult()
calls getResultList()
internally, it's clearer like so:
但是代码并没有真正反映您的意图。由于在内部getSingleResult()
调用getResultList()
,因此更清晰:
public boolean objExists(...) {
return getResultList(...).size() == 1;
}
If you query by object id and you have caching enabled, that will become a simple lookup in the cache if the object has already been loaded.
如果您按对象 id 查询并且启用了缓存,那么如果该对象已经被加载,这将成为在缓存中的简单查找。
回答by J?rn Horstmann
If you are searching by primary key you can also use Entitymanger.find(entityClass, primaryKey)
which returns null
when the entity does not exist.
如果您按主键搜索,您还可以使用Entitymanger.find(entityClass, primaryKey)
whichnull
在实体不存在时返回。
回答by Radu
Try to avoid loading the entity into the session (getSingleResult()
) just to check for it's existence. A count is better here. With the Criteria Query API it would look something like this:
尽量避免将实体加载到会话 ( getSingleResult()
) 中只是为了检查它是否存在。在这里计数更好。使用 Criteria Query API,它看起来像这样:
public <E extends AbstractEntity> boolean exists(final Class<E> entityClass, final int id) {
final EntityManager em = getEntityManager();
final CriteriaBuilder cb = em.getCriteriaBuilder();
final CriteriaQuery<Long> cq = cb.createQuery(Long.class);
final Root<E> from = cq.from(entityClass);
cq.select(cb.count(from));
cq.where(cb.equal(from.get(AbstractEntity_.id), id));
final TypedQuery<Long> tq = em.createQuery(cq);
return tq.getSingleResult() > 0;
}
回答by Halayem Anis
Simply use count(e)
in your query, so no NoResultException
will be thrown and you will avoid loading the entity object
So the Java code can be as follow:
只需count(e)
在您的查询中使用,因此不会NoResultException
抛出任何内容并且您将避免加载实体对象
因此Java代码可以如下:
public boolean isRecordExist() {
String query = "select count(e) from YOUR_ENTITY e where ....";
// you will always get a single result
Long count = (Long) entityManager.createQuery( query ).getSingleResult();
return ( ( count.equals( 0L ) ) ? false : true );
}
Hope that helps someone :)
希望对某人有所帮助:)
回答by user738048
here is a generic approach to work with a type Tand an arbitrary IDvalue
这是处理类型T和任意ID值的通用方法
public boolean exists(Object key) {
EntityManager entityManager = getEntityManager();
Metamodel metamodel = entityManager.getMetamodel();
EntityType<T> entity = metamodel.entity(entityClass);
SingularAttribute<T, ? extends Object> declaredId = entity.getDeclaredId(key.getClass());
CriteriaBuilder cb = entityManager.getCriteriaBuilder();
javax.persistence.criteria.CriteriaQuery<T> cq = cb.createQuery(entityClass);
Root<T> from = cq.from(entityClass);
Predicate condition = cb.equal(from.get(declaredId), key);
cq.where(condition);
TypedQuery<T> q = entityManager.createQuery(cq);
return q.getResultList().size() > 0;
}
回答by Van Tyc
Try this
尝试这个
public boolean exists(Object id){
return getEntityManager().find(entityClass, id)!=null;
}