Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/jpa/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
持久化/合并上的JPA树值传播_Jpa_Jpa 2.1 - Fatal编程技术网

持久化/合并上的JPA树值传播

持久化/合并上的JPA树值传播,jpa,jpa-2.1,Jpa,Jpa 2.1,我有 我试过了 Any node must have at least its parent node owners 或者 @PreUpdate public void propagateOwnersTopDown(Node node) { for(Node child : node.getChildren()) { for(Owner owner : node.getOwnerList()) { if(!child.ge

我有

我试过了

Any node must have at least its parent node owners
或者

@PreUpdate
public void propagateOwnersTopDown(Node node)
{
    for(Node child : node.getChildren())
    {
        for(Owner owner : node.getOwnerList())
        {
            if(!child.getOwnerList().contains(owner))
            {
                child.getOwnerList().add(owner);
            }
        }
    }
}
即使我知道这是不合法的,事实上,这些都不起作用(
@PreUpdate
只在根目录上调用)

我知道我可以

  • 编写一个
    addOwner()
    方法,将所有者传播到子级
    • 但是如果其他一些代码调用
      node.getOwnerList().add(owner)

  • 显式调用
    propagateOwnersTopDown()
    或类似于
    em.merge(node)
    之前的调用(通常在事务内部)
    • 但我必须将此添加到每个EJB/事务方法中
我想知道是否有什么好办法来完成这件事

我不是DB专家,但是有可能实现与存储过程/触发器/任何东西的一致性吗

如果为true,调用
@PrePersist
/
@PreUpdate
中的过程/触发器/任何内容是否可能/合法

我在EclipseLink 2.5.2和MySQL 5.6上


谢谢。

我实现了自己的侦听器子系统:

@PreUpdate
public void propagateOwnersBottomUp(Node node)
{
    if(node.getParent() == null) return;

    for(Owner owner : node.getParent().getOwnerList())
    {
        if(!node.getOwnerList().contains(owner))
        {
            node.getOwnerList().add(owner);
        }
    }
}
受保护的void invokeListeners(T实体,类listenerClass:serviceListeners.value())
{
对象实例=listenerClass.newInstance();
Set methods=ReflectionUtils.getAllMethods(listenerClass,ReflectionUtils.withAnnotation(annotation));
用于(方法m:方法)
{
m、 调用(实例、实体);
}
}
}
捕获(例外e)
{
抛出新的RuntimeException(e.getMessage(),e);
}
}
}
公共无效创建(T实体)
{
invokeListeners(实体,OnCreate.class);
em.persist(实体);
}
公共T更新(T实体)
{
invokeListeners(实体,OnUpdate.class);
T entity2=em.merge(实体);
em.flush();
em.refresh(实体2);
返回实体2;
}

EclipseLink 2.5.2拥有JPA2.1。你说得对。谢谢
@PreUpdate
public void propagateOwnersBottomUp(Node node)
{
    if(node.getParent() == null) return;

    for(Owner owner : node.getParent().getOwnerList())
    {
        if(!node.getOwnerList().contains(owner))
        {
            node.getOwnerList().add(owner);
        }
    }
}
protected <T extends AbstractEntity> void invokeListeners(T entity, Class<? extends Annotation> annotation)
{
    ServiceListeners serviceListeners = entity.getClass().getAnnotation(ServiceListeners.class);
    if(serviceListeners != null)
    {
        try
        {
            for(Class<?> listenerClass : serviceListeners.value())
            {
                Object instance = listenerClass.newInstance();

                Set<Method> methods = ReflectionUtils.getAllMethods(listenerClass, ReflectionUtils.withAnnotation(annotation));
                for(Method m : methods)
                {
                    m.invoke(instance, entity);
                }
            }
        }
        catch(Exception e)
        {
            throw new RuntimeException(e.getMessage(), e);
        }
    }
}

public <T extends AbstractEntity> void create(T entity)
{
    invokeListeners(entity, OnCreate.class);

    em.persist(entity);
}

public <T extends AbstractEntity> T update(T entity)
{
    invokeListeners(entity, OnUpdate.class);

    T entity2 = em.merge(entity);
    em.flush();
    em.refresh(entity2);

    return entity2;
}