java.lang.IllegalStateException:org.hibernate.TransientPropertyValueException [英] java.lang.IllegalStateException: org.hibernate.TransientPropertyValueException

查看:1630
本文介绍了java.lang.IllegalStateException:org.hibernate.TransientPropertyValueException的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的应用程序有两个实体产品和类别。添加产品时,用户选择产品所属的类别。但是,当将产品保存到数据库时,我遇到了错误。


org.springframework.web.util.NestedServletException:请求处理失败;嵌套的异常是java.lang.IllegalStateException:org.hibernate.TransientPropertyValueException:非空属性引用一个瞬态值 - 在当前操作之前必须保存瞬态实例


实体的内容是
Category.java

  @Entity 
@Table )
public class Category {

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
私人长ID;

@Column(name =category_name)
private String categoryName;

@Column(name =description)
私有字符串描述;

@OneToMany(mappedBy =category,fetch = FetchType.LAZY)
private Set< Product>产品;

// getter and setter method
}

java

  @Entity 
@Table(name =product)
public class Product {

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
私人长ID;

@Column(name =name)
@NotNull
@NotEmpty
私人字符串名称;

@Column(name =description)
私有字符串描述;

@Column(name =manufacture)
私人字符串制造;

@Column(name =price)
私人长仓;

@Column(name =image_name)
private String imageName;

@ManyToOne
@JoinColumn(name =category_id,referencedColumnName =id,nullable = false)
Category category;

// getter and setter method
}

ProductDAO。 java

  @Repository(ProductDAO)
@Transactional
public class ProductDAO {

@PersistenceContext
私人EntityManager entityManager;

public EntityManager getEntityManager(){
return entityManager;
}

public void setEntityManager(EntityManager entityManager){
this.entityManager = entityManager;
}

public void create(Product product){
entityManager.merge(product.getCategory());
entityManager.persist(product);
}
//其他方法
}

我的jsp文件

 < form:form method =postcommandName =productaction =add.htmlenctype =multipart /格式数据> 
Productname< form:input path =name/>
< form:errors path =nameclass =error/>< br>
description< form:input path =description/>< br>
price< form:input path =price/>< br>
制造< form:input path =manufacture/>< br>
Category
< form:select path =category>
< form:options items =$ {categories}itemValue =iditemLabel =categoryName/>
< / form:select>
< form:errors path =categoryclass =error/>< br>
< br />
产品图片< input type =filename =file/>
< form:errors path =imageNameclass =error/>< br>
< input type =submitclass =registervalue =Save>
< / form:form>

我的转换器

  public class CategoryConverter implements Converter< String,Category> {

@Autowired
private CategoryService categoryService;

public类型转换(String id){
返回categoryService.findById(Long.valueOf(id));
}
}

感谢任何帮助

解决方案

请将(Cascade = CascadeType.ALL)添加到产品的类别字段映射中

  @ManyToOne(cascade = CascadeType.ALL)
@JoinColumn(name =category_id,referencedColumnName =id,nullable = false)
Category category;

并在ProductDAO中移除此行:

  entityManager.merge(product.getCategory()); 

注意:如果您的产品类别是现有的类别,则应先加载它,然后将其设置为您的产品,这是正常的流量。不要新建重复的Category对象。

My application has two entity Product and Category. When add product , user choose the category that product belong to. But when save the product to data base i meet the error

org.springframework.web.util.NestedServletException: Request processing failed; nested exception is java.lang.IllegalStateException: org.hibernate.TransientPropertyValueException: Not-null property references a transient value - transient instance must be saved before current operation

the content of entity is Category.java

@Entity
@Table(name="category")
public class Category {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private long id;

@Column(name="category_name")
private String categoryName;

@Column(name="description")
private String description;

@OneToMany(mappedBy = "category", fetch=FetchType.LAZY)
private Set<Product> products;

//getter and setter method
}

Product.java

@Entity
@Table(name="product")
public class Product {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private long id;

@Column(name="name")
@NotNull
@NotEmpty
private String name;

@Column(name="description")
private String description;

@Column(name="manufacture")
private String manufacture;

@Column(name="price")
private long price;

@Column(name="image_name")
private String imageName;

@ManyToOne
@JoinColumn(name = "category_id", referencedColumnName = "id", nullable = false)
Category category;

//getter and setter method
}

ProductDAO.java

@Repository("ProductDAO")
@Transactional
public class ProductDAO {

@PersistenceContext
private EntityManager entityManager;

public EntityManager getEntityManager() {
    return entityManager;
}

public void setEntityManager(EntityManager entityManager) {
    this.entityManager = entityManager;
}

public void create(Product product) {
    entityManager.merge(product.getCategory());
    entityManager.persist(product);
}
//other method
}

my jsp file

<form:form method="post" commandName="product" action="add.html" enctype="multipart/form-data">
    Productname <form:input path="name"/>
                <form:errors path="name" class ="error"/><br>
    description    <form:input   path="description"/><br>
    price    <form:input   path="price"/><br>
    manufacture <form:input path="manufacture"/><br>
    Category
    <form:select path="category">
    <form:options items="${categories}" itemValue="id" itemLabel="categoryName" />
    </form:select>
    <form:errors path="category" class ="error"/><br>
    <br/>
    Product image<input type="file" name="file" />
    <form:errors path="imageName" class ="error"/><br>
    <input type="submit" class="register" value="Save">
</form:form>

my Converter

public class CategoryConverter implements Converter<String, Category>{

    @Autowired
    private CategoryService categoryService;

    public Category convert(String id) {
        return categoryService.findById(Long.valueOf(id));
    }
}

thank for any help

解决方案

please add (cascade=CascadeType.ALL) into category field mapping of Product

@ManyToOne(cascade=CascadeType.ALL)
@JoinColumn(name = "category_id", referencedColumnName = "id", nullable = false)
Category category;

and remove this line in ProductDAO:

entityManager.merge(product.getCategory());

NOTE: if your product's category is an existing one, you should load it first then set it to your product, this is normal flow. Do not new duplicated Category object.

这篇关于java.lang.IllegalStateException:org.hibernate.TransientPropertyValueException的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