Spring boot SpringRESTAPI-外键ID而不是整个对象

Spring boot SpringRESTAPI-外键ID而不是整个对象,spring-boot,rest,spring-rest,Spring Boot,Rest,Spring Rest,我的RESTAPI GET方法返回的Json有问题 这就是我的实体的外观: @Entity public class Employee { ... @ManyToOne(fetch = FetchType.EAGER, optional = false) @JoinColumn(name = "department_id", nullable = true) private Department department; } @Entity public clas

我的RESTAPI GET方法返回的Json有问题

这就是我的实体的外观:

@Entity
public class Employee {
    ...
    @ManyToOne(fetch = FetchType.EAGER, optional = false)
    @JoinColumn(name = "department_id", nullable = true)
    private Department department;
}

@Entity
public class Department {
    ...
    @OneToMany(mappedBy = "department", fetch = FetchType.EAGER, cascade = CascadeType.ALL)
    @JsonBackReference
    private Set<Employee> employees;
}
现在,取而代之的是整个部门对象,我只想得到一个简单的id:
“Department\u id”:1
,我不知道怎么做

第二个问题:在RESTAPI中,这种情况下的
好做法是什么?我应该保持原样吗;只暴露id(我问你怎么做);或者使用DTO而不显示它?
此外,无论如何,我要添加到该用户部门的链接,在这种情况下,我认为只留下id应该可以(如果我错了,请告诉我)。

期待您的回答

一个好的做法是定义一个DTO来表示API公开的数据。 这应该与您的领域(员工)分离,因为它将为您提供更大的灵活性,就像您想要实现的一样

class EmployeeDTO extends RepresentationModel {
    private long id;
    private String surname;
    private long departmentId;

   // getters and setters
}
这应该行得通。当然,您需要将员工实体映射到EmployeeDTO。RepresentationModel包含您想要用于HATEOAS的_links属性(例如,查看 )

关于从数据库中公开id,我认为不这样做的一个很好的理由是,您免费提供有关数据库大小的信息,而这可能是您不想做的。甚至可以从中获得更多信息

在这里,您可以找到关于该主题的良好讨论:

我建议看一下UUID,它是一个通用的唯一字母数字标识符,不会公开有关数据的信息。
关于UUID的更多信息:

一个好的做法是定义一个DTO,它表示API公开的数据。 这应该与您的领域(员工)分离,因为它将为您提供更大的灵活性,就像您想要实现的一样

class EmployeeDTO extends RepresentationModel {
    private long id;
    private String surname;
    private long departmentId;

   // getters and setters
}
这应该行得通。当然,您需要将员工实体映射到EmployeeDTO。RepresentationModel包含您想要用于HATEOAS的_links属性(例如,查看 )

关于从数据库中公开id,我认为不这样做的一个很好的理由是,您免费提供有关数据库大小的信息,而这可能是您不想做的。甚至可以从中获得更多信息

在这里,您可以找到关于该主题的良好讨论:

我建议看一下UUID,它是一个通用的唯一字母数字标识符,不会公开有关数据的信息。
关于UUID的更多信息:

@JsonIgnoreProperties

要仅获取部门id而不更改任何实现,您可以使用
@JsonIgnoreProperties({“name”,“room”})
如下

@ManyToOne(fetch = FetchType.EAGER, optional = false)
@JoinColumn(name = "department_id", nullable = true)
@JsonIgnoreProperties({"name", "room"})
private Department department;
[
    {
        "id": 1,
        "surname": "smith",
        "department": {
            "id": 1
        }
    }
]
它将以以下方式响应

@ManyToOne(fetch = FetchType.EAGER, optional = false)
@JoinColumn(name = "department_id", nullable = true)
@JsonIgnoreProperties({"name", "room"})
private Department department;
[
    {
        "id": 1,
        "surname": "smith",
        "department": {
            "id": 1
        }
    }
]
您可能还想探索其他方法来实现同样的目标


最佳实践

我们永远不应该公开和返回我们的模态和实体作为对API的响应。我们可以创建DTO/DAO来接收和传输对象和数据。您还可以使用将实体转换为DTO,并将DTO转换为实体


对于DTO,您可以只包含部门id,如果需要,可以使用存储库获取对象

@JsonIgnoreProperties

要仅获取部门id而不更改任何实现,您可以使用
@JsonIgnoreProperties({“name”,“room”})
如下

@ManyToOne(fetch = FetchType.EAGER, optional = false)
@JoinColumn(name = "department_id", nullable = true)
@JsonIgnoreProperties({"name", "room"})
private Department department;
[
    {
        "id": 1,
        "surname": "smith",
        "department": {
            "id": 1
        }
    }
]
它将以以下方式响应

@ManyToOne(fetch = FetchType.EAGER, optional = false)
@JoinColumn(name = "department_id", nullable = true)
@JsonIgnoreProperties({"name", "room"})
private Department department;
[
    {
        "id": 1,
        "surname": "smith",
        "department": {
            "id": 1
        }
    }
]
您可能还想探索其他方法来实现同样的目标


最佳实践

我们永远不应该公开和返回我们的模态和实体作为对API的响应。我们可以创建DTO/DAO来接收和传输对象和数据。您还可以使用将实体转换为DTO,并将DTO转换为实体


对于DTO,您可以只包含部门id,如果需要,可以使用存储库获取对象

嘿,你们能给出一个提示,或者举个例子,如何将实体映射到扩展了RepresentationModel的DTO吗?现在,使用实现RepresentationModelAssembler的类添加链接,然后在toModel函数中调用(employee)的EntityModel.of(EntityModel)@昵称11我回答了你的另一个问题,看看它是否适合你嘿,你能给出一个提示,或者举个例子,如何将实体映射到DTO以扩展RepresentationModel吗?现在,使用实现RepresentationModelAssembler的类添加链接,然后在toModel函数中调用(employee)的EntityModel.of(EntityModel)@昵称11我回答了你的另一个问题,看看是否适合你