先看代码:
package connFlex.impl;import java.util.List;import org.hibernate.Hibernate;
import org.hibernate.SQLQuery;
import org.hibernate.Session;
import org.springframework.orm.hibernate3.HibernateCallback;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;import connFlex.QuerySuperManagerDao;
import pojo.SuperManager;public class QuerySuperManager extends HibernateDaoSupport implements QuerySuperManagerDao { ///验证登陆
public List FindSuperManager(final String username) throws Exception{
//System.out.println("xxxxx");
List<SuperManager> list=null;
System.out.println(getHibernateTemplate());
//如果要进行增删改的动作,那么要开启事务
return (List)getHibernateTemplate().execute(new HibernateCallback(){
public Object doInHibernate(Session session){
SQLQuery q = session.createSQLQuery("select {sm.*} from supermanager sm where sm.userName='"+username+"'");
q.addEntity("sm", SuperManager.class);
List list1=q.list();
return list1;
}
});
// SuperManager[] superManager = new SuperManager[list.size()];
// for(int i=0;i<list.size();i++){
// superManager[i] = (SuperManager)list.get(i);
// }
}
public List FindSumSuperManager() throws Exception{
//System.out.println("xxxxx");
List<SuperManager> list=null;
//如果要进行增删改的动作,那么要开启事务
return (List)getHibernateTemplate().execute(new HibernateCallback(){
public Object doInHibernate(Session session){
SQLQuery q = session.createSQLQuery("select sum(sm.id),sm.username from supermanager sm group by sm.username");
q.addScalar("sum(sm.id)",Hibernate.INTEGER);
q.addScalar("sm.username",Hibernate.STRING);
List list1=q.list();
return list1;
}
});
// SuperManager[] superManager = new SuperManager[list.size()];
// for(int i=0;i<list.size();i++){
// superManager[i] = (SuperManager)list.get(i);
// }
}}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//处理post方式乱码
request.setCharacterEncoding("utf-8");
//设置浏览器输出字符编码
response.setCharacterEncoding("utf-8");
// PrintWriter writer=response.getWriter();
//获取flex传递的参数 username password
try{
String username = java.net.URLDecoder.decode(request.getParameter("username"), "UTF-8");
// String username = request.getParameter("username");
System.out.println(username);
PrintWriter out=response.getWriter();
//构建一个list存放一些数据用来模拟用户是否存在这一功能
String xmlContent = "<?xml version='1.0' encoding='utf-8'?><SuperManagers>";
ServletContext servletContext = request.getSession().getServletContext();
ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
QuerySuperManager l=(QuerySuperManager)ctx.getBean("superManager"); System.out.println(l.getHibernateTemplate());
List list=l.FindSuperManager(username);
if(list.size()>0){
SuperManager superManager=(SuperManager)list.get(0);
System.out.println(superManager.getId()+" "+superManager.getUserName()+" "+superManager.getPassword());
}
//response.sendRedirect("/fei/index.jsp");
if(list.size()>0){
for(int i=0;i<list.size();i++){
System.out.println("运行了");
SuperManager superManager=(SuperManager)list.get(i);
xmlContent +="<SuperManager><id>"+superManager.getId()+"</id><userName>"
+superManager.getUserName()+"</userName><password>"+superManager.getPassword()+"</password></SuperManager>";
//检验用户
}
xmlContent +="</SuperManagers>";}else{
xmlContent="ok";
}
if(list.size()==0)
out.print(xmlContent);
else
out.println(xmlContent);
out.flush();
out.close();
}catch(Exception e){
e.printStackTrace();
}
}
问题这样的为什么在servlet里面红色字部分那调用的hibernatetemplate为空
而当运行到FindSuperManager()方法的时候里面输出的hibernatetemplat又存在了 为什么
package connFlex.impl;import java.util.List;import org.hibernate.Hibernate;
import org.hibernate.SQLQuery;
import org.hibernate.Session;
import org.springframework.orm.hibernate3.HibernateCallback;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;import connFlex.QuerySuperManagerDao;
import pojo.SuperManager;public class QuerySuperManager extends HibernateDaoSupport implements QuerySuperManagerDao { ///验证登陆
public List FindSuperManager(final String username) throws Exception{
//System.out.println("xxxxx");
List<SuperManager> list=null;
System.out.println(getHibernateTemplate());
//如果要进行增删改的动作,那么要开启事务
return (List)getHibernateTemplate().execute(new HibernateCallback(){
public Object doInHibernate(Session session){
SQLQuery q = session.createSQLQuery("select {sm.*} from supermanager sm where sm.userName='"+username+"'");
q.addEntity("sm", SuperManager.class);
List list1=q.list();
return list1;
}
});
// SuperManager[] superManager = new SuperManager[list.size()];
// for(int i=0;i<list.size();i++){
// superManager[i] = (SuperManager)list.get(i);
// }
}
public List FindSumSuperManager() throws Exception{
//System.out.println("xxxxx");
List<SuperManager> list=null;
//如果要进行增删改的动作,那么要开启事务
return (List)getHibernateTemplate().execute(new HibernateCallback(){
public Object doInHibernate(Session session){
SQLQuery q = session.createSQLQuery("select sum(sm.id),sm.username from supermanager sm group by sm.username");
q.addScalar("sum(sm.id)",Hibernate.INTEGER);
q.addScalar("sm.username",Hibernate.STRING);
List list1=q.list();
return list1;
}
});
// SuperManager[] superManager = new SuperManager[list.size()];
// for(int i=0;i<list.size();i++){
// superManager[i] = (SuperManager)list.get(i);
// }
}}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//处理post方式乱码
request.setCharacterEncoding("utf-8");
//设置浏览器输出字符编码
response.setCharacterEncoding("utf-8");
// PrintWriter writer=response.getWriter();
//获取flex传递的参数 username password
try{
String username = java.net.URLDecoder.decode(request.getParameter("username"), "UTF-8");
// String username = request.getParameter("username");
System.out.println(username);
PrintWriter out=response.getWriter();
//构建一个list存放一些数据用来模拟用户是否存在这一功能
String xmlContent = "<?xml version='1.0' encoding='utf-8'?><SuperManagers>";
ServletContext servletContext = request.getSession().getServletContext();
ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
QuerySuperManager l=(QuerySuperManager)ctx.getBean("superManager"); System.out.println(l.getHibernateTemplate());
List list=l.FindSuperManager(username);
if(list.size()>0){
SuperManager superManager=(SuperManager)list.get(0);
System.out.println(superManager.getId()+" "+superManager.getUserName()+" "+superManager.getPassword());
}
//response.sendRedirect("/fei/index.jsp");
if(list.size()>0){
for(int i=0;i<list.size();i++){
System.out.println("运行了");
SuperManager superManager=(SuperManager)list.get(i);
xmlContent +="<SuperManager><id>"+superManager.getId()+"</id><userName>"
+superManager.getUserName()+"</userName><password>"+superManager.getPassword()+"</password></SuperManager>";
//检验用户
}
xmlContent +="</SuperManagers>";}else{
xmlContent="ok";
}
if(list.size()==0)
out.print(xmlContent);
else
out.println(xmlContent);
out.flush();
out.close();
}catch(Exception e){
e.printStackTrace();
}
}
问题这样的为什么在servlet里面红色字部分那调用的hibernatetemplate为空
而当运行到FindSuperManager()方法的时候里面输出的hibernatetemplat又存在了 为什么
public List FindSuperManager(final String username) throws Exception{
//System.out.println("xxxxx");和 ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
QuerySuperManager l=(QuerySuperManager)ctx.getBean("superManager"); System.out.println(l.getHibernateTemplate());
List list=l.FindSuperManager(username);
你这2是两种不同的QuerySuperManager 获取方式
是直接冲spring的上下文中获取bean
QuerySuperManager l=(QuerySuperManager)ctx.getBean("superManager");而
public class QuerySuperManager extends HibernateDaoSupport implements QuerySuperManagerDao {
是没有spring上下文的去官网上下个 mybatis与spring集成的jar下来
然后
public class UserDaoImpl extends SqlSessionDaoSupport implements UserDao {
public User getUser(String userId) {
return (User) getSqlSession()
.selectOne("org.mybatis.spring.sample.mapper.UserMapper.getUser", userId);
}
}
参照里面的配置说明
<bean id="userMapper" class="org.mybatis.spring.sample.mapper.UserMapperImpl">
<property name="sqlSessionFactory" ref="sqlSessionFactory" />
</bean>
参考文档
里面的东西在web项目加载时候spring会通过自己的加载方式把spring的配置信息给设置进去。
就是spring已经把信息设置到里面去了。
然后你通过QuerySuperManager l=(QuerySuperManager)ctx.getBean("superManager");
获取bean。
但是你继承daosupport时候,spring没有帮你把bean注入到你的dao里面去,所以你要把你需要的东西注入进去
如sessionfactory简单说就是:WebApplicationContextUtils 系统加载自动配置。
你要使用你自己的dao需要你自己注入
<bean id="superManager" class="connFlex.impl.QuerySuperManager">
- <property name="sessionFactory">
<ref bean="mySessionFactory" />
</property>
</bean>
可以看到我是已经把sessionfactory注入进去了正因为这个注入方法里面调用HibernateTemplate才被实例化了不然也一样为空
这个与一般的bean dao还是有区别的集中不同的实现方法:
1.
把你的QuerySuperManager 设置成静态的。但是set方法 把static 去掉。 (不推荐)2.
使用你的方法
ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
这个方式就是获取上下文,不是在servlet中注入了。servlet 与普通的bean不一样,生命周期不是由spring管理的,所以spring无法注入,这个就是根本原因所以你的通过2方法可以获取
QuerySuperManager ,但是在servlet中无法通过注入QuerySuperManager
如果像你这样说servlet中无法注入 就是无法实例化? 获取的QuerySuperManager 这个不是实例化了?还有
ClassPathResource resource = new ClassPathResource("applicationContext.xml");
BeanFactory factory = new XmlBeanFactory(resource);
QuerySuperManager l=(QuerySuperManager)factory.getBean("superManager");
获取的QuerySuperManager这个实例l却是可以
也就是System.out.println(l.getHibernateTemplate()); 输出来的是存在的并没有出现空
我觉得这就是两者不同
但是为什么通过WEB初始化的就不行呢
为什么创建的实例调用hibernatetemplate时不可以注入sessionfactory呢?
这个的实现是spring读取配置文件后设置到这个工具类中。
区别就是一个是你自己读取配置文件,一个是spring自己读取配置文件。
你这里写了2行代码,spirng写了一行代码
加载sping的配置文档种类很多,spring不只是能使用在web项目,但是不是web项目。就可以通过你这中方式加载。你看看spring的官方文档把
如果像你这样说servlet中无法注入 就是无法实例化?
servlet 这个类 你没有自己 new 出来吧,就是这个意思,是由tomcat等等容器创建的,
而不是像自己new的 User u = new User();
就是一个层次问题:
所有的QuerySuperManager 都要注入 sessionfactory但是我们分层之后悔吧QuerySuperManager 注入到action 等等 其他调用入口,如果是struts 那么 我们在action 中会把 QuerySuperManager 注入到action中
public class DemoAction extends BaseAction {
private QuerySuperManager querySuperManager ; //在action中可以注入,要引
//入spring与struts的jar,再写上set 方法,这样是可以在action中获取得到的,
//而不不用再去读取配置文件ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApp
如果是servlet中
package com.wsd.servlet;import java.io.IOException;import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;import org.springframework.beans.factory.BeanFactory;
import org.springframework.context.support.ClassPathXmlApplicationContext;import com.wsd.service.TestService;
import com.wsd.vo.User;/**
* Servlet implementation class TestServlet
*/
public class TestServlet extends HttpServlet {
private static final long serialVersionUID = 1L; //private QuerySuperManager querySuperManager ;//这个是无法通过正常的注入的,你可以设置为静态的变量,获取通过
//ApplicationContext ctx = WebApplicationContextUtils.getRequiredWebApp ,等等加载配置文件来获取
//就像我下面的 获取TestService cm = (TestService) factory.getBean("testService"); 一样
private static BeanFactory factory = new ClassPathXmlApplicationContext(
"applicationContext-*.xml"); /**
* Default constructor.
*/
public TestServlet() {
// TODO Auto-generated constructor stub
} /**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse
* response)
*/
protected void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
this.doPost(request, response);
} /**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse
* response)
*/
protected void doPost(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException { TestService cm = (TestService) factory.getBean("testService");
for (int i = 0; i < 1; i++) {
User u = new User();
u.setId(i + "");
u.setName("name" + i);
u.setPass("pass" + i);
try {
cm.addUser(u);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// cm.addUser2(u);
try {
cm.doUser(u);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// cm.doUser2(u);
} }}
所以我们一般是把项目代码层次分清楚;action --service ---dao(你的就是QuerySuperManager )所以在 mapper的都要把 sessionfactory注入进去,不用管 action,service层次。但是你在servlet中获取的应该是 service层,但是servlet中是无法通过注入把service注入进去的(正常情况下),就是servlet中,不能使用正常的像QuerySuperManager 注入sessionfactory一样注入属性,需要变换方式
明白了吧
你的意思是说其实sessionfactory其实在web初始化的时候并没有注入到QuerySuperManager这个里面,而是等调用QuerySuperManager个里面的FindSuperManager方法才能注入进去???
如果你的配置文件里面有:
<bean id="superManager" class="connFlex.impl.QuerySuperManager">
<property name="sessionFactory">
<ref bean="mySessionFactory" />
</property>
</bean>说明你已经注入了,如果获取不到 看看其他细节地方是否配置错误了
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-2.0.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-2.0.xsd"> <!-- 配置数据源 -->
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName">
<value>com.mysql.jdbc.Driver</value>
</property>
<property name="url">
<value>jdbc:mysql://localhost:3306/jike?useUnicode=true&characterEncoding=utf8&autoReconnect=true&autoReconnectForPools=true</value>
</property>
<property name="username">
<value>root</value>
</property>
<property name="password">
<value></value>
</property>
</bean> <!-- 配置SessionFactory -->
<bean id="mySessionFactory"
class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">
<property name="mappingResources">
<list>
<value>pojo/SuperManager.hbm.xml</value>
</list>
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">
org.hibernate.dialect.MySQLDialect
</prop>
<prop key="hibernate.show_sql">true</prop>
<prop key="current_session_context_class">thread</prop>
<prop key="hibernate.cache.provider_class">
org.hibernate.cache.EhCacheProvider
</prop>
<prop key="hibernate.hbm2ddl.auto">update</prop>
<!-- 最大连接数 -->
<prop key="hibernate.c3p0.max_size">200</prop>
<!-- 最小连接数 -->
<prop key="hibernate.c3p0.min_size">10</prop>
<!-- 获得连接的超时时间,如果超过这个时间,会抛出异常,单位毫秒 -->
<prop key="hibernate.c3p0.timeout">120</prop>
<!-- 最大的PreparedStatement的数量 -->
<prop key="hibernate.c3p0.max_statements">0</prop>
<!-- 每隔120秒检查连接池里的空闲连接 ,单位是秒-->
<prop key="hibernate.c3p0.idle_test_period">120</prop>
<!-- 当连接池里面的连接用完的时候,C3P0一下获取的新的连接数 -->
<prop key="hibernate.c3p0.acquire_increment">2</prop>
<!-- 每次都验证连接是否可用 -->
<prop key="hibernate.c3p0.validate">true</prop>
</props>
</property>
<property name="dataSource">
<ref bean="dataSource"/>
</property>
</bean> <!-- 配置TransactionManager -->
<bean id="myTxManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="mySessionFactory" />
</bean> <!-- 配置事务策略 -->
<tx:advice id="txAdvice" transaction-manager="myTxManager">
<tx:attributes>
<tx:method name="*" propagation="REQUIRED" read-only="true" />
</tx:attributes>
</tx:advice> <aop:config proxy-target-class="true">
<aop:pointcut id="productServiceMethods" expression="execution(* connFlex.impl.*.*(..))" />
<aop:advisor advice-ref="txAdvice" pointcut-ref="productServiceMethods" />
</aop:config> <bean id="superManager"
class="connFlex.impl.QuerySuperManager">
<property name="sessionFactory"><ref bean="mySessionFactory"/></property>
</bean>
</beans>
我就是这样配置的没看出错在哪?