2012-03-24 9 views
0

ich mit Frühling arbeite 3, Hibernate 3.0.6 und JPA 2.Frühling 3 JPA: LazyInitializationException trotz @Transactional Service-Methode

ich LazyInitializationException bin immer:

Hier ist der Service: @Service Die öffentliche Klasse ReportServiceImpl implementiert ReportService { private ReportDAO reportDAO; private FieldDefDAO fieldDefDAO; private FieldDefService fieldDefService;

/** 
    * 
    */ 
    @Override 
    @Transactional(propagation = Propagation.REQUIRED) 
    public void updateReport(ReportTemplate reportTemplate, String[] fieldIds) { 
     logger.entry(reportTemplate); 

     try { 
      ReportTemplate existingReport = reportDAO.findById(
        reportTemplate.getId(), true); 

      existingReport.setName(reportTemplate.getName()); 
      existingReport.setDepartment(reportTemplate.getDepartment()); 

      // set selected fields 
      if (fieldIds != null) { 
       existingReport.removeReportFields(); 

       for (String fieldId : fieldIds) { 

        FieldDef fd = fieldDefDAO.findById(Long.parseLong(fieldId), false); 

        // EXCEPTION THROWN HERE (
        reportTemplate.addReportField(fd, i); 
       } 
      } 
      reportDAO.mergeState(existingReport, false); 
     } catch (FocusDAOException fde) { 
      throw new FocusServiceException(fde); 
     } 
     logger.exit(); 
    } 
} 

Die Entitäten:

@Entity 
@Table(name = "REPORT_TEMPLATE") 
@SQLDelete(sql = "UPDATE REPORT_TEMPLATE SET deleted = 1 WHERE REPORTTEMPLATE_ID = ? and OPTLOCK = ?") 
@Where(clause = "deleted <> 1") 
public class ReportTemplate extends Template { 

    private Long id; 
    private Set<ReportField> reportFields = new HashSet<ReportField>(); 

    /** 
    * @return the id 
    */ 
    @Id 
    @GeneratedValue(strategy = GenerationType.AUTO) 
    @Column(name = "REPORTTEMPLATE_ID") 
    public Long getId() { 
     return id; 
    } 

    /** 
    * @param id 
    *   the id to set 
    */ 
    public void setId(Long id) { 
     this.id = id; 
    } 

    /** 
    * @return the reportFields 
    */ 
    @OneToMany(mappedBy = "reportTemplate", cascade = { CascadeType.PERSIST, 
      CascadeType.MERGE }) 
    public Set<ReportField> getReportFields() { 
     return reportFields; 
    } 

    /** 
    * @param reportFields 
    *   the reportFields to set 
    */ 
    public void setReportFields(Set<ReportField> reportFields) { 
     this.reportFields = reportFields; 
    } 

    /** 
    * 
    * @param field 
    */ 
    @Transient 
    public void addReportField(FieldDef field, int order) { 
     ReportField rf = new ReportField(this, field, order); 

     reportFields.add(rf); 
     field.getReportFields().add(rf);   
    } 

    /** 
    * 
    */ 
    public void removeReportFields() { 
     for (ReportField rf : reportFields) { 
      rf.setReportTemplate(null); 
      reportFields.remove(rf); 
     } 
    } 

} 

@Entity 
@Table(name = "REPORT_FIELD", uniqueConstraints = @UniqueConstraint(columnNames = { 
    "REPORTFIELD_ID", "FIELDDEF_ID", "DISPLAY_ORDER" })) 
public class ReportField { 

private Long id; 

// @OrderColumn 
private FieldDef field; 
private ReportTemplate reportTemplate; 
private int order; 

/** 
* 
*/ 
public ReportField() {} 

/** 
* 
* @param reportTemplate 
* @param field 
* @param order 
*/ 
public ReportField(ReportTemplate reportTemplate, FieldDef field, int order) { 
    this.reportTemplate = reportTemplate; 
    this.field = field; 
    this.order = order; 
} 

/** 
* @return the id 
*/ 
@Id 
@GeneratedValue(strategy = GenerationType.AUTO) 
@Column(name = "REPORTFIELD_ID") 
public Long getId() { 
    return id; 
} 

/** 
* @param id 
*   the id to set 
*/ 
public void setId(Long id) { 
    this.id = id; 
} 

/** 
* @return the field 
*/ 
@ManyToOne 
@JoinColumn(name = "FIELDDEF_ID", nullable = false) 
public FieldDef getField() { 
    return field; 
} 

/** 
* @param field 
*   the field to set 
*/ 
public void setField(FieldDef field) { 
    this.field = field; 
} 

/** 
* @return the report 
*/ 
@ManyToOne 
@JoinColumn(name = "REPORTTEMPLATE_ID", nullable = false) 
public ReportTemplate getReportTemplate() { 
    return reportTemplate; 
} 

/** 
* @param report 
*   the report to set 
*/ 
public void setReportTemplate(ReportTemplate reportTemplate) { 
    this.reportTemplate = reportTemplate; 
} 

/** 
* @return the order 
*/ 
@Column(name = "DISPLAY_ORDER", nullable = false) 
public int getOrder() { 
    return order; 
} 

/** 
* @param order 
*   the order to set 
*/ 
public void setOrder(int order) { 
    this.order = order; 
} 

}

