java - 更新包含对象字段的实体

标签 java hibernate jpa

我正在尝试更新包含另一个类类型的字段的实体。

所以这是我的实体:

@Entity
public class Owner {

    @Id
    @GeneratedValue
    private int id;

    @Column(name = "first_name")
    @NotNull(message="{NotNull}")
    @Size(min=2,max=15,message="{Size}")
    private String firstName;

    @NotNull(message="{NotNull}")
    @Size(min=2,max=15,message="{Size}")
    @Column(name = "last_name")
    private String lastName;

    @Valid
    @OneToOne(cascade = CascadeType.ALL)
    private Phone phone;

    @Valid
    @OneToOne(cascade = CascadeType.ALL)
    private Pet pet;

从这个角度看:

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>

<meta charset="ISO-8859-1"></meta>

<title>Owner details</title>
</head>
<body>
    <div id="owner">
        <form th:action="@{|/ownerList/${owner.id}.do|}"
            th:object="${owner}" method="post">
            <table>
                <tr>
                    <td>Id:</td>
                    <td><input type="text" th:field="*{id}" /></td>
                    <td th:if="${#fields.hasErrors('id')}" th:errors="*{id}">fieldError</td>
                </tr>
                <tr>
                    <td>First name</td>
                    <td><input type="text" th:field="*{firstName}" /></td>
                    <td th:if="${#fields.hasErrors('firstName')}"
                        th:errors="*{firstName}">fieldError</td>
                </tr>
                <tr>
                    <td>Last name</td>
                    <td><input type="text" th:field="*{lastName}" /></td>
                    <td th:if="${#fields.hasErrors('lastName')}"
                        th:errors="*{lastName}">fieldError</td>
                </tr>
                <tr>
                    <td>Phone</td>
                    <td><input type="text" th:field="*{phone.number}" /></td>
                    <td th:if="${#fields.hasErrors('phone.number')}"
                        th:errors="*{phones[0].number}">fieldError</td>
                </tr>
                <tr>
                    <td>Pet</td>
                    <td><input type="text" th:field="*{pet.petName}" /></td>
                    <td th:if="${#fields.hasErrors('pet.petName')}"
                        th:errors="*{pet.petName}">fieldError</td>
                </tr>
                <tr>
                    <td><input type="submit" value="update" name="action" /></td>
                    <td><input type="submit" value="delete" name="action" /></td>
                </tr>
            </table>
        </form>
        <a href="/ownerList">Back</a>
    </div>
</body>
</html>

我正在使用这个 Controller :

@RequestMapping(value = "/ownerList/{id}.do")
    public String ownerDetailsDo(@ModelAttribute(value = "owner") Owner owner, BindingResult result,
            @RequestParam(value = "action") String action, Model model) {


        switch (action) {
        case "update":
            ObjectBinder.bind(owner);
            ownerService.update(owner);
            return "ownerDetail";
        case "delete":
            ownerService.remove(owner.getId());
            model.addAttribute("ownerList", ownerService.getAll());
            return "ownerList";
        }
        model.addAttribute("owner", owner);
        return "ownerDetail";
    }

所以我试图更新所有者的对象,但在 .merge 之后的数据库内部我可以找到新的实体,例如电话,具有新的 Id。

为了澄清,例如我有: 所有者: 名字:XYZ 姓氏:BBB 宠物:鲍勃 电话:1234

当我尝试更新手机时,假设为“2222”,然后在数据库中我可以找到两条记录 第一个是“1234”,第二个是“2222”,我想让“2222”替换旧的“1234”。

最佳答案

如果您想在没有任何所有者引用的情况下删除手机,则需要添加@OrphanRemoval。

Orphan Removal in Relationships When a target entity in one-to-one or one-to-many relationship is removed from the relationship, it is often desirable to cascade the remove operation to the target entity. Such target entities are considered “orphans,” and the orphanRemoval attribute can be used to specify that orphaned entities should be removed. For example, if an order has many line items and one of them is removed from the order, the removed line item is considered an orphan. If orphanRemoval is set to true, the line item entity will be deleted when the line item is removed from the order.

The orphanRemoval attribute in @OneToMany and @oneToOne takes a Boolean value and is by default false.

The following example will cascade the remove operation to the orphaned customer entity when it is removed from the relationship:

@OneToMany(mappedBy="customer", orphanRemoval="true") public List getOrders() { ... }

@Entity
public class Owner {

    @Id
    @GeneratedValue
    private int id;

    @Column(name = "first_name")
    @NotNull(message="{NotNull}")
    @Size(min=2,max=15,message="{Size}")
    private String firstName;

    @NotNull(message="{NotNull}")
    @Size(min=2,max=15,message="{Size}")
    @Column(name = "last_name")
    private String lastName;

    @Valid
    @OneToOne(cascade = CascadeType.ALL, orphanRemoval="true")
    private Phone phone;

    @Valid
    @OneToOne(cascade = CascadeType.ALL, orphanRemoval="true")
    private Pet pet;

如果你这样做:

owner.set(new Phone(2222));
entityManager.merge(owner));
// update the owner phone
owner.set(new Phone(77777));
//the phone(2222) will be deleted
entityManager.merge(owner));

关于java - 更新包含对象字段的实体,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38826528/

相关文章:

java - 如何从 Maven 解析器中排除 persistence.xml

java - 在使用项目路径的同时可以使用Server.xml中的ROOT路径吗?

java - 无法创建内部bean 'org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter....'

hibernate - 从 Hibernate 3/Grails 2.2.4 迁移到 Hiberate 5/Grails 3.2.4 时出现 MappingException

java - 在 Spring boot Rest api 中使用 @embeded 时,在数据库中获取 null 值? java新手帮帮我吧

hibernate - 如何在Hibernate/JPA中为每个持久单元执行differnet import.sql?

java - PHP/Java 集成

java - 将 double 组转换为 float 组

java - 如何使用 Spring MVC 的单表继承获取子类属性

java - 未使用 Hibernate 持久化实体