java - Tomcat HTTP 状态 500 - 无法初始化代理 - 无 session

标签 java json tomcat hibernate-annotations http-status-code-500

当我作为服务器运行我的应用程序时出现错误,我知道原因。这是我的错误:

HTTP Status 500 - could not initialize proxy - no Session (through reference chain: java.util.ArrayList[0]->it.jack.fdd.model.Staff["staffType"]->it.jack.fdd.model.StaffType_$$_jvstbaa_15["type"])


type Exception report

message could not initialize proxy - no Session (through reference chain: java.util.ArrayList[0]->it.jack.fdd.model.Staff["staffType"]->it.jack.fdd.model.StaffType_$$_jvstbaa_15["type"])

description The server encountered an internal error that prevented it from fulfilling this request.

exception
org.codehaus.jackson.map.JsonMappingException: could not initialize proxy - no Session (through reference chain: java.util.ArrayList[0]->it.jack.fdd.model.Staff["staffType"]->it.jack.fdd.model.StaffType_$$_jvstbaa_15["type"])
	org.codehaus.jackson.map.JsonMappingException.wrapWithPath(JsonMappingException.java:218)
	org.codehaus.jackson.map.JsonMappingException.wrapWithPath(JsonMappingException.java:183)
	org.codehaus.jackson.map.ser.std.SerializerBase.wrapAndThrow(SerializerBase.java:140)
	org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:158)
	org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:112)
	org.codehaus.jackson.map.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:446)
	org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:150)
	org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:112)
	org.codehaus.jackson.map.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:72)
	org.codehaus.jackson.map.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:23)
	org.codehaus.jackson.map.ser.std.AsArraySerializerBase.serialize(AsArraySerializerBase.java:86)
	org.codehaus.jackson.map.ser.StdSerializerProvider._serializeValue(StdSerializerProvider.java:659)
	org.codehaus.jackson.map.ser.StdSerializerProvider.serializeValue(StdSerializerProvider.java:271)
	org.codehaus.jackson.map.ObjectWriter.writeValue(ObjectWriter.java:325)
	org.codehaus.jackson.jaxrs.JacksonJsonProvider.writeTo(JacksonJsonProvider.java:556)
	com.sun.jersey.json.impl.provider.entity.JacksonProviderProxy.writeTo(JacksonProviderProxy.java:160)
	com.sun.jersey.spi.container.ContainerResponse.write(ContainerResponse.java:302)
	com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1510)
	com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1419)
	com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1409)
	com.sun.jersey.spi.container.servlet.WebComponent.service(WebComponent.java:409)
	com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:558)
	com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:733)
	javax.servlet.http.HttpServlet.service(HttpServlet.java:729)
	org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)


root cause
org.hibernate.LazyInitializationException: could not initialize proxy - no Session
	org.hibernate.proxy.AbstractLazyInitializer.initialize(AbstractLazyInitializer.java:165)
	org.hibernate.proxy.AbstractLazyInitializer.getImplementation(AbstractLazyInitializer.java:286)
	org.hibernate.proxy.pojo.javassist.JavassistLazyInitializer.invoke(JavassistLazyInitializer.java:185)
	it.jack.fdd.model.StaffType_$$_jvstbaa_15.getType(StaffType_$$_jvstbaa_15.java)
	sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	java.lang.reflect.Method.invoke(Method.java:497)
	org.codehaus.jackson.map.ser.BeanPropertyWriter.get(BeanPropertyWriter.java:483)
	org.codehaus.jackson.map.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:418)
	org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:150)
	org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:112)
	org.codehaus.jackson.map.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:446)
	org.codehaus.jackson.map.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:150)
	org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:112)
	org.codehaus.jackson.map.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:72)
	org.codehaus.jackson.map.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:23)
	org.codehaus.jackson.map.ser.std.AsArraySerializerBase.serialize(AsArraySerializerBase.java:86)
	org.codehaus.jackson.map.ser.StdSerializerProvider._serializeValue(StdSerializerProvider.java:659)
	org.codehaus.jackson.map.ser.StdSerializerProvider.serializeValue(StdSerializerProvider.java:271)
	org.codehaus.jackson.map.ObjectWriter.writeValue(ObjectWriter.java:325)
	org.codehaus.jackson.jaxrs.JacksonJsonProvider.writeTo(JacksonJsonProvider.java:556)
	com.sun.jersey.json.impl.provider.entity.JacksonProviderProxy.writeTo(JacksonProviderProxy.java:160)
	com.sun.jersey.spi.container.ContainerResponse.write(ContainerResponse.java:302)
	com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1510)
	com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1419)
	com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1409)
	com.sun.jersey.spi.container.servlet.WebComponent.service(WebComponent.java:409)
	com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:558)
	com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:733)
	javax.servlet.http.HttpServlet.service(HttpServlet.java:729)
	org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)

