目前,我正在春季和冬眠的一个项目上工作。花更多的时间来获取记录并在JSP中显示这些记录。我将时间戳记无处不在,以了解花费更多时间的地方:
Time @ HomeController[start] : 2014-07-09 18:58:52.621
**Time @ userService[start] : 2014-07-09 18:58:52.622**
**Time @ UserDao[start] : 2014-07-09 18:58:57.678**
Time before executing Query : 2014-07-09 18:58:57.678
Time After executing Query : 2014-07-09 18:58:59.272
Time @ UserDao[end] : 2014-07-09 18:58:59.272
Time @ userService[End] : 2014-07-09 18:59:00.068
Time @ HomeController[end] : 2014-07-09 18:59:00.068
Time stamp in JSP :2014-07-09 18:59:00.129
通过以上分析,从服务层到DAO层大约需要5秒钟,我在下面给出了服务和DAO的代码:
UserService :
public class UserServiceImpl implements UserService {
@Override
public List<User> getUserpagination(int page) {
System.out.println("Time @ userService[start] : "+new Timestamp(new Date().getTime())); ----------- (1)
List<User> u = userDao.getUserpagination(page);
System.out.println("Time @ userService[End] : "+new Timestamp(new Date().getTime()));
return u;
}
}
UserDao :
public class UserDaoImpl implements UserDao {
@Override
@Transactional
public List<User> getUserpagination(int page) {
System.out.println("Time @ UserDao[start] : "+new Timestamp(new Date().getTime())); ------- (2)
return userlist;
}
因此,从第(1)行到第(2)行需要5秒钟。谁能解释为什么以及如何减少时间?
我正在从属性文件获取数据库连接:
jdbc.properties:
database.driver=oracle.jdbc.driver.OracleDriver
database.url=jdbc:oracle:thin:@xxx.xxx.xxx.xx:1521:osm
database.user=osm
database.password=xxxxxx
hibernate.dialect=org.hibernate.dialect.Oracle10gDialect
hibernate.show_sql=true
hibernate.hbm2ddl.auto=create/update
下面是XML文件中的配置:
<context:property-placeholder location="classpath:jdbc.properties" />
<tx:annotation-driven transaction-manager="hibernateTransactionManager" />
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="${database.driver}" />
<property name="url" value="${database.url}" />
<property name="username" value="${database.user}" />
<property name="password" value="${database.password}" />
</bean>
<bean id="sessionFactory"
class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="annotatedClasses">
<list>
<value>com.xxx</value>
</list>
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">${hibernate.dialect}</prop>
</props>
</property>
</bean>
<bean id="hibernateTransactionManager"
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
现在,我使用了HikariCP,并且出现了超时错误:
SEVERE: Servlet.service() for servlet [dispatcher] in context with path [/springhiber1] threw exception [Request processing failed; nested exception is org.springframework.transaction.CannotCreateTransactionException: Could not open Hibernate Session for transaction; nested exception is org.hibernate.exception.GenericJDBCException: Cannot open connection] with root cause
java.sql.SQLException: Timeout of 30000ms encountered waiting for connection.
at com.zaxxer.hikari.pool.HikariPool.getConnection(HikariPool.java:192)
at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:91)
at org.springframework.orm.hibernate3.LocalDataSourceConnectionProvider.getConnection(LocalDataSourceConnectionProvider.java:81)
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="${database.driver}" />
<property name="url" value="${database.url}" />
<property name="username" value="${database.user}" />
<property name="password" value="${database.password}" />
</bean>
在您的配置中,您正在使用DriverManagerDataSource
尽管这只是一个适当的数据源实现。它不是连接池。发生的情况是,每个连接都是按需创建的,需要关闭后,它将立即关闭。这是性能的杀手er。
如果要提高性能,请使用连接池。有很多实现
只需dataSource
使用适当的连接池替换bean定义。例如,如果您想用HikariCP替换它,则可以使用类似的方法。
<bean id="dataSource" class="com.zaxxer.hikari.HikariDataSource" destroy-method="shutdown">
<property name="dataSourceClassName" value="oracle.jdbc.pool.OracleDataSource" />
<property name="connectionTestQuery" value="SELECT 1 FROM DUAL" />
<property name="dataSource.user" value="${database.user}" />
<property name="dataSource.password" value="${database.password}" />
<property name="dataSource.url" value="${database.url}" />
</bean>
当然,您将不得不为池本身添加依赖项。
<dependency>
<groupId>com.zaxxer</groupId>
<artifactId>HikariCP</artifactId>
<version>1.4.0</version>
<scope>compile</scope>
</dependency>
有关可以设置哪些属性的信息,请参见HikariCP文档和Oracle Datasource文档。
另一件事是,您的代码库中散布着许多行来衡量性能,这确实不是最明智的事情,也不是非常有效。我建议使用一些AOP对代码进行性能评估,然后例如可以在生产中轻松将其删除。现在,您必须清理整个代码库。
Spring已经有一个PerformanceMonitorInterceptor
您可以使用和配置的。如果您想进行更精细的测量,可以使用JamonPerformanceMonitorInterceptor
。
<bean id="performanceInterceptor" class="org.springframework.aop.interceptor.PerformanceMonitorInterceptor"/>
<aop:config>
<aop:pointcut id="ourMethods" expression="execution(* com.your.base-package..*.*(..))"/>
<aop:advisor pointcut-ref="ourMethods" advice-ref="performanceInterceptor"/>
</aop:config>
现在,您可以轻松地测量和记录性能。保持代码整洁,您可以衡量所需的内容。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句