How do I make my entity object managed so I can remove it?

£可爱£侵袭症+ 提交于 2019-12-11 10:24:51

问题


This doesn't work -- I always get the IllegalArgumentException thrown with the advice to "try merging the detached and try the remove again."

@PersistenceContext private EntityManager   em;
@Resource           private UserTransaction utx;
public void delete(EN entity) {
    if (entity == null) return;   // null-safe
    EN target = entity;
    try {
        if (!em.contains(entity)) {
            System.out.println("delete() entity not managed: " + entity);
            utx.begin();
            target = em.merge(entity);
            utx.commit();
            System.out.print("delete() this entity should now be managed: " + em.contains(target));
        }
        utx.begin();
        em.remove(target);
        utx.commit();
    } catch (RollbackException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (HeuristicMixedException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (HeuristicRollbackException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (SecurityException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (IllegalStateException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (NotSupportedException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    } catch (SystemException ex) {
        Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null, ex);
    }
}

The output log shows the following:

INFO: delete() entity not managed: com.database.SomeTable[ id=2 ]  
INFO: delete() this entity should now be managed: false

In other words the merge() does not return a managed entity. Can anyone spot what I did wrong?

Second question: is there a way to do this in one transaction rather than two?

This is with EclipseLink inside GlassFish 3.1.


回答1:


After commiting your persistence context should be gone. So your println test after the commit will fail, because the "target" object is not managed anymore.

Do all your stuff within one transaction and it should work. You just have to start your transaction after your "try" begins.




回答2:


This snippet of code creates two transactions:

if (!em.contains(entity)) {
    System.out.println("delete() entity not managed: " + entity);
    utx.begin();
    target = em.merge(entity);
    utx.commit();
    System.out.print("delete() this entity should now be managed: " + em.contains(target));
}
utx.begin();
em.remove(target);
utx.commit();

While it is true that the entity is merged into the persistence context, it is true only of the first transaction, and not for both. In the second transaction, the persistence context associated with the transaction will again find a detached object passed as an argument, in the following line:

em.remove(target);

since, the previous utx.commit() would have detached the reference to target.

To fix this, you must merge the entity into the persistence context, and delete the entity in the same transaction, before the reference is detached:

if (!em.contains(entity)) {
    System.out.println("delete() entity not managed: " + entity);
    utx.begin();
    target = em.merge(entity);
    em.remove(target);
    utx.commit();
    System.out.print("delete() this entity should now be deleted: " + (!em.contains(target)) );
}


来源:https://stackoverflow.com/questions/7448392/how-do-i-make-my-entity-object-managed-so-i-can-remove-it

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!