我有一个应该是多对多(双向)的列表
这是Filter类:
@ManyToMany(targetEntity=Serving.class)
@JoinTable(name = "BRIDGE_SERV_FILTER", joinColumns={
@JoinColumn(name="filter_id")}, inverseJoinColumns={@JoinColumn(name="serving_id")})
private List<Serving> servings;
public List<Serving> getServing() { return this.servings; }
public void setServing(List<Serving> servings) { this.servings = servings; }
这是Serving类:
@ManyToMany(targetEntity=Filter.class)
@JoinTable(name = "BRIDGE_SERV_FILTER", joinColumns={
@JoinColumn(name="serving_id")}, inverseJoinColumns={@JoinColumn(name="filter_id")})
private List<Filter> filters;
public List<Filter> getFilters() { return filters;}
public void setFilters(List<Filter> filters) { this.filters = filters;}
然后我应该调用一些东西来获取服务中的所有过滤器,这就是我所做的(serv类型为Serving):
List<Filter> filters = serv.getFilters();
//iterate from all filter
for(Filter allf : allFilter)
{
boolean mark_this = false;
//..and matched the currently-iterated-all-filters with filter from
//which the serving got
for(com.pos.model.Filter f : filters)
{
//if matched, mark this current filter
if (allf.getId().equals(f.getId()))
mark_this = true;
}
tmodel.addRow(new Object[] { allf.getName(), mark_this });
}
该方法在模型中定义,并且是静态的。所以,当表单加载时,它调用像jTable.setTableModel(Filter.toTableModel(thisServing));
它读取,并显示数据。但是,Hibernate也会调用delete:
Hibernate: select filter0_.filter_id as filter1_2_, filter0_.is_showable as is2_2_, filter0_.name as name2_ from DIM_FILTER filter0_ where is_showable=true
Hibernate: select filters0_.serving_id as serving1_4_1_, filters0_.filter_id as filter2_6_1_, filter1_.filter_id as filter1_2_0_, filter1_.is_showable as is2_2_0_, filter1_.name as name2_0_ from BRIDGE_SERV_FILTER filters0_ inner join DIM_FILTER filter1_ on filters0_.filter_id=filter1_.filter_id where filters0_.serving_id=?
Hibernate: delete from BRIDGE_SERV_FILTER where serving_id=?
事实上,我根本不做任何删除,我不会要求hibernate删除任何东西。我不明白的东西可能会发生......如何防止Hibernate被删除?或者我做错了什么?
答案 0 :(得分:2)
在代码中的某处,您必须清除服务的过滤器集合,或将此集合设置为null。 Hibernate使这种变化持久化。
另请注意,您的映射是错误的,这是您看到奇怪行为的原因。您没有双向ManyToMany,而是使用两个不相关的单向ManyToMany,它们都使用相同的连接表。必须选择其中一方作为另一方的倒数。例如,如果您希望过滤器端是关联的所有者,则必须使用mappedBy
属性将服务端标记为反面:
class Filter {
@ManyToMany
@JoinTable(name = "BRIDGE_SERV_FILTER", joinColumns={
@JoinColumn(name="filter_id")}, inverseJoinColumns={@JoinColumn(name="serving_id")})
private List<Serving> servings;
}
class Serving {
@ManyToMany(mappedBy = "servings")
private List<Filter> filters;
}
the documentation中描述了这一点。
答案 1 :(得分:0)
这个问题实际上已经在8天前发生在我身上,让我无助。
问题在于我如何获得list()。所以......如果你有双向关系,就不要这样做:
Long id = getIdFromCombo();
Serving s = (Serving) session.getId(Serving.class, id).uniqueResult();
与您同时使用以下内容初始化表单时
Public theFormName(Menu m){
this.menu = m;
}
如果菜单的服务为一对多,则最好不要根据您的会话查询服务。最好在一个接一个地匹配它:
Serving s;
for(int i=0; i<this.menu.getServings().size(); i++)
{
if(equal code) s = menu.getServings().get(i);
}
然后你不应该像我上面列出的那样出问题。这很奇怪。陷阱。我想知道是否有人遇到过这个问题。这不是我的错,也不是错误,我不确定。
因为我仍然不知道为什么同时查询Serving类(通过Session的帮助)是错误的,有一个menu.getServings()可以提供你的服务(但有一个较少的观点(因为你得到的服务与serve.menu.id = menu.id),无论如何,无关紧要)