查看:java.util.ArrayList[0]->it.jack.fdd.model.Staff["staffType"]->it.jack.fdd.model.StaffType_$$_jvstbaa_15["输入"])

这是因为我有两个模型类,加入我数据库的两个表,这两个类是:

员工.java:

package it.jack.fdd.model;
// Generated 30-nov-2016 0.17.09 by Hibernate Tools 4.3.1.Final

import java.util.Date;
import java.util.HashSet;
import java.util.Set;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.xml.bind.annotation.XmlRootElement;

import org.codehaus.jackson.annotate.JsonIgnore;

/**
 * Staff generated by hbm2java
 */
@XmlRootElement
@Entity
@Table(name = "staff", catalog = "fdd_dbproducts")
public class Staff implements java.io.Serializable {

	private Integer idstaff;
	private StaffType staffType;
	private String name;
	private String surname;
	private Date birthDate;
	private String phone;
	private boolean gender;
	private StaffLogin staffLogin;
	private Set<RtStaffDispenser> rtStaffDispensers = new HashSet<RtStaffDispenser>(0);

	public Staff() {
	}

	public Staff(StaffType staffType, String name, String surname, Date birthDate, String phone, boolean gender) {
		this.staffType = staffType;
		this.name = name;
		this.surname = surname;
		this.birthDate = birthDate;
		this.phone = phone;
		this.gender = gender;
	}

	public Staff(StaffType staffType, String name, String surname, Date birthDate, String phone, boolean gender,
			StaffLogin staffLogin, Set<RtStaffDispenser> rtStaffDispensers) {
		this.staffType = staffType;
		this.name = name;
		this.surname = surname;
		this.birthDate = birthDate;
		this.phone = phone;
		this.gender = gender;
		this.staffLogin = staffLogin;
		this.rtStaffDispensers = rtStaffDispensers;
	}

	@Id
	@GeneratedValue(strategy = IDENTITY)

	@Column(name = "idstaff", unique = true, nullable = false)
	public Integer getIdstaff() {
		return this.idstaff;
	}

	public void setIdstaff(Integer idstaff) {
		this.idstaff = idstaff;
	}

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "fkstaff_type_staff", nullable = false)
	@JsonIgnore
	public StaffType getStaffType() {
		return this.staffType;
	}

	public void setStaffType(StaffType staffType) {
		this.staffType = staffType;
	}

	@Column(name = "name", nullable = false, length = 45)
	public String getName() {
		return this.name;
	}

	public void setName(String name) {
		this.name = name;
	}

	@Column(name = "surname", nullable = false, length = 45)
	public String getSurname() {
		return this.surname;
	}

	public void setSurname(String surname) {
		this.surname = surname;
	}

	@Temporal(TemporalType.DATE)
	@Column(name = "birth_date", nullable = false, length = 10)
	public Date getBirthDate() {
		return this.birthDate;
	}

	public void setBirthDate(Date birthDate) {
		this.birthDate = birthDate;
	}

	@Column(name = "phone", nullable = false, length = 45)
	public String getPhone() {
		return this.phone;
	}

	public void setPhone(String phone) {
		this.phone = phone;
	}

	@Column(name = "gender", nullable = false)
	public boolean isGender() {
		return this.gender;
	}

	public void setGender(boolean gender) {
		this.gender = gender;
	}

	@OneToOne(fetch = FetchType.LAZY, mappedBy = "staff")
	@JsonIgnore
	public StaffLogin getStaffLogin() {
		return this.staffLogin;
	}

	public void setStaffLogin(StaffLogin staffLogin) {
		this.staffLogin = staffLogin;
	}

	@OneToMany(fetch = FetchType.LAZY, mappedBy = "staff")
	@JsonIgnore
	public Set<RtStaffDispenser> getRtStaffDispensers() {
		return this.rtStaffDispensers;
	}

	public void setRtStaffDispensers(Set<RtStaffDispenser> rtStaffDispensers) {
		this.rtStaffDispensers = rtStaffDispensers;
	}

}

