廢話不多說,先上圖,如果是你想要的或者能有所學習就可以接著往下看了。

1、創(chuàng)建project
在idea中new project-->maven-->右側(cè)選中maven-archetype-webapp,然后一路next,新建的好的項目目錄如下

因此需要在main文件夾下新家java,test,testResources三個文件夾,后兩個用于測試,并不必需。新建后在file->Project Structure->Modiles頁面將新建的文件夾賦予相應的屬性,如將java文件夾mark as Sources,這樣才能被spring識別。至此,總體結(jié)構上便完整了。
2、資源文件配置
1、pom.xml依賴設置
簡單而言就是添加項目所需要的jar包,但是maven大大簡化了這個過程,只需要將依賴包名按標準加入,剩下的maven自動搞定,推薦一個查詢依賴包的網(wǎng)站,http://mvnrepository.com/,只要記得包名就能找到。在該項目下添加的依賴如下,直接copy放入
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>4.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jpa</artifactId>
<version>1.7.0.RELEASE</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.8</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<version>4.3.7.Final</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.3</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.12</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.7</version>
</dependency>
<dependency>
<groupId>org.freemarker</groupId>
<artifactId>freemarker</artifactId>
<version>2.3.21</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>org.testng</groupId>
<artifactId>testng</artifactId>
<version>6.11</version>
</dependency>
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.2</version>
</dependency>
<dependency>
<groupId>javax.persistence</groupId>
<artifactId>persistence-api</artifactId>
<version>1.0.2</version>
</dependency>
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>0.9.5-pre9</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.38</version>
</dependency>
</dependencies>
2、配置文件.xml設置
在文件夾下新建一個application.xml(名稱無要求),添加代碼如下,注解在代碼中
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:jpa="http://www.springframework.org/schema/data/jpa"
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/aop http://www.springframework.org/schema/aop/spring-aop-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/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd
http://www.springframework.org/schema/data/jpa http://www.springframework.org/schema/data/jpa/spring-jpa-1.8.xsd ">
<!--自動掃描(自動注入)-->
<context:component-scan base-package="com.zhang.Demo" />
<!--第一步,配置數(shù)據(jù)源-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="driverClass" value="com.mysql.jdbc.Driver"/>
<property name="jdbcUrl" value="jdbc:mysql:///demo"/><!--jdbc:mysqsl://localhost:3306/xxx-->
<property name="user" value="root"/>
<property name="password" value="wangzhang"/>
<!--連接池中保留的最大連接數(shù)。默認值: 15 -->
<property name="maxPoolSize" value="1000"/>
<!-- 連接池中保留的最小連接數(shù),默認為:3-->
<property name="minPoolSize" value="800"/>
<!-- 初始化連接池中的連接數(shù),取值應在minPoolSize與maxPoolSize之間,默認為3-->
<property name="initialPoolSize" value="500"/>
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="jpaVendorAdapter" ref="hibernateJpaVendorAdapter" />
<property name="packagesToScan" value="com.zhang.Demo.entity" />
<property name="jpaProperties">
<props>
<prop key="hibernate.ejb.naming_strategy">org.hibernate.cfg.ImprovedNamingStrategy</prop>
<prop key="hibernate.show_sql">true</prop>
<prop key="hibernate.hbm2ddl.auto">update</prop>
</props>
</property>
</bean>
<bean id="hibernateJpaVendorAdapter"
class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="databasePlatform" value="org.hibernate.dialect.MySQLDialect" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
<jpa:repositories base-package="com.zhang.Demo.repository"
entity-manager-factory-ref="entityManagerFactory"
transaction-manager-ref="transactionManager">
</jpa:repositories>
<tx:annotation-driven transaction-manager="transactionManager"
proxy-target-class="true" />
<mvc:default-servlet-handler/>
<mvc:annotation-driven/>
<mvc:resources mapping="/static/**" location="/WEB-INF/static/"/>
<mvc:resources location="/WEB-INF/js/" mapping="/js/**"/>
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver" id="internalResourceViewResolver">
<property name="prefix" value="/WEB-INF/page/"/>
<property name="suffix" value=".jsp"/>
</bean>
</beans>
3、web.xml配置
在web.xml中加入過濾器與服務器映射
<!DOCTYPE web-app PUBLIC
"-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd" >
<web-app>
<display-name>Archetype Created Web Application</display-name>
<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>
<servlet-name>Demo</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name> <!-- 指明數(shù)據(jù)庫等配置文件的位置 -->
<param-value>classpath:application.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>Demo</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
至此,項目已經(jīng)完成一小半了,所有的要用到的配置文件都已經(jīng)配置好了,剩下的只剩下代碼的編寫了。
3、后臺代碼的編寫
1、如目錄結(jié)構,在java下新建一個package,在該package下新建4個package以對應springMVC結(jié)構,分別為controller控制層,entity實體層,repository持久層(控制數(shù)據(jù)庫),service服務層。
<1>entity層
該層主要定義實體的字段,@Id定義主鍵,@GeneratedValue設置自增屬性,不必須,但一般有,@Table屬性為Jpa的自動建表,設置后會在數(shù)據(jù)庫中自動建立一個名為user的表(數(shù)據(jù)庫還是要自己建的),字段上也可以加各種屬性,諸如非空,長度等。
@Entity
@Table(name = "user")
public class User {
@Id
@GeneratedValue
private Integer id;
private String name;
private String job;
private String phone;
//以下加字段的set 與get方法,alt+insert鍵彈出快捷窗
}
<2>controller層
加@Controller以注明其為控制層,@RequestMapping注解表示其訪問路徑。該層主要負責控制,將前端來的訪問請求轉(zhuǎn)發(fā)到對應的處理service層。第一步,注入service層
private MyService myService;
@Autowired
public void setMyService(MyService myService) {
this.myService = myService;
}
這樣就可以直接調(diào)用seivice層接口,將處理過程交給service層,大幅縮減controller層代碼,邏輯更加簡明。自動注入之后編寫的增刪改查代碼如下
@RequestMapping(value="/addOne",method= RequestMethod.GET)
@ResponseBody
public User inSave(@ModelAttribute User user)
{
myService.save(user);
return user;
}
@RequestMapping(value="/findOne",method= RequestMethod.GET)
@ResponseBody
public JSONObject findOne(int id)
{
User user = myService.findOne(id);
JSONObject json = new JSONObject();
json.put("data",user);
return json;
}
@RequestMapping(value="/deleteById",method= RequestMethod.GET)
@ResponseBody
public void deleteById(int id)
{
myService.delete(id);
return ;
}
@RequestMapping(value="/modifyOne",method= RequestMethod.GET)
@ResponseBody
//WebRequest request, ModelMap model,@RequestBody User user
public JSONObject modifyOne(@ModelAttribute User user){
User user1=myService.saveAndFlush(user);
JSONObject json = new JSONObject();
json.put("data",user1);
return json;
}
看起來是不是很簡潔,因為它把所有的業(yè)務處理都交給service層了,由于Jpa的相當給力,你會發(fā)現(xiàn)service層也相當簡潔,如果你沒有自定義的一些方法。如果不結(jié)合datatable插件,那么查詢所有的信息的代碼也是很簡潔的
@RequestMapping(value="/findAll",method= RequestMethod.GET)
@ResponseBody
public JSONObject findAll()
{
List<User> userList = myService.findAll();
JSONObject json = new JSONObject();
json.put("data",userList);
return json;
}
補充一點,如果不加@ResponseBody注解,那么上圖返回的內(nèi)容為“json.jsp”或者其他網(wǎng)頁格式,而不是json格式的字段。
<3>service層
在該層下,一般建立一個service接口與一個serviceImpl實現(xiàn)類,以符合分層思想與層之間以接口鏈接。
public interface MyService {
User save(User user);
List<User> findAll();
User findById(int id);
List<User> findByName(String name);
User findOne(int id);
void delete(int id);
User saveAndFlush(User user);
}
接口的實現(xiàn)類
@Service
@Transactional //事務標記
public class MyServiceImpl implements MyService{
private MyRepository myRepository;
@Autowired
public void setMyRepository(MyRepository myRepository) {
this.myRepository = myRepository;
}
public User save(User user)
{
myRepository.save(user);
return user;
}
public List<User> findAll() {
List<User> all = myRepository.findAll();
return all;
}
public User findById(int id) {
User user = myRepository.findById(id);
return user;
}
public List<User> findByName(String name) {
List<User> names = myRepository.findByName(name);
return names;
}
public User findOne(int id) {
User user=myRepository.findOne(id);
return user;
}
public void delete(int id) {
myRepository.delete(id);
}
public User saveAndFlush(User user) {
User user1=myRepository.saveAndFlush(user);
return user1;
}
<4>reposiory層
也被稱為Dao層,主要負責對數(shù)據(jù)庫的操縱,當繼承了JpaRepository后,便含有findAll,save,delete等各種自帶方法,如果沒有也可以使用findByxxx復寫方法,程序會自動進行識別查找相應的列,當然也可以加@Query注解完全自寫數(shù)據(jù)庫語句。
import com.zhang.Demo.entity.User;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.List;
public interface MyRepository extends JpaRepository<User,Integer>{
User findById(int id);
List<User> findByName(String name);
}
至此,后臺的業(yè)務邏輯處理就基本完成了,源碼中還有其他的一些代碼,那個是處理前臺傳輸過來的dataTable封裝好的json格式數(shù)據(jù)的,想看完整的功能還是建議參照源碼一起看。注:每層的類都需要注明屬性,諸如實體層@Entity。
4、與datatable相關的部分前端與后臺處理
<1>前端datatable的固定定義代碼
<script>
$(document).ready( function () {
var table = $('#myTable').DataTable({
language: {
url: "scripts/zh_CN.txt"
},
info: true,
paging: true,
bServerSide: true, //是否啟動服務器端數(shù)據(jù)導入
sAjaxSource: "/demo/tableDemoAjax", //請求的地址
fnServerData: retrieveData, // 獲取數(shù)據(jù)的處理函數(shù)
autoWidth: false, //禁用自動調(diào)整列寬
stripeClasses: ["odd", "even"], //為奇偶行加上樣式,兼容不支持CSS偽類的場合
processing: true, //隱藏加載提示,自行處理
serverSide: true, //啟用服務器端分頁
searching: false, //禁用原生搜索
// orderMulti: true, //啟用多列排序
order: [], //取消默認排序查詢,否則復選框一列會出現(xiàn)小箭頭
renderer: "bootstrap", //渲染樣式:Bootstrap和jquery-ui
pagingType: "simple_numbers", //分頁樣式:simple,simple_numbers,full,full_numbers
columnDefs: [{
"targets": 'nosort', //列的樣式名
"orderable": false //包含上樣式名‘nosort’的禁止排序
}],
columns: [
{data: 'id'},
{data: 'name'},
{data: 'job'},
{data: 'phone'},
{data: function (obj) {
op = "<div id='toolbar' class='btn-group'>";
op1 = "<button id='btn_edit' type='button' class='btn btn-default' onclick='show_detail(" + obj.id + ");'><span class='glyphicon glyphicon-list' aria-hidden='true'></span>詳情</button>";
op2 = "<button id='btn_edit' type='button' class='btn btn-default' onclick='show_modify(" + obj.id + ");'><span class='glyphicon glyphicon-pencil' aria-hidden='true'></span>修改</button>";
op3 = "<button id='btn_edit' type='button' class='btn btn-default' onclick='show_delete(" + obj.id + ");'><span class='glyphicon glyphicon-remove' aria-hidden='true'></span>刪除</button>";
op_ = "</div>";
return op + op1 + op2 + op3 +op_;
}
}
]
});
function retrieveData(sSource, aoData, fnCallback) {
$.ajax({
url: sSource, //這個就是請求地址對應sAjaxSource
data: {"aoData": JSON.stringify(aoData)}, //這個是把datatable的一些基本數(shù)據(jù)傳給后臺,比如起始位置,每頁顯示的行數(shù) ,分頁,排序,查詢等的值
type: 'GET',
dataType: 'json',
async: false,
success: function (result) {
fnCallback(result); //把返回的數(shù)據(jù)傳給這個方法就可以了,datatable會自動綁定數(shù)據(jù)的
},
error: function (msg) {
}
});
}
});
</script>
sAjaxSource為訪問的路徑,retrieveData為數(shù)據(jù)傳輸定義,一定得是三個參數(shù),上圖的sSource就是sAjaxSource里得內(nèi)容,傳輸?shù)胶笈_的是一個json字符串,封裝的內(nèi)容有很多,包括分頁、排序等參數(shù),詳情可以自行百度。
<2>后臺處理
@RequestMapping(value="/tableDemoAjax",method= RequestMethod.GET)
@ResponseBody
public String tableDemoAjax(@RequestParam String aoData) {
DataTableParameter dataTableParam = myService.getDataTableParameterByJsonParam(aoData);
List<User> userList = myService.findAll();
int iDisplayEnd=dataTableParam.getiDisplayStart()+dataTableParam.getiDisplayLength();
if(userList.size()<iDisplayEnd)
iDisplayEnd=userList.size();
com.alibaba.fastjson.JSONObject getObj = new com.alibaba.fastjson.JSONObject();
getObj.put("sEcho", dataTableParam.getsEcho());// 記錄訪問的次數(shù)
getObj.put("iTotalRecords", userList.size());//實際的行數(shù)
getObj.put("iTotalDisplayRecords", userList.size());//顯示的行數(shù),這個要和上面寫的一樣
getObj.put("aaData", userList.subList(dataTableParam.getiDisplayStart(),iDisplayEnd));//要以JSON格式返回
return getObj.toString();
}
上述的getDataTableParameterByJsonParam(aoData)方法是自寫方法,定義在service層的接口,在實現(xiàn)類中實現(xiàn)方法,詳情自看源碼。
5、結(jié)語
一定要參照源碼看,這樣更容易理解。掛上去的源碼只要建個數(shù)據(jù)庫,庫名與配置文件中一致就可以直接運行了,向時筆者學習的時候基本上找不到直接能跑的,有的還有各種問題的,給學習增加了不少麻煩。源碼
文中如有錯誤或者更好的建議,請不吝賜教。不理解的也非常歡迎留言交流。