服务中的@Transactional(SpringMVC + Hibernate) - 找不到当前线程错误的会话

时间:2018-04-10 07:32:51

标签: java hibernate spring-mvc transactional

我有ApplicationContextConfig类:

@Configuration
@ComponentScan("com.appname")
@EnableTransactionManagement
@EnableWebMvc
@EnableAsync
public class ApplicationContextConfig extends WebMvcConfigurerAdapter {

private static final Logger logger = LogManager.getLogger(Thread.currentThread().getClass().getName());

private static String dbPassKey = null, dbPass = null, dbUserKey = null, dbUser = null, dbNameKey = null, dbName = null, 
        dbServer = null, printHql = null;
static {
    logger.debug("First Step : Loading properties files : start");
    Properties prop = new Properties();
    try {
        if(Utils.getEnvironment().equals(Constants.DEVELOPMENT_ENV)) {
            InputStream input = new FileInputStream(Constants.DEV_DATABASE_CONSTANTS_FILE);
            prop.load(input);
        } else if (Utils.getEnvironment().equals(Constants.TEST_ENV)) {
            InputStream input = new FileInputStream(Constants.TEST_DATABASE_CONSTANTS_FILE);
            prop.load(input);
        } else {
            InputStream input = new FileInputStream(Constants.PROD_DATABASE_CONSTANTS_FILE);
            prop.load(input);
        }
        dbPassKey = prop.getProperty("PROPERTY1");
        dbPass = prop.getProperty("PROPERTY2");
        dbUserKey = prop.getProperty("PROPERTY3");
        dbUser = prop.getProperty("PROPERTY4");
        dbNameKey = prop.getProperty("PROPERTY5");
        dbName = prop.getProperty("PROPERTY6");
        dbServer = prop.getProperty("PROPERTY7");
        printHql = prop.getProperty("PROPERTY8");
        logger.debug("First Step : Loading properties files : end");
    } catch (Exception e) {
        e.printStackTrace();
        logger.error(e.getMessage(), e);
    }
}

@Bean(name = "viewResolver")
public InternalResourceViewResolver getViewResolver() {
    InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
    viewResolver.setPrefix("/WEB-INF/views/");
    viewResolver.setSuffix(".jsp");
    return viewResolver;
}

@Override
public void addResourceHandlers(final ResourceHandlerRegistry registry) {
    registry.addResourceHandler("/assets/**").addResourceLocations("/assets").setCachePeriod(31556926);
}

@Override
public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
    configurer.enable();
}

@Bean(name="multipartResolver")
public MultipartResolver getMultipartResolver() {
    CommonsMultipartResolver mpResolver = new CommonsMultipartResolver();
    return mpResolver;
}

@Bean(name = "dataSource")
public DataSource getDataSource() {
    BasicDataSource dataSource = new BasicDataSource();
    dataSource.setDriverClassName("com.mysql.jdbc.Driver");
    String dbUrl = null;
    try {
        System.out.println(getDbNameKey() + " -----------;;---------- " + getDbName()); 
        dbUrl = "jdbc:mysql://"+getDbServer()+":3306/"+GeneratePlainPassword.decrypt(getDbNameKey(), getDbName());
        dataSource.setUrl(dbUrl);

        dataSource.setUsername(GeneratePlainPassword.decrypt(getDbUserKey(), getDbUser()));
        dataSource.setPassword(GeneratePlainPassword.decrypt(getDbPassKey(), getDbPass()));
    }catch(Exception ex) {
        logger.error(ex.getMessage(), ex);
    }
    logger.debug("Settings2 : " + dbUrl);
    return dataSource;
}


private Properties getHibernateProperties() {
    Properties properties = new Properties();
    properties.put("hibernate.show_sql", getPrintHql());
    properties.put("hibernate.dialect", "org.hibernate.dialect.MySQLDialect");
    return properties;
}

@Autowired
@Bean(name = "sessionFactory")
public SessionFactory getSessionFactory(DataSource dataSource) {
    LocalSessionFactoryBuilder sessionBuilder = new LocalSessionFactoryBuilder(dataSource);
    sessionBuilder.addProperties(getHibernateProperties());
    sessionBuilder.scanPackages("com.appname.model");
    return sessionBuilder.buildSessionFactory();
}

@Autowired
@Bean(name = "transactionManager")
public HibernateTransactionManager getTransactionManager(SessionFactory sessionFactory) {
    HibernateTransactionManager transactionManager = new HibernateTransactionManager(sessionFactory);
    return transactionManager;
}



@Autowired
@Bean(name = "processSpectrumService")
public ProcessSpectrumService getProcessSpectrumService() {
    return new ProcessSpectrumServiceImpl();
}

@Autowired
@Bean(name = "analyserDao")
public AnalyserDAO getAnalyserDAO(SessionFactory sessionFactory) {
    return new AnalyserDAOImpl(sessionFactory);
}


