I experience strange behavior with Ebean (version 3.2.2), whenever I try to use multiple @ManyToMany
attributes with CascadeType.ALL
in a model.
I've made a simplified example to reproduce the problem:
I have the following two Entities (getters omitted)
@Entity
public class Foo extends Model {
@Id
@GeneratedValue
private Long id;
@ManyToMany(cascade = CascadeType.ALL)
@JoinTable(name = "foo_bar1")
private List<Bar> bars1;
@ManyToMany(cascade = CascadeType.ALL)
@JoinTable(name = "foo_bar2")
private List<Bar> bars2;
public void addBar1(Bar bar1) {
bars1.add(bar1);
}
public void addBar2(Bar bar2) {
bars2.add(bar2);
}
}
and
@Entity
public class Bar extends Model {
@Id
@GeneratedValue
private Long id;
private String name;
@ManyToMany(mappedBy = "bars1")
private List<Foo> foos1;
@ManyToMany(mappedBy = "bars2")
private List<Foo> foos2;
public Bar(String name) {
this.name = name;
}
}
but it leads to strange behavior whenever I execute the following test
@Test
public void cascadeTest() {
Ebean.beginTransaction();
Foo foo = new Foo();
Bar bar1 = new Bar("bar1");
Bar bar2 = new Bar("bar2");
foo.addBar1(bar1);
foo.addBar2(bar2);
Ebean.save(foo);
Ebean.commitTransaction();
}
as the values in Foo.bars2
aren't persisted (e.g. foo.getBars2().size() == 0
).
Ebean generates the following SQL queries
insert into foo (id) values (1)
insert into bar (id, name) values (1,'bar1')
insert into foo_bar1 (foo_id, bar_id) values (1, 1)
insert into bar (id, name) values (2,'bar2')
without the needed insert into foo_bar2 (foo_id, bar_id) values (1, 2)
query.
Does someone know what's going on here?
This is interesting case. I made some tests and there are results:
After adding
foo
to bar lists Ebean saved relations correctly.So the following code:
produced following SQL queries:
But when I wanted read
foo
and it's bars I received interesting result.Following code:
gave result:
and produced queries:
Ebean should refer to
foo_bar1
table while looking forbar1
and tofoo_bar2
table while looking forbar2
. But in both cases Ebean queriedfoo_bar1
table.While I changed code to:
then Ebean referred two times to
foo_bar2
table.It seems that two
@ManyToMany
relations is too many for Ebean. I suppose that Ebean assumes that there can be only one jointable between two tables. And it's name is cached after first query.