正在从父实体的集合中删除子实体 class
Deleting child entity from set in parent class
我正在尝试将图像文件附加到名为产品的实体。我可以很好地创建产品和图像,但是当我尝试删除图像时出现以下错误。
HTTP 500 - 请求处理失败;嵌套异常是 org.hibernate.PersistentObjectException:传递给持久化的分离实体:com.IJM.model.Product
产品Class
@Entity
@Table(name = "Product")
public class Product {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "Id")
private Long id;
@NotNull
@Size(min = 3, max = 10)
@Column(name = "Code", nullable = false)
private String code;
@NotNull
@Size(min = 3, max = 50)
@Column(name = "Name", nullable = false)
private String name;
@Size( max = 50)
@Column(name = "Description", nullable = false)
private String description;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name = "Id_Category")
private Category category;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name = "Id_Unit")
private Unit unit;
@OneToMany(cascade = CascadeType.ALL,
fetch= FetchType.EAGER,
orphanRemoval = true,
mappedBy="product")
private Set<Image> images;
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Category getCategory() {
return category;
}
public void setCategory(Category category) {
if(this.category==null||!this.category.equals(category))
{
this.category=category;
}
return;
}
public Unit getUnit() {
return unit;
}
public void setUnit(Unit unit) {
if(this.unit==null||!this.unit.equals(unit))
{
this.unit=unit;
}
return;
}
public Set<Image> getImages() {
return images;
}
public void setImages(Set<Image> images) {
this.images = images;
}
}
图片Class
@Entity
@Table(name = "product_Image")
public class Image {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name="id", nullable = false)
private long id;
@Lob
@Column(name = "File", nullable = false)
private byte[] file;
@Column(name = "Checksum",nullable = false)
private String checksum;
@Column(name = "Extension",nullable = false)
private String extension;
@Column(name = "File_Name",nullable = false)
private String file_name;
@Column(name = "Size",nullable = false)
private int size;
@Column(name = "Last_Updated",nullable = false)
private Timestamp last_Updated;
@ManyToOne(cascade=CascadeType.ALL)
@JoinColumn(name="Id_Product")
private Product product;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name="Id_Directory")
private Directory directory;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public byte[] getFile() {
return file;
}
public void setFile(byte[] file) {
this.file = file;
}
public String getChecksum() {
return checksum;
}
public void setChecksum(String checksum) {
this.checksum = checksum;
}
public String getExtension() {
return extension;
}
public void setExtension(String extension) {
this.extension = extension;
}
public String getFile_name() {
return file_name;
}
public void setFile_name(String file_name) {
this.file_name = file_name;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
public Timestamp getLast_Updated() {
return last_Updated;
}
public void setLast_Updated(Timestamp last_Updated) {
this.last_Updated = last_Updated;
}
public Product getProduct() {
return product;
}
public void setProduct(Product product) {
this.product = product;
}
public Directory getDirectory() {
return directory;
}
public void setDirectory(Directory directory) {
this.directory = directory;
}
这是控制器调用删除方法的代码
@RestController
@RequestMapping("/image")
public class ImageController {
@Autowired
ProductService productService;
@Autowired
ImageService imageService;
private static final String productImagePath="C:\IJM\Images\Product\";
@RequestMapping(value = "/product/{code}", method = RequestMethod.DELETE)
public ResponseEntity<Image> deleteProductImage(@PathVariable("code") String code) {
System.out.println("Fetching & Deleting Image for product " + code);
code = code.toUpperCase();
if (!productService.isProductExist(code)) {
System.out.println("Product with code " + code + " not found");
return new ResponseEntity<Image>(HttpStatus.NOT_FOUND);
}
else
{
Product product = productService.findProductByCode(code);
if(product.getImages()!=null)
{
for(Image image:product.getImages())
{
product.getImages().remove(image);
image.setProduct(null);
imageService.deleteImage(image.getId());
}
productService.saveProduct(product);
try{
File file = new File(productImagePath+code);
if(FileDeleter.removeDirectory(file)){
System.out.println(file.getName() + " is deleted!");
}else{
System.out.println("Delete operation is failed.");
}
}catch(Exception e){
e.printStackTrace();
}
}
}
return new ResponseEntity<Image>(HttpStatus.NO_CONTENT);
}
}
万一其他人想知道..服务只是调用 DAO
@Override
public void deleteImage(long id) {
Image image = imageDao.findById(id);
imageDao.delete(image);
}
这就是道Class
@Repository("imageDao")
public class ImageDaoImpl extends AbstractDao<Long,Image> implements ImageDao{
@Override
public void delete(Image image) {
super.delete(image);
}
}
这是我的抽象 DAO 中的代码 class
public void delete(T entity) {
getSession().delete(entity);
}
似乎这些行的顺序不正确。
product.getImages().remove(image);
image.setProduct(null);
imageService.deleteImage(image.getId());
也不确定imageService.deleteImage(image.getId());
在做什么。不需要。
请按以下方式尝试。
for(Image image:product.getImages())
{
image.setProduct(null);
product.getImages().remove(image);
}
productService.saveProduct(product);
这应该足够了。我知道更改顺序没有任何意义,但它对我有用。
我正在尝试将图像文件附加到名为产品的实体。我可以很好地创建产品和图像,但是当我尝试删除图像时出现以下错误。
HTTP 500 - 请求处理失败;嵌套异常是 org.hibernate.PersistentObjectException:传递给持久化的分离实体:com.IJM.model.Product
产品Class
@Entity
@Table(name = "Product")
public class Product {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "Id")
private Long id;
@NotNull
@Size(min = 3, max = 10)
@Column(name = "Code", nullable = false)
private String code;
@NotNull
@Size(min = 3, max = 50)
@Column(name = "Name", nullable = false)
private String name;
@Size( max = 50)
@Column(name = "Description", nullable = false)
private String description;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name = "Id_Category")
private Category category;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name = "Id_Unit")
private Unit unit;
@OneToMany(cascade = CascadeType.ALL,
fetch= FetchType.EAGER,
orphanRemoval = true,
mappedBy="product")
private Set<Image> images;
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Category getCategory() {
return category;
}
public void setCategory(Category category) {
if(this.category==null||!this.category.equals(category))
{
this.category=category;
}
return;
}
public Unit getUnit() {
return unit;
}
public void setUnit(Unit unit) {
if(this.unit==null||!this.unit.equals(unit))
{
this.unit=unit;
}
return;
}
public Set<Image> getImages() {
return images;
}
public void setImages(Set<Image> images) {
this.images = images;
}
}
图片Class
@Entity
@Table(name = "product_Image")
public class Image {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name="id", nullable = false)
private long id;
@Lob
@Column(name = "File", nullable = false)
private byte[] file;
@Column(name = "Checksum",nullable = false)
private String checksum;
@Column(name = "Extension",nullable = false)
private String extension;
@Column(name = "File_Name",nullable = false)
private String file_name;
@Column(name = "Size",nullable = false)
private int size;
@Column(name = "Last_Updated",nullable = false)
private Timestamp last_Updated;
@ManyToOne(cascade=CascadeType.ALL)
@JoinColumn(name="Id_Product")
private Product product;
@ManyToOne(cascade = CascadeType.MERGE)
@JoinColumn(name="Id_Directory")
private Directory directory;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public byte[] getFile() {
return file;
}
public void setFile(byte[] file) {
this.file = file;
}
public String getChecksum() {
return checksum;
}
public void setChecksum(String checksum) {
this.checksum = checksum;
}
public String getExtension() {
return extension;
}
public void setExtension(String extension) {
this.extension = extension;
}
public String getFile_name() {
return file_name;
}
public void setFile_name(String file_name) {
this.file_name = file_name;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
public Timestamp getLast_Updated() {
return last_Updated;
}
public void setLast_Updated(Timestamp last_Updated) {
this.last_Updated = last_Updated;
}
public Product getProduct() {
return product;
}
public void setProduct(Product product) {
this.product = product;
}
public Directory getDirectory() {
return directory;
}
public void setDirectory(Directory directory) {
this.directory = directory;
}
这是控制器调用删除方法的代码
@RestController
@RequestMapping("/image")
public class ImageController {
@Autowired
ProductService productService;
@Autowired
ImageService imageService;
private static final String productImagePath="C:\IJM\Images\Product\";
@RequestMapping(value = "/product/{code}", method = RequestMethod.DELETE)
public ResponseEntity<Image> deleteProductImage(@PathVariable("code") String code) {
System.out.println("Fetching & Deleting Image for product " + code);
code = code.toUpperCase();
if (!productService.isProductExist(code)) {
System.out.println("Product with code " + code + " not found");
return new ResponseEntity<Image>(HttpStatus.NOT_FOUND);
}
else
{
Product product = productService.findProductByCode(code);
if(product.getImages()!=null)
{
for(Image image:product.getImages())
{
product.getImages().remove(image);
image.setProduct(null);
imageService.deleteImage(image.getId());
}
productService.saveProduct(product);
try{
File file = new File(productImagePath+code);
if(FileDeleter.removeDirectory(file)){
System.out.println(file.getName() + " is deleted!");
}else{
System.out.println("Delete operation is failed.");
}
}catch(Exception e){
e.printStackTrace();
}
}
}
return new ResponseEntity<Image>(HttpStatus.NO_CONTENT);
}
}
万一其他人想知道..服务只是调用 DAO
@Override
public void deleteImage(long id) {
Image image = imageDao.findById(id);
imageDao.delete(image);
}
这就是道Class
@Repository("imageDao")
public class ImageDaoImpl extends AbstractDao<Long,Image> implements ImageDao{
@Override
public void delete(Image image) {
super.delete(image);
}
}
这是我的抽象 DAO 中的代码 class
public void delete(T entity) {
getSession().delete(entity);
}
似乎这些行的顺序不正确。
product.getImages().remove(image);
image.setProduct(null);
imageService.deleteImage(image.getId());
也不确定imageService.deleteImage(image.getId());
在做什么。不需要。
请按以下方式尝试。
for(Image image:product.getImages())
{
image.setProduct(null);
product.getImages().remove(image);
}
productService.saveProduct(product);
这应该足够了。我知道更改顺序没有任何意义,但它对我有用。