Hibernate数据映射到子对象



我试图弄清楚如何将请求中传入的数据映射到Hibernate对象,问题是传入的数据可能是对象或子对象,字段数据不一定是已知的-表单是用户配置的,以包含和收集所需的数据。

对象大致如下:

Job {
  String title;
  @ManyToOne
  @JoinColumn(name = "location_id")
  JobLocation location;
}
JobLocation {
  int id;
  String description;
  double latitude;
  double longitude;
}

因此,如果用户已经定义他们想要编辑JobLocation描述,我们将在请求中返回

一行的内容。
{ jobLocationDescription: 'Santa Fe' }

如何将其映射回我正在处理的Job的子?在节省时间时,我所拥有的是对Job的参考,所有其他项目可能会根据他们在下拉菜单中选择的内容而变化。一种选择是存储一个引用,如job.location.description,并使用getter和反射来做一个进程驱动选项:

String[] field = requestField.split(".");
Entity ent = (get object from field[0]);
if (field.length > 2) {
  ent = ent.get[get method name from next field position]();
}
ent.set[get method name from last field[] value](requestValue);

遗憾的是,没有什么说它不能是多层的,为了得到我们目前认为的方法,我们必须使用反射。还有其他更好的方法来做这种手术吗?还是我们只能在这个过程中挣扎?

在我们的项目中我也有类似的需求。我们最终使用反射+注释进行映射。简而言之,我们有这样的东西来构造对象。

class Job {
  String title;
  @ManyToOne
  @JoinColumn(name = "location_id")
  @EntityMapper(isRef="true")//Custom Annotation
  JobLocation location;
}
class JobLocation {
  @EntityMapper(fieldName="jobLocationId")
  int id;
  @EntityMapper(fieldName="jobLocationDescription")//Custom Annotation
  String description;
  double latitude;
  double longitude;
}

如果你不明白我的意思,我们创建了自定义注释,并编写了一个实用程序方法,通过反射循环遍历具有注释的元素,如下所示:

for (Field field : object.getClass().getDeclaredFields()) {
   //check for the EntityMapper annotation
   if (field.getAnnotation(EntityMapper.class) != null) {
       .
       .
       .//Use more reflection to use getters and setters to create and assign values from the JSON request.
   }
}

如果在编译时知道要调用的方法的名称,则不必使用反射。听起来你需要反思一下。但是,这并不意味着您必须使用原始的java.lang.reflect API,直接使用它是相当痛苦的。如果您已经在使用Spring,那么BeanWrapperImpl是一个非常好的实用程序,它可以使用您现有的ConversionService将您的输入转换为目标类型。否则我建议使用Commons BeanUtils,它可以做几乎相同的事情,但没有Springiness。两个库都知道如何处理嵌套属性和Map值的属性。

最新更新