Java 如何在spring中从Autopopulate列表中删除对象
我是春天+冬眠的新手。当我添加客户及其目的地(一对多关系)时,一切正常。但是,当我更新客户的目的地时,所有以前的目的地都会保留在数据库中,并带有空的客户外键 假设我插入4个目的地a、b、c、d。更新客户后,我插入x,y。然后,它总共存储6个目的地:a、b、c、d(带有空引用)和x、y(带有客户引用) 这是我的密码: 1)。客户实体 与目的地有一对多关系,且关系是单向的Java 如何在spring中从Autopopulate列表中删除对象,java,spring,hibernate,Java,Spring,Hibernate,我是春天+冬眠的新手。当我添加客户及其目的地(一对多关系)时,一切正常。但是,当我更新客户的目的地时,所有以前的目的地都会保留在数据库中,并带有空的客户外键 假设我插入4个目的地a、b、c、d。更新客户后,我插入x,y。然后,它总共存储6个目的地:a、b、c、d(带有空引用)和x、y(带有客户引用) 这是我的密码: 1)。客户实体 与目的地有一对多关系,且关系是单向的 @Entity @Table(name="customers") @Proxy(lazy=false) public class
@Entity
@Table(name="customers")
@Proxy(lazy=false)
public class CustomerEntity {
@Id
@Column(name="id")
@GeneratedValue
private Integer id;
private String description;
private String panNo;
private String cstNo;
private String vatNo;
@OneToMany(fetch = FetchType.EAGER,cascade = CascadeType.ALL)
@JoinColumn(name = "customer_id", referencedColumnName = "id")
public List<DestinationsEntity> destination = new AutoPopulatingList<DestinationsEntity>(DestinationsEntity.class);
//getter and setters
}
1)。AddCustomer.jsp
此代码用于在自动填充列表中添加更多目的地
<div id="destination_container">
<div><textarea row="3" col="5" class="destination_address" name= "destination[${0}].destination" placeholder="Please enter address"></textarea></div>
</div>
<script type="text/javascript">
$(document).ready(function(){
var index = 1;
/*
* Add more destination
*/
$('#add_more_destination').click(function(){
$('#destination_container').append('<div><textarea row="3" col="5" class="destination_address" name= "destination[${"'+index+'"}].destination" placeholder="Please enter address"></textarea><span class="remove_dest">*</span></div>');
index++;
});
});
</script>
更新客户信息
@RequestMapping(value = "/addCustomerForm", method = RequestMethod.GET)
public String addCustomerForm(ModelMap map) {
return "master/addCustomer";
}
@RequestMapping(value = "/addCustomer", method = RequestMethod.POST)
public String addCustomer(@ModelAttribute(value = "customer") CustomerEntity customer,BindingResult result, HttpServletRequest request) {
customerService.addCustomer(customer);
return "redirect:/customer";
}
这是我昨晚试过的新东西。问题部分解决了
@ModelAttribute
public void updateOperation(HttpServletRequest request, ModelMap map) {
if(null !=request.getParameter("id"))
map.addAttribute("customer1", customerService.findOne(Integer.parseInt(request.getParameter("id"))));
}
@RequestMapping(value = "/updateCustomerForm/{customerId}", method = RequestMethod.GET)
public String updateCustomerForm(@PathVariable("customerId") Integer customerId, ModelMap map, HttpServletRequest request) {
CustomerEntity customerEntity = customerService.findOne(customerId);
map.addAttribute("customer", customerEntity);
map.addAttribute("destinationss",customerEntity.getDestination());
}
@RequestMapping(value = "/updateCustomer", method = RequestMethod.POST)
public String updateCustomer(@ModelAttribute(value = "customer1")CustomerEntity customer1,BindingResult result, HttpServletRequest request,HttpServletResponse response) {
customerService.updateCustomer(customer1);
return "redirect:/customer";
}
}
1)。CustomerServiceImpl
public class CustomerServiceImpl implements CustomerService{
@Autowired
private CustomerDao customerDao;
@Override
@Transactional
public void addCustomer(CustomerEntity customer) {
customerDao.addCustomer(customer);
}
@Override
@Transactional
public CustomerEntity findOne(Integer id){
return customerDao.findOne(id);
}
@Override
@Transactional
public void updateCustomer(CustomerEntity customerEntity){
if (null != customerEntity) {
customerDao.updateCustomer(customerEntity);
}
}
}
public class CustomerDaoImpl implements CustomerDao{
@Autowired
private SessionFactory sessionFactory;
@Override
@Transactional
public void addCustomer(CustomerEntity customer){
this.sessionFactory.getCurrentSession().save(customer);
}
@Override
public CustomerEntity findOne(Integer id){
return (CustomerEntity) sessionFactory.getCurrentSession().load(CustomerEntity.class, id);
}
@Override
@Transactional
public void updateCustomer(CustomerEntity customerEntity){
if (null != customerEntity) {
this.sessionFactory.getCurrentSession().update(customerEntity);
}
}
}
2).客户DAOImpl
public class CustomerServiceImpl implements CustomerService{
@Autowired
private CustomerDao customerDao;
@Override
@Transactional
public void addCustomer(CustomerEntity customer) {
customerDao.addCustomer(customer);
}
@Override
@Transactional
public CustomerEntity findOne(Integer id){
return customerDao.findOne(id);
}
@Override
@Transactional
public void updateCustomer(CustomerEntity customerEntity){
if (null != customerEntity) {
customerDao.updateCustomer(customerEntity);
}
}
}
public class CustomerDaoImpl implements CustomerDao{
@Autowired
private SessionFactory sessionFactory;
@Override
@Transactional
public void addCustomer(CustomerEntity customer){
this.sessionFactory.getCurrentSession().save(customer);
}
@Override
public CustomerEntity findOne(Integer id){
return (CustomerEntity) sessionFactory.getCurrentSession().load(CustomerEntity.class, id);
}
@Override
@Transactional
public void updateCustomer(CustomerEntity customerEntity){
if (null != customerEntity) {
this.sessionFactory.getCurrentSession().update(customerEntity);
}
}
}
问题是Spring将为您提供新的客户实体,所以我猜这个客户中的目标实体最初是空的。所以在更新操作中,您只需添加一些新的目标实体,然后根据代码将它们添加到客户 因此,在这种情况下,客户实体仅具有新的目标对象,而先前映射的现有目标实体不存在于客户实体中 要解决此问题,首先从数据库中获取客户实体,然后此实体将具有目标对象集。现在,对于该客户,您可以添加新的目标对象,并在需要时更新现有的目标对象,然后让Hibernate执行更新操作。在这种情况下,Hibernate可以查看您以前的目标对象以及新的目标对象,并基于此运行插入和更新查询 代码如下所示:
// First get the customer object from database:
Customer customer = (Customer) this.sessionFactory.getCurrentSession().get(Customer.class, customerId);
// Now add your destination objects, if you want you can update the existing destination entires here.
for (int i = 0; i < destinationAddrs.length; i++) {
DestinationsEntity destination = new DestinationsEntity();
destination.setDestination(destinationAddrs[i]);
customer.getDestinationEntity().add(destination);
}
// Then do the update operation
this.sessionFactory.getCurrentSession().update(customer);
//首先从数据库获取客户对象:
Customer=(Customer)this.sessionFactory.getCurrentSession().get(Customer.class,customerId);
//现在添加目标对象,如果需要,可以在此处更新现有的目标实体。
for(int i=0;i
您的问题不清楚,请适当解释。事实上,我与一对多客户有多个目的地的关系。当我用4个目的地保存1个客户时,所有客户都工作正常。但是,当尝试更新客户对象时,先前将destinations for ign键更改为null,并将新的destinations保存在数据库中解决方案是获取客户的目的地并将其存储在一个集合中,然后将新的目的地添加到集合中,然后执行更新。现在Hibernate将处理好这段关系。如果不这样做,则hibernate假定您正在尝试删除旧的目标并添加新的目标,这就是为什么在目标表中为那些旧实体删除外键的原因。当我在集合中添加新目标时,它工作正常,但当减少目标时,结果生成错误,正如我前面解释的那样。我认为当@modelAttribute在updateCustomer中创建新的customer对象时,这就是问题产生的原因。但不确定是否要向现有客户添加新的目的地,对吗?@modeldattribute始终为我提供新的客户对象如何使用persist对象进行回复。。任何解决办法。或工作示例。在更新页面上呈现之前,如何加载持久对象而不是新的客户对象我正在传递用户请求的客户对象。。但随后它会提交updatecustomer表单,然后在controller@modelAttribute中创建新对象并再次设置新对象中的所有数据。我想将其设置为已存在的持久对象@modelAttribute
,这只会帮助您从UI获取数据,而不会给您现有的目标条目。如果需要,请确保前端的表单也发送了目标条目。@JavedShhaikh,您尝试过的内容,请更新您的问题并向我们显示代码。在调用hibernate update之前,还要打印您为目的地获取的数据,以确保您拥有所有目的地条目。