和 StaffType.java:

package it.jack.fdd.model;
// Generated 30-nov-2016 0.17.09 by Hibernate Tools 4.3.1.Final

import java.util.HashSet;
import java.util.Set;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;
import javax.xml.bind.annotation.XmlRootElement;

import org.codehaus.jackson.annotate.JsonIgnore;

/**
 * StaffType generated by hbm2java
 */
@XmlRootElement
@Entity
@Table(name = "staff_type", catalog = "fdd_dbproducts")
public class StaffType implements java.io.Serializable {

	private Integer idstaffType;
	private String type;
	private Set<Staff> staffs = new HashSet<Staff>(0);

	public StaffType() {
	}

	public StaffType(String type) {
		this.type = type;
	}

	public StaffType(String type, Set<Staff> staffs) {
		this.type = type;
		this.staffs = staffs;
	}

	@Id
	@GeneratedValue(strategy = IDENTITY)

	@Column(name = "idstaff_type", unique = true, nullable = false)
	public Integer getIdstaffType() {
		return this.idstaffType;
	}

	public void setIdstaffType(Integer idstaffType) {
		this.idstaffType = idstaffType;
	}

	@Column(name = "type", nullable = false, length = 45)
	public String getType() {
		return this.type;
	}

	public void setType(String type) {
		this.type = type;
	}

	@OneToMany(fetch = FetchType.LAZY, mappedBy = "staffType")
	@JsonIgnore
	public Set<Staff> getStaffs() {
		return this.staffs;
	}

	public void setStaffs(Set<Staff> staffs) {
		this.staffs = staffs;
	}

}

我出现此错误是因为我在 Staff 和 StaffType 之间存在多对一关系。 这是问题所在:

@OneToMany(fetch = FetchType.LAZY, mappedBy = "staffType")
@JsonIgnore
public Set<Staff> getStaffs() {
    return this.staffs;
}

事实上,使用@JsonIgnore 是可行的!现在我的问题是:如果没有@JsonIgnore,我该如何修复它?因为,如果我使用@JsonIgnore,我的结果 json 文件不包含外键:fkstaff_type_staff。我该如何解决? 谢谢。

ps: 这是我的BaseDaoImpl.java:

package it.jack.fdd.dao.impl;

import it.jack.fdd.dao.interfaces.BaseDao;
import it.jack.fdd.model.Product;
import it.jack.fdd.model.Staff;
import it.jack.fdd.model.User;
import it.jack.fdd.util.HibernateUtilLezione;

import java.io.Serializable;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

import org.hibernate.HibernateException;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;

public class BaseDaoImpl<T> implements BaseDao<T> {

	public BaseDaoImpl() {
		super();
	}