public static String getDbPassKey() {
    return dbPassKey;
}

public static String getDbPass() {
    return dbPass;
}

public static String getDbUserKey() {
    return dbUserKey;
}

public static String getDbUser() {
    return dbUser;
}

public static String getDbNameKey() {
    return dbNameKey;
}

public static String getDbName() {
    return dbName;
}

public static String getDbServer() {
    return dbServer;
}

public static String getPrintHql() {
    return printHql;
}


}

这是我的服务类:

@Service("processSpectrumService")
public class ProcessSpectrumServiceImpl implements 
ProcessSpectrumService {

@Autowired
private AnalyserDAO analyserDao;

@Override
public String processSpectrumDataFile(List<Date> dates, List<DataFile> dataFiles, BatchCompound batchCompound) {
    String status = null;
     try {
          logger.debug("Call Matlab code1");

          List<BatchCompoundCoanalyte> batchCompoundCoanalytes = analyserDao.getCoanalytesForBatchCompound(batchCompound.getBatchCompoundId());
          HashMap<Integer, Code3Output> output = octaveCode2(dataFiles, batchCompound, batchCompoundCoanalytes);

         if(output != null && !output.isEmpty()) {
              status = saveResultsToDB(batchCompound, output);
         }

     }catch(Exception e) {
         e.printStackTrace();
         batchCompound.setError(e.getMessage());
         batchCompound = analyserDao.saveBatchCompoundToDatabase(batchCompound);
         status = Constants.PROCESS_STATUS.PROCESS_FAILED;
    }

    return status;
}

@Transactional("transactionManager")
public String saveResultsToDB( BatchCompound batchCompound, HashMap<Integer, Code3Output> outputs) {
String status = null;
try{
  for(int loopCount = 0; loopCount < outputs.size(); loopCount++) {
     Result result = new Result();  //
     //process the datas and get result

     result = analyserDao.saveResultToDatabase(result);
     status = Constants.PROCESS_STATUS.PROCESS_SUCCESS;
  }
}catch(Exception ex){
 batchCompound.setError(Constants.FILE_STATUS.ERROR_IN_PROCESSING);
            batchCompound.setError(ex.getMessage());
            batchCompound = analyserDao.saveBatchCompoundToDatabase(batchCompound);
            ex.printStackTrace();
            status = Constants.PROCESS_STATUS.PROCESS_FAILED;
}
return status;
}

在AnalyserDAOImpl中,我有方法:

public class AnalyserDAOImpl implements AnalyserDAO {


@Autowired
private SessionFactory sessionFactory;

public AnalyserDAOImpl() {
}

public AnalyserDAOImpl(SessionFactory sessionFactory) {
    this.sessionFactory = sessionFactory;
}

@Override
@Transactional("transactionManager")
public BatchCompound saveBatchCompoundToDatabase(BatchCompound batchCompound) {
    sessionFactory.getCurrentSession().saveOrUpdate(batchCompound);
    return batchCompound;
}

@Override
public Result saveResultToDatabase(Result result) {
    sessionFactory.getCurrentSession().saveOrUpdate(result);
    return result;

}



}

代码在AnalyserDAOImpl处返回错误:

org.hibernate.HibernateException: No Session found for current thread
    at 


  org.springframework.orm.hibernate4.SpringSessionContext.currentSession(SpringSessionContext.java:106)
    at org.hibernate.internal.SessionFactoryImpl.getCurrentSession(SessionFactoryImpl.java:1014)
    at com.appname.dao.AnalyserDAOImpl.saveResultToDatabase(AnalyserDAOImpl.java:309)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:201)
    at com.sun.proxy.$Proxy57.saveResultToDatabase(Unknown Source)
    at com.appname.service.ProcessSpectrumServiceImpl.saveResultsToDB(ProcessSpectrumServiceImpl.java:119)
    at com.appname.service.ProcessSpectrumServiceImpl.processSpectrumDataFile(ProcessSpectrumServiceImpl.java:65)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:201)
    at com.sun.proxy.$Proxy64.processSpectrumDataFile(Unknown Source)
    at com.appname.service.AnalyserServiceImpl.processDataFiles(AnalyserServiceImpl.java:413)
    at com.appname.service.AnalyserServiceImpl.automateProcess(AnalyserServiceImpl.java:352)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:190)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:157)
    at org.springframework.aop.interceptor.AsyncExecutionInterceptor$1.call(AsyncExecutionInterceptor.java:97)
    at java.util.concurrent.FutureTask.run(FutureTask.java:266)
    at java.lang.Thread.run(Thread.java:748)

当@Transactional移动到AnalyserDAOImpl中的方法时,它可以正常工作,但结果将一个接一个地保存,直到发生错误。我希望只有在整个结果中没有错误时才能保存所有结果。

0 个答案:

没有答案