Konfiguration:

 <security:global-method-security 
      pre-post-annotations="enabled" /> 

     <mvc:resources mapping="/resources/**" location="/resources/" /> 

     <bean id="jspViewResolver" 
      class="org.springframework.web.servlet.view.InternalResourceViewResolver"> 
      <property name="viewClass" 
       value="org.springframework.web.servlet.view.JstlView" /> 
      <property name="prefix" value="/WEB-INF/jsp/" /> 
      <!-- <property name="suffix" value=".jsp" /> --> 
     </bean> 

     <bean id="tilesViewResolver" 
      class="org.springframework.web.servlet.view.UrlBasedViewResolver"> 
      <property name="viewClass"> 
       <value> 
        org.springframework.web.servlet.view.tiles2.TilesView 
      </value> 
      </property> 
      <property name="order" value="1" /> 
     </bean> 

     <bean id="tilesConfigurer" 
      class="org.springframework.web.servlet.view.tiles2.TilesConfigurer"> 
      <property name="definitions"> 
       <list> 
        <value>/WEB-INF/tiles/tiles.xml</value> 
       </list> 
      </property> 
     </bean> 

     <bean id="projectDS" class="org.apache.tomcat.jdbc.pool.DataSource" 
      destroy-method="close" 
      p:driverClassName="${driver.class.name}" 
      p:url="${url}" 
      p:initialSize="${initial.size}" 
      p:maxActive="${max.active}" 
      p:maxIdle="${max.idle}" 
      p:minIdle="${min.idle}" 
      p:testOnBorrow="true" 
      p:validationQuery="SELECT 1" 
      p:validationInterval="30000" 
      p:timeBetweenEvictionRunsMillis="30000" 
      p:removeAbandoned="true" 
      p:removeAbandonedTimeout="60" 
      p:logAbandoned="true" 
      p:abandonWhenPercentageFull="75" 
      p:jdbcInterceptors="ConnectionState;StatementFinalizer;ResetAbandonedTimer;SlowQueryReport(threshold=3000)" 
     /> 

     <bean id="projectEMF" 
      class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"> 
      <property name="dataSource" ref="projectDS" /> 
      <property name="jpaVendorAdapter" ref="jpaVendorAdapter" /> 
     </bean> 

     <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"> 
      <property name="entityManagerFactory" ref="projectEMF" /> 
      <property name="dataSource" ref="projectDS" /> 
     </bean> 

     <bean id="jpaVendorAdapter" 
      class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter"> 

      <property name="database" value="SQL_SERVER" /> 
      <property name="showSql" value="false" /> 
      <property name="generateDdl" value="false" /> 
      <property name="databasePlatform" value="org.hibernate.dialect.SQLServerDialect" /> 
     </bean> 

     <bean id="validator" 
      class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" /> 

     <bean id="auditLog" class="ca.utoronto.med.dc.focus.persistence.audit.AuditLog" /> 

     <bean 
      class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" /> 

    <!-- focus: Edit the package name below. --> 
     <bean id="logoutHandlerBean" 
      class="ca.utoronto.med.dc.focus.security.LogoutSuccessHandlerImpl" /> 

     <bean id="customAuthenticationFailureHandlerBean" 
      class="ca.utoronto.med.dc.focus.security.AuthenticationFailureHandlerImpl" /> 

     <bean id="customAuthenticationSuccessHandlerBean" 
      class="ca.utoronto.med.dc.focus.security.AuthenticationSuccessHandlerImpl" /> 

     <bean id="httpSessionEventListener" 
      class="ca.utoronto.med.dc.focus.security.SimpleHttpSessionEventListenerImpl" /> 

     <mvc:annotation-driven /> 
     <task:annotation-driven /> 
     <tx:annotation-driven transaction-manager="transactionManager"/> 

     <context:component-scan base-package="ca.utoronto.med.dc.*" /> 

    <!-- Uncomment the following section to enable Aspects --> 
    <!-- <aop:aspectj-autoproxy /> 
     <bean id="authorizationMgr" class="ca.utoronto.med.dc.focus.aspect.AuthorizationMgr" /> 
    --> 

     <context:annotation-config 
      transaction-manager="transactionManager" proxy-target-class="false" /> 

     <util:properties id="projectProperties" location="/WEB-INF/focus.properties" /> 

     <!--Bean to load properties file --> 
     <bean id="placeholderConfig" 
      class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer"> 
      <property name="location" value="/WEB-INF/focus.properties" /> 
     </bean> 

     <!-- mail --> 
    <!-- <bean id="mailSender" class="org.springframework.mail.javamail.JavaMailSenderImpl">   
      <property name="host" value="${mailserver.host}" /> 
      <property name="port" value="${mailserver.port}" /> 
      <property name="username" value="${mailserver.username}" /> 
      <property name="password" value="${mailserver.password}" /> 
     </bean> --> 

     <!-- Configure the multipart resolver --> 
     <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"> 

      <!-- one of the properties available; the maximum file size in bytes --> 
      <property name="maxUploadSize" value="1000000"/> 

     </bean> 

    </beans> 

Antwort

Verwandte Themen