[英]Spring Data Rest projection for Embedded Entities
Lets assume I have the following entities: 让我们假设我有以下实体:
@Entity
public class Registration {
@ManyToOne
private Student student;
//getters, setters
}
@Entity
public class Student {
private String id;
private String userName;
private String name;
private String surname;
//getters, setters
}
@Projection(name="minimal", types = {Registration.class, Student.class})
public interface RegistrationProjection {
String getUserName();
Student getStudent();
}
I'm trying to create the following JSON representation, So when I use http://localhost:8080/api/registrations?projection=minimal
I dont need all the user data to come along: 我正在尝试创建以下JSON表示,所以当我使用
http://localhost:8080/api/registrations?projection=minimal
我不需要所有用户数据出现:
{
"_links": {
"self": {
"href": "http://localhost:8080/api/registrations{?page,size,sort,projection}",
}
},
"_embedded": {
"registrations": [
{
"student": {
"userName": "user1"
}
}
],
"_links": {
"self": {
"href": "http://localhost:8080/api/registrations/1{?projection}",
}
}
}
}
However the Projection I have created I get an exception(it works without the getUserName() statement. Obviously I have defined the interface in the wrong way...but which is the correct way to do something like this? 然而,我创建的Projection我得到一个异常(它没有getUserName()语句。显然我已经以错误的方式定义了接口......但是这样做的正确方法是什么?
EDIT: Exception is the following 编辑:例外情况如下
Invalid property 'userName' of bean class [com.test.Registration]:
Could not find field for property during fallback access! (through reference chain: org.springframework.hateoas.PagedResources["_embedded"]
->java.util.UnmodifiableMap["registrations"]->java.util.ArrayList[0]->org.springframework.data.rest.webmvc.json.["content"]
->$Proxy119["userName"])</div></body></html>
As exception said userName
is not a member of Registration
entity. 作为例外,
userName
不是Registration
实体的成员。 That why it failed. 这就是它失败的原因。 But I think you already understand that.
但我想你已经明白了。
First at all if you just want to expose its projection for Registration
you should first change the following line: 首先,如果您只想公开其
Registration
预测,您应首先更改以下行:
@Projection(name="minimal", types = {Registration.class, Student.class})
By setting types = {Registration.class, Student.class}
you asked Spring Data Rest to apply projection on Registration.class
and Student.class
. 通过设置
types = {Registration.class, Student.class}
您要求Spring Data Rest在Registration.class
和Student.class
上应用投影。 And that can cause some issue because depending of the type you should not have the same member/methods. 这可能会导致一些问题,因为根据类型,您不应该使用相同的成员/方法。 In practice
types
must share a common ancestor. 在实践中,
types
必须共享共同的祖先。
Otherwise for the main problem you should try virtual projections the following thing (I didn't try on your sample but it should work, I hope): 否则对于主要问题你应该尝试虚拟投影以下的事情(我没有尝试你的样本,但它应该工作,我希望):
@Projection(name="minimal", types = {Registration.class})
public interface RegistrationProjection {
@Value("#{target.getStudent().getUserName()}")
String getUserName();
}
I don't know if you are familiar with SPeL but the previous code just create a getUserName
like this.getStudent().getUserName()
because target
is bound on the instance object (see documentation). 我不知道您是否熟悉SPeL,但前面的代码只是创建了一个
getUserName
如this.getStudent().getUserName()
因为target
绑定在实例对象上(参见文档)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.