2014-04-01 55 views
0

我有一个数据库的Web应用程序,其中两个实体具有多对多的关系,但我手动实现了连接表。当其中一个实体被删除时,它会删除连接表中的所有条目并更新另一个实体,因此所有实体都可以很好地工作,但现在我应该为此功能编写一个测试。为了测试我使用的内存数据库,这就是真正的,唯一的区别,具有相同的注解(和级联型)相同的方法被调用,但我不断收到:CascadeType不适用于内存数据库

org.hibernate.exception.ConstraintViolationException: integrity constraint violation: foreign key no action; FKC17477FD8940DF2B table ENTITY1_ENTITY2 

我没有粘贴任何代码自从它工作以来,我不相信它有什么问题。我不要求为我解决这个问题,我只需要知道什么可能会导致这种行为,因为我刚刚用完了想法,我不知道还有什么要搜索的......谢谢

编辑:下面是一些代码:

@Entity 
@Table(name = "interviewer") 
public class Interviewer implements Identifiable { 

    @OneToMany(fetch = FetchType.EAGER) 
    @JoinColumn(name = "interviewer_id") 
    private Collection<InterviewerTechnology> technologies; 
} 


@Entity 
@Table(name = "technology") 
public class Technology implements Identifiable { 

    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY) 
    @JoinColumn(name = "technology_id") 
    private Collection<InterviewerTechnology> technologies; 
} 

@Entity 
@Table(name = "interviewer_technology") 
public class InterviewerTechnology implements Identifiable { 

    @Id 
    @GeneratedValue(strategy = GenerationType.IDENTITY) 
    private Integer id; 

    @ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.LAZY) 
    private Interviewer interviewer; 

    @ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.EAGER) 
    private Technology technology; 
} 

@Component 
public class TechnologyDao extends AbstractEntityDao<Technology> { 

    public void remove(Integer id) { 
     Technology technology = find(id); 
     em.remove(technology); 
    } 
} 

此代码不正是我想要它做的,它似乎只是用于测试,并没有看到CascadeType的参数在这里做所有的工作

+0

如果您向我们展示代码,对我们来说,这仍然会轻松许多。 – Schokea

+0

好的,会粘贴相关的部分 – Lucas

+0

尝试CascadeType.PERSIST – Schokea

回答

0

数据库我发现了这个问题,它是@Transactional注释。我所有的测试DAOs都扩展了通用测试DAO,该测试用@Transactional加注,我再次用它盲注每一个DAO。这里的问题是一些操作需要作为单个事务执行(执行后可能需要flush()),以便数据可用于其他操作。考虑以下示例:

@Transactional 
public abstract class AbstractEntityDao<E> { 
    @PersistenceContext(unitName = "some-persistence") 
    protected EntityManager em; 

    public E create(E e) { 
     em.persist(e); 
     return e; 
    } 
    (...) 
} 

这意味着此类中的每个方法都是一个事务。现在,如果我们使用@Transactional注解扩展此类的另一个类,则每种方法都将是另一个事务,这意味着如果我们在一种方法中删除多个事物,它应该执行多个事务(它们都需要调用flush()方法才能执行级联),但相反,他们将作为一个交易运行(除非我们指定Propagation)。让大家(尤其是我)认真思考哪些操作需要单独的事务,哪些操作可以作为一个单独执行。

相关问题