java.lang.IollegalStateException:在同步过程中,通过一个未标记为cascade PERS



我有两个2类,它们是多对多的关系。

@Entity
@Table(name = "recipies")
public class Recipie implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name;
private String url;
private String image;
@ManyToMany
@JoinTable(
        name = "recipie_ingredients",
        joinColumns = {
            @JoinColumn(name = "recipie_id", referencedColumnName = "id")},
        inverseJoinColumns = {
            @JoinColumn(name = "ingredient_id", referencedColumnName = "id")})
private List<Ingredient> ingredients = new ArrayList<>();



@Entity
@Table(name = "ingredients")
public class Ingredient implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    private String name;
    @ManyToMany(mappedBy = "ingredients") 
    private List<Recipie> recipies; 

我想用这种方式创建一个新的接收器:

List<Ingredient> ingredientsList = new ArrayList<>();

String ingredientName = "example";
Ingredient ingredient = ingredientsDao.findIngredientByName(ingredientName);
if (ingredient == null) {
   ingredient = new Ingredient();
   ingredient.setName(ingredientName);
}
ingredientsList.add(ingredient);
.....
recipie.setIngredients(ingredientsList);
recipiesDao.addRecipie(recipie);

如果数据库中不存在成分,就会出现类似的错误

Caused by: java.lang.IllegalStateException: During synchronization a new object was found through a relationship that was not marked cascade PERSIST

有没有任何方法可以自动在表中创建Ingredient对象?

我尝试添加CascadeType.PERSIST,但它也不起的作用

@ManyToMany(mappedBy = "ingredients", cascade = CascadeType.PERSIST) 
private List<Recipie> recipies; 

首先,对于双向关系,双方都需要更新,所以:

recipe.getIngredients().add(ingredient);
ingredient.getRecipes().add(recipe);

然后,您可以在传递给save()的关系一侧将级联设置为PERSIST。因此,如果您正在保存recipe,则应使用标记Recipe.ingredients

@ManyToMany(cascade = CascadeType.PERSIST)

(旁注,拼写为"recipie")

正如@Gimby所提到的,您需要分配关系的双方。

与@Many打交道时。。。侧面关系我总是初始化集合(你已经在一侧完成了):

@Entity
@Table(name = "recipies")
public class Recipie implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;
    private String url;
    private String image;
    @ManyToMany
    @JoinTable(
        name = "recipie_ingredients",
        joinColumns = {
            @JoinColumn(name = "recipie_id", referencedColumnName = "id")},
        inverseJoinColumns = {
            @JoinColumn(name = "ingredient_id", referencedColumnName = "id")})
    private List<Ingredient> ingredients = new ArrayList<>();
    ...
}

@Entity
@Table(name = "ingredients")
public class Ingredient implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    private String name;
    @ManyToMany(mappedBy = "ingredients") 
    private List<Recipie> recipies = new ArrayList<>(); 
    ...
}

然后你的逻辑略有变化:

String ingredientName = "example";
Ingredient ingredient = ingredientsDao.findIngredientByName(ingredientName);
if (ingredient == null) {
   ingredient = new Ingredient();
   ingredient.setName(ingredientName);
}
...
// Don't forget to assign both sides of the relationship
recipe.getIngredients().add(ingredient);
ingredient.getRecipies().add(recipe);
recipiesDao.addRecipe(recipe);

然后,这应该会正确地级联持久化/更新。

当你试图找出如何将数量与成分联系起来时,真正的乐趣就会开始。。。

最新更新