Hibernate忽略具有ManyToOne关系的属性上的设置值

时间:2014-01-31 09:51:54

标签: java spring hibernate spring-mvc many-to-one

我有一个Java Spring MVC控制器应用程序。它使用 hibernate 4和spring 3 。使用 Bitronix事务管理器

以下是我的一些模型类

User.java

    public class User  implements java.io.Serializable {

        private Integer userId;
        private String userName;
        private String emailId;
        private Set<Jobs> jobses = new HashSet<Jobs>(0);

        //getters and setters   

        @OneToMany(cascade=CascadeType.ALL, fetch=FetchType.LAZY, mappedBy="user")
        public Set<Jobs> getJobses() {
            return this.jobses;
        }

        public void setJobses(Set<Jobs> jobses) {
            this.jobses = jobses;
        }
    }

Jobs.java

@NamedQueries({
    @NamedQuery(
        name = "findJobsByUser",
        query = "from Jobs jobs where jobs.user = :user"
    )
})
@JsonIgnoreProperties("user")
@Entity
@Table(name="jobs"
    ,catalog="mydb"
)
public class Jobs  implements java.io.Serializable {

    private Integer jobId;
    private User user;
    private String jobName;
    private Set<Tasks> taskses = new HashSet<Tasks>(0);
    //getters & setters

    @XmlTransient
    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="UserId")
    public User getUser() {
        return this.user;
    }

    public void setUser(User user) {
        this.user = user;
    }

    @OneToMany(cascade=CascadeType.ALL, fetch=FetchType.EAGER, mappedBy="jobs")
    public Set<Tasks> getTaskses() {
        return this.taskses;
    }

    public void setTaskses(Set<Tasks> taskses) {
        this.taskses = taskses;
    }
}

Tasks.java

public class Tasks  implements java.io.Serializable {

    private Integer taskId;
    private Jobs jobs;
    private String taskName;
    private Set<Process> processes = new HashSet<Process>(0);

    //getters & setters

    @XmlTransient
    @ManyToOne(fetch=FetchType.LAZY, cascade=CascadeType.ALL)
    @JoinColumn(name="JobId")
    public Jobs getJobs() {
        return this.jobs;
    }

    public void setJobs(Jobs jobs) {
        this.jobs = jobs;
    }

    @OneToMany(cascade=CascadeType.ALL, fetch=FetchType.EAGER, mappedBy="tasks")
    public Set<Process> getProcesses() {
        return this.processes;
    }

    public void setProcesses(Set<Process> processes) {
        this.processes = processes;
    }
}

Process.java

public class Process  implements java.io.Serializable {

    private Integer processId;
    private Tasks tasks;
    private String processName;

    //getters and setters

    @XmlTransient
    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="TaskId")
    public Tasks getTasks() {
        return this.tasks;
    }

    public void setTasks(Tasks tasks) {
        this.tasks = tasks;
    }

}

在我的控制器中使用命名查询我试图获得所有工作。

JobsDetailsController.java控制器方法

@RequestMapping(value = "/jobsdeatils/{userId}", method = RequestMethod.GET)
@ResponseBody
public List<Jobs> jobsDetails(@PathVariable Integer userId) throws IOException {
    try {
        User user=userService.findById(userId);

        Map<String, Object> queryParams=new LinkedHashMap<String, Object>(); 

        queryParams.put("user", user);

        jobs=jobsService.findByNamedQuery("findJobsByUser", queryParams);

    } catch(Exception e) {
        logger.debug(e.getMessage());
    }
    return jobs;
}

我能够获取数据,但是大数据需要更多时间。转换为JSON时会出错。然后我发现它将进行无限循环并且StackOverflowException正在发生。我为所有不需要的模型类添加了JsonIgnoreProperties。但是当通过休眠检索时需要时间。

在乔布斯,有set<Tasks>。在任务中有JobsId它正在尝试再次设置作业对象并进行循环。同样有set<Process>,它映射到tasks并经历循环。最后,当我在Web浏览器中回复结果为JSON时,它会出错。

我想要的是,当我检索List<Jobs>时,我想要任务,然后在内部任务中,我不希望hibernate为jobs对象设置值。而且在Process我也不想为tasks对象设置。

我尝试在每个注释为@Transient的字段中添加@ManyToOne(javax.persistence)。

但是我收到以下错误

org.hibernate.AnnotationException: mappedBy reference an unknown target entity property

所有这些领域。

我该如何解决?

我想要的是

2 个答案:

答案 0 :(得分:0)

我认为你需要注册Hibernate Module支持。 为此,请创建自定义映射器。

Maven依赖

要在基于Maven的项目上使用模块,请使用以下依赖项:

<dependency>
  <groupId>com.fasterxml.jackson.datatype</groupId>
  <artifactId>jackson-datatype-hibernate4</artifactId>
  <version>2.2.3</version>
</dependency>    

然后是映射器

public class HibernateAwareObjectMapper extends ObjectMapper{

  public HibernateAwareObjectMapper(){
      registerModule(new Hibernate4Module());
  }
}

然后将其添加为要使用的对象映射器

<mvc:annotation-driven>
    <mvc:message-converters>
        <!-- Use the HibernateAware mapper instead of the default -->
        <bean class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
            <property name="objectMapper">
                <bean class="path.to.your.HibernateAwareObjectMapper" />
            </property>
        </bean>
    </mvc:message-converters>
</mvc:annotation-driven>

资源来自:https://github.com/FasterXML/jackson-datatype-hibernate

答案 1 :(得分:0)

  @XmlTransient
    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="TaskId")
    public Tasks getTasks() {
        return this.tasks;
    }

此映射不应与taskId对应。由于您在Tasks表中的属性名称具有taskId

的键,因此小T而不是大写