今天搭建了一個ssh+dwr框架,其實ssh框架配置和以前差不多,主要是使用了註解實現C和M層,下面就是web.xml配置
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
id="WebApp_ID" version="2.5">
<display-name>nwr-web</display-name>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:applicationContext*.xml</param-value>
</context-param>
<context-param>
<param-name>log4jConfigLocation</param-name>
<param-value>/WEB-INF/classes/log4j.properties</param-value>
</context-param>
<context-param>
<param-name>log4jRefreshInterval</param-name>
<param-value>60000</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<listener>
<listener-class>org.springframework.web.util.Log4jConfigListener</listener-class>
</listener>
<filter>
<filter-name>struts-prepare</filter-name>
<filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareFilter</filter-class>
<init-param>
<param-name>actionPackages</param-name>
<param-value>com.essential.action</param-value>
</init-param>
</filter>
<filter>
<filter-name>struts-execute</filter-name>
<filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsExecuteFilter</filter-class>
</filter>
<servlet>
<servlet-name>dwr</servlet-name>
<servlet-class>org.directwebremoting.spring.DwrSpringServlet</servlet-class>
<init-param>
<param-name>debug</param-name>
<param-value>true</param-value>
</init-param>
</servlet>
<filter-mapping>
<filter-name>struts-prepare</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>struts-execute</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter>
<filter-name>characterEncodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>characterEncodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<servlet-mapping>
<servlet-name>dwr</servlet-name>
<url-pattern>/dwr/*</url-pattern>
</servlet-mapping>
<welcome-file-list>
<welcome-file>News.jsp</welcome-file>
</welcome-file-list>
<error-page>
<error-code>500</error-code>
<location>/error.jsp</location>
</error-page>
<error-page>
<error-code>402</error-code>
<location>/error.jsp</location>
</error-page>
</web-app>
唯一需要說明一下的就是如果要使用struts2的註解就必須在配置filter的時候帶上actionPackages的參數,這個參數就是設置struts2容器搜索action的包路徑。
下面是struts.xml的配置文件:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.1.7//EN"
"http://struts.apache.org/dtds/struts-2.1.7.dtd">
<struts>
<package name="default" extends="struts-default">
<global-results>
<result name="error">error.jsp</result>
<result name="input">error.jsp</result>
</global-results>
</package>
<constant name="struts.convention.default.parent.package"
value="default" />
</struts>
我是用的struts.convention插件把所有action的父包都定義爲我自定義的一個default包,大家也可以自定義其它父包,這樣定義的父包是所有action的默認父包,當然你也可以使用@package標籤爲action類定義不同的包。
下面介紹spring的配置文件:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:dwr = "http://www.directwebremoting.org/schema/spring-dwr"
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-3.0.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
http://www.directwebremoting.org/schema/spring-dwr
http://www.directwebremoting.org/schema/spring-dwr-3.0.xsd"
>
<dwr:annotation-scan scanRemoteProxy="true" base-package="com.essential.dwr"/>
<dwr:annotation-scan scanDataTransferObject="true" base-package="com.essential.entity"/>
<context:component-scan base-package="com.essential" />
<bean id="configurer" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
<property name="locations">
<value>classpath*:init.properties</value>
</property>
</bean>
<bean id="mainDataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close">
<property name="driverClass" value="${jdbc.driverClass}"></property>
<property name="jdbcUrl" value="${jdbc.jdbcUrl}"></property>
<property name="user" value="${jdbc.user}"></property>
<property name="password" value="${jdbc.password}"></property>
<property name="maxPoolSize" value="${jdbc.maxPoolSize}"></property>
<property name="minPoolSize" value="${jdbc.minPoolSize}"></property>
<property name="initialPoolSize" value="${jdbc.initialPoolSize}"></property>
<property name="idleConnectionTestPeriod" value="${jdbc.idleConnectionTestPeriod}"></property>
<property name="maxIdleTime" value="${jdbc.maxIdleTime}"></property>
<property name="acquireIncrement" value="${jdbc.acquireIncrement}"/>
</bean>
<bean id="dataSource"
class="org.springframework.jdbc.datasource.LazyConnectionDataSourceProxy">
<property name="targetDataSource">
<ref local="mainDataSource" />
</property>
</bean>
<bean id="sessionFactory"
class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource">
<ref bean="dataSource" />
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">${hibernate.dialect}</prop>
<prop key="hibernate.show_sql">${hibernate.show_sql}</prop>
<prop key="hibernate.format_sql">${hibernate.format_sql}</prop>
<prop key="hibernate.use_sql_comments">${hibernate.use_sql_comments}</prop>
<prop key="hibernate.jdbc.batch_size">${hibernate.jdbc.batch_size}</prop>
</props>
</property>
<property name="packagesToScan" value="${hibernate.packagesToScan}" />
</bean>
<bean id="transactionManager"
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory">
<ref local="sessionFactory" />
</property>
</bean>
<tx:advice id="txAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="upd*" propagation="REQUIRED" read-only="false" />
<tx:method name="del*" propagation="REQUIRED" read-only="false" />
<tx:method name="add*" propagation="REQUIRED" read-only="false" />
<tx:method name="insert*" propagation="REQUIRED" read-only="false" />
<tx:method name="find*" propagation="SUPPORTS" read-only="true" />
<tx:method name="query*" propagation="SUPPORTS" read-only="true" />
<tx:method name="*" propagation="SUPPORTS" read-only="true" />
</tx:attributes>
</tx:advice>
<aop:config>
<aop:pointcut id="productServiceMethods"
expression="${spring.execution}" />
<aop:advisor advice-ref="txAdvice" pointcut-ref="productServiceMethods" />
</aop:config>
</beans>
首先前兩行配置是dwr和spring整合的配置第一個是配置dwr的遠程代理對象的所在的包名,第二個則是dwr裏的傳輸對象所在的包名。
下面一行是spring搜索bean的包名。下面其他的配置和以前沒什麼變化。
現在來講講struts2的action用註解怎麼實現:
1.其實註解和xml配置步驟差不多首先肯定是配置包,但是我們前面用struts.convention配置了默認包,所以也不用再配置,然後肯定是配置訪問的虛擬路勁咯,也就是配置namespace,使用@Namespace(value = "/mail")標籤配置,value屬性是配置namespace的路徑。
2.配置好了namespace然後就是action咯,配置這個是使用@Action(value = "sendMail", results = { @Result(name = SUCCESS, type = "redirect", location = "../News.jsp") })標籤,其中value是配置action的路徑,results是配置action的處理結果跳轉頁面,也可以配置多個頁面。
這樣就配置好了一個完整的action咯,我們現在要和spring整合就必須調用spring的bean,要調用bean很簡單定義一個私有變量,然後在變量上使用@resource標籤就行了,但是需要注意的是這裏的變量名必須和後面要講到的@service標籤中的名字要一致才行,不然注入不進來。
下面附上一個例子:
public class ActivityAction extends BaseAction {
/**
*
*/
private static final long serialVersionUID = 5488332603981342055L;
private long uid;
private long eventId;
private ActivityService activityService;
/**
* 查詢活動列表
*
* @return
* @throws Exception
*/
@Action(value = "findActivityList")
public String findActivityList() throws Exception {
List<ActivityVo> activityVos = activityService.findActivityList();
String result = ListToJsonString(activityVos);
toWrite(result);
return null;
}
/**
* 參加活動
*
* @return
* @throws Exception
*/
@Action(value = "joinActivity")
public String joinActivity() throws Exception {
boolean isSucc = activityService.insertActivityForUser(eventId, uid);
toWrite(isSucc + "");
return null;
}
/**
* 根據用戶標識查找活動列表
*
* @return 我的活動列表
* @throws Exception
*/
@Action(value = "findMyActivityList")
public String findMyActivityList() throws Exception {
List<ActivityVo> activityVos = activityService.findMyActivityList(uid);
String result = ListToJsonString(activityVos);
toWrite(result);
return null;
}
@Resource
public void setActivityService(ActivityService activityService) {
this.activityService = activityService;
}
public void setUid(long uid) {
this.uid = uid;
}
public void setEventId(long eventId) {
this.eventId = eventId;
}
}
然後來講講service的配置,配置方法是使用@service(value="serviceName")標籤設置service,很簡單不用多講,而且調用dao的時候和action調用service一樣使用@resource標籤引入屬性就行了,下面是例子源碼:
@Service(value = "activityService")
public class ActivityServiceImpl implements ActivityService {
@Resource
ActivityDao activityDao;
private DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
@Override
public boolean insertActivityForUser(long eventId, long uid) {
return activityDao.insertActivityForUser(eventId, uid);
}
@Override
public List<ActivityVo> findActivityList() {
List<Activity> list = activityDao.findActivityList();
List<ActivityVo> activityVos = new ArrayList<ActivityVo>();
for (Activity activity : list) {
ActivityVo activityVo = new ActivityVo();
activityVo.setId(activity.getId());
activityVo.setTitle(activity.getTitle());
activityVo.setPublishTime(df.format(activity.getPublishTime()));
activityVo.setImagurl(activity.getImagurl());
activityVo.setContent(activity.getContent());
activityVos.add(activityVo);
}
return activityVos;
}
@Override
public List<ActivityVo> findMyActivityList(long uid) {
List<Activity> list = activityDao.findMyActivityList(uid);
List<ActivityVo> activityVos = new ArrayList<ActivityVo>();
for (Activity activity : list) {
ActivityVo activityVo = new ActivityVo();
activityVo.setId(activity.getId());
activityVo.setTitle(activity.getTitle());
activityVo.setPublishTime(df.format(activity.getPublishTime()));
activityVo.setImagurl(activity.getImagurl());
activityVo.setDatetime(activity.getDatetime());
activityVo.setDescription(activity.getDescription());
activityVo.setContent(activity.getContent());
activityVos.add(activityVo);
}
return activityVos;
}
}
然後就是dao的配置和前面的差不多就是定義dao的時候是用@repository標籤,直接貼代碼就行了:
@Repository(value = "activityDao")
public class ActivityDao extends BaseDao<Activity> {
/**
* 參加活動
*
* @param eventId
* 活動ID
* @param uid
* 用戶ID
* @return 成功返回true,失敗返回false
*/
@SuppressWarnings("unchecked")
public boolean insertActivityForUser(long eventId, long uid) {
Session session = getSession();
Query query = session
.createSQLQuery("select au.aid from activity_users au where au.aid=:aid and au.uid=:uid");
List list = query.setParameter("uid", uid).setParameter("aid", eventId)
.list();
if (list.size() > 0) {
return false;
} else {
session.createSQLQuery(
"insert into activity_users(aid,uid) values(:aid,:uid)")
.setParameter("uid", uid).setParameter("aid", eventId)
.executeUpdate();
return true;
}
}
/**
* 查詢活動列表
*
* @return 活動列表
*/
@SuppressWarnings("unchecked")
public List<Activity> findActivityList() {
Session session = getSession();
List<Activity> list = session.createQuery(
"from Activity where status = 2 order by publishTime desc")
.setMaxResults(10).list();
return list;
}
/**
* 根據用戶標識查詢用戶參加的所有活動
*
* @param uid
* 用戶標識
* @return 活動列表
*/
@SuppressWarnings("unchecked")
public List<Activity> findMyActivityList(final long uid) {
return getHibernateTemplate().execute(new HibernateCallback() {
@Override
public Object doInHibernate(Session session)
throws HibernateException, SQLException {
List<Activity> list = session
.createQuery(
"select a from Activity a left join a.users u where u.id=:uid order by a.publishTime desc")
.setParameter("uid", uid).list();
return list;
}
});
}
}
下面是BaseDao的代碼:
public class BaseDao<E> extends HibernateDaoSupport {
@Resource(name = "sessionFactory")
public void setInjectionSessionFacotry(SessionFactory sessionFacotry) {
super.setSessionFactory(sessionFacotry);
}
@PostConstruct
public void injectSessionFactory() {
logger.info(super.getSessionFactory());
}
public Serializable save(E entity) {
return getHibernateTemplate().save(entity);
}
public void update(E entity) {
getHibernateTemplate().update(entity);
}
public void delete(E entity) {
getHibernateTemplate().delete(entity);
}
public User query(long id) {
return getHibernateTemplate().get(User.class, id);
}
}
在這個類裏面注入sessionFactory對象。
下面來講講dwr的配置,要配置dwr的遠程代理對象在類上使用@RemoteProxy類中的方法@RemoteMethod這樣在javascript中直接用類名+方法名直接調用就行了。如果要調用spring的bean和上面一樣,就不不多說。如果dwr和jsp頁面傳輸的時候需要用到java實體那麼就在需要傳輸的實體類上用@DataTransferObject標籤,才能正確轉換類型,不然會報異常。下面是例子:
@RemoteProxy
public class TestDwr implements Serializable {
/**
*
*/
private static final long serialVersionUID = -2060851629180328131L;
@RemoteMethod
public String testDwr() {
return "測試.";
}
}
實體的例子大家可以隨便定義一個類就行了加上標籤就OK,這裏就不列出來了。
下面是jsp使用dwr必須引入3個jsp:
<script type="text/javascript" src="<%=path %>/dwr/engine.js"></script>
<script type="text/javascript" src="<%=path %>/dwr/util.js"></script>
<script type="text/javascript" src="<%=path %>/dwr/interface/TestDwr .js"></script>
前面2個是dwr必須要使用的2個js包,後面一個就是你在java中定義的類.這樣就可以調用裏面的方法了。
到這裏全部講完了,有什麼不足的地方還請各位多補充。
所有jar包已經上傳,需要的可以去下載http://download.csdn.net/detail/yaoyeyzq/4516689