	/* (non-Javadoc)
	 * @see it.unisalento.se.dao.impl.BaseDao#save(T)
	 */
	public int save(T entity) {
	
		int id = 0;
		
		try {
			
			
			/*
			 *  DIFFERENZA TRA openSession() e getCurrentSession):
			 *  
			  	When you create a hibernate session using any of the sessionFactory.openSession(...)
			 	methods the session factory will 'bind' the session to the current context.
			  	The default context is 'thread' which means the sesion factory will bind the session
			  	to the thread from which openSession(...) is called. 

				This is useful because you can later call sessionFactory.getCurrentSession() which will
				return the session that is bound to the currently running thread. 

				You can use other predefined current_session_context_class values such as 'jta' which will
				bind the session to the currently running JTA transaction (if you're running in an
				application server that supports JTA this is really useful). Or you can write your
				own implementation of org.hibernate.context.CurrentSessionContext and use that implementation
				to manage the current session context (not really advisable unless you absolutely need to). 
			 * 
			 */
			
			
			//Prep work
			//SessionFactory sessionFactory = HibernateUtil.getSessionFactory();
			
			Session session = HibernateUtilLezione.openSession(); //dall'esempio mio fa getCurrentSession()
			Transaction tx = session.beginTransaction();
			
			id =  (Integer) session.save(entity);
			tx.commit();
			session.close();
		}catch(HibernateException e){
			e.printStackTrace();
		}
		return id;
	}

	/* (non-Javadoc)
	 * @see it.unisalento.se.dao.impl.BaseDao#getAll(java.lang.Class)
	 */
	public List<T> getAll(Class clazz) {
		
		Session session = HibernateUtilLezione.openSession();
		Transaction tx = session.beginTransaction();
		
		@SuppressWarnings("unchecked")
		List<T> list = session.createQuery("from "+clazz.getName()).list();
		tx.commit();
		session.close();
				
		return list; 
	}

	/* (non-Javadoc)
	 * @see it.unisalento.se.dao.impl.BaseDao#getById(int, java.lang.Class)
	 */
	public T getById(int id, Class clazz) {
		try{
		
			Session session = HibernateUtilLezione.openSession();
			Transaction tx = session.beginTransaction();
			
			@SuppressWarnings("unchecked")
			T returnObj = (T) session.get(clazz.getName(), id);
			/*
			System.out.println("vediamo "+session.getIdentifier(returnObj));
			System.out.println("vediamo2 "+session.getEntityName(returnObj));
			*/
			tx.commit();
			session.close();
			
			return returnObj;
		}
		catch(HibernateException e){
			e.printStackTrace();
			return null;
		}
		
	}
	
	/* (non-Javadoc)
	 * @see it.unisalento.se.dao.impl.BaseDao#delete(int, java.lang.Class)
	 */
	public void delete (int id, Class clazz){
		
		Session session = HibernateUtilLezione.openSession();
		Transaction tx = session.beginTransaction();
		
		T t = (T) session.get(clazz, id);
		session.delete(t);
		tx.commit();
		session.close();
		
	}


/*
	public Serializable getByUID(Staff stf) {
		// TODO Auto-generated method stub
		return null;
	}
	*/

	public void update(T entity) {
		try {
			Session session = HibernateUtilLezione.openSession();
			Transaction tx = session.beginTransaction();
					
			session.update(entity);
			tx.commit();
			session.close();
		}
		catch(HibernateException e){
			e.printStackTrace();
		}
		
	}
	
}

最佳答案

序列化在 JPA session 关闭后发生。 Jackson 尝试访问惰性字段,但由于 session 已关闭,它引发了异常。

要么你:

  • 通过在 JPA session 关闭之前访问它来完全加载该字段,或者
  • 声明字段 eager (fetch = FetchType.EAGER)

关于java - Tomcat HTTP 状态 500 - 无法初始化代理 - 无 session ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40895454/

相关文章:

java - 通过netbeans在tomcat服务器上部署应用

java - MongoDB : How to make findAndModify returns the Last Updated Record

java - Tomcat 似乎无法释放线程

json - Angular Response.json() 未记录

JavaScript 解析嵌套 JSON 数组

mysql - 在 docker 中为 mySQL 创建数据库和模式

负载下的 Spring MVC IndexOutOfBounds

java - Spring MVC 为什么我的模型中的数据没有显示在 output.jsp 中?

java - 多个 eclipse 配置文件

javascript - 如何在 Javascript 中从 JSON 数组对象读取数据