@AdditionalCriteria与@OneToOne结合使用会产生QueryException

时间:2012-04-29 13:00:17

标签: jpa eclipselink multi-tenant one-to-one

我正在尝试创建RESTful服务。对于多租户,我正在应用@AdditionalCriteria注释。但是,当我使用@OneToOne批注加入实体时,会引发以下异常:

Exception [EclipseLink-6174] (Eclipse Persistence Services - 2.3.0.v20110604-
r9504): org.eclipse.persistence.exceptions.QueryException
Exception Description: No value was provided for the session property 
[SECURITYID]. This exception is possible when using additional criteria or 
tenant discriminator columns without specifying the associated contextual 
property. These properties must be set through Entity Manager, Entity Manager 
Factory or persistence unit properties. If using native EclipseLink, these 
properties should be set directly on the session.
Query: ReadObjectQuery(name="readObject" referenceClass=Addresses 
sql="SELECT id, city, country, postalcode, province, security_id, street 
FROM addresses WHERE ((id = ?) AND (security_id = ?))")

我在EntityManager级别设置属性[SECURITYID],没有连接,一切正常。但是当我使用@OneToOne加入一个实体时,我发现该属性不存在。我没有足够的经验来确定这是由于我做错了什么或者这是一个错误。对我来说,看起来使用不同的EntityManager来获取已连接的实体。但我猜是因为我缺乏知识。我也尝试在EntityManagerFactory级别设置属性,但无济于事。

这是我的设置。 实体:

@Entity
@AdditionalCriteria("this.securityId=:SECURITYID")
@Table(name = "tasks", catalog = "catalog", schema = "schema")
@XmlRootElement
@NamedQueries(
{
  @NamedQuery(name = "Tasks.findAll", query = "SELECT t FROM Tasks t")

})
public class Tasks implements Serializable
{
...
  @OneToOne(fetch=FetchType.EAGER)
  @JoinColumn(name="service_address_id")
  private Addresses serviceAddress;

...
}

RESTFacade类

@Stateless
@Path("tasks")
public class TasksFacadeREST extends AbstractFacade<Tasks>
{
  @PersistenceContext(unitName = "UnitName")
  private EntityManager em;

...

  @java.lang.Override
  protected EntityManager getEntityManager()
  {
    // Temp! REMOVE WHEN DONE
    sessionId = "123456789";

    Identifier.setIdentity(em,sessionId);
    em.setProperty("SECURITYID",Identifier.securityId);
    em.setProperty("USERID",Identifier.userId);

    return em;
  }

谢谢&amp; RGDS, 中号

2 个答案:

答案 0 :(得分:1)

我的猜测是这与缓存有关。

通常,租户属性将在EntityManagerFactory上设置,而不是EntityManager。这意味着您为每个租户提供了不同的EntityManagerFactory。您还可以在persistence.xml中定义租户属性,并为每个租户设置不同的持久性单元。

如果您需要为每个EntityManager设置租户,则需要禁用共享缓存,或将缓存模式设置为受保护。

http://wiki.eclipse.org/EclipseLink/UserGuide/JPA/Advanced_JPA_Development/Single-Table_Multi-Tenancy#Setting_Properties_and_Caching_Scope

答案 1 :(得分:1)

作为参考,要禁用的属性为eclipselink.cache.shared.default

<property name="eclipselink.cache.shared.default" value="false"/>