Springboot學習筆記(三)Springboot+Thymleaf資料互動
阿新 • • 發佈:2020-11-02
本篇是在上一篇“SpringBoot快速整合MyBatis+MySQL”的基礎上,檢視層通過整合Thymeleaf,資料持久層通過整合MyBatis從而完成資料的增刪改查。
Thymeleaf是什麼
簡單說, Thymeleaf 是一個跟 Velocity、FreeMarker 類似的模板引擎,它可以完全替代 JSP 。
它的優點:
- 開箱即用,它提供標準和spring標準兩種方言,可以直接套用模板實現JSTL、 OGNL表示式效果,避免每天套模板、改jstl、改標籤的困擾。同時開發人員也可以擴充套件和建立自定義的方言;
- Thymeleaf 提供spring標準方言和一個與 SpringMVC 完美整合的可選模組,可以快速的實現表單繫結、屬性編輯器、國際化等功能。
使用之前需在pom.xml中先引入依賴
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-thymeleaf</artifactId> </dependency>
還需要在springboot專案的application.properties做如下配置
#Thymeleaf配置 spring.thymeleaf.cache=false spring.thymeleaf.encoding=utf-8 spring.thymeleaf.mode=HTML5 spring.thymeleaf.prefix=classpath:/templates/ spring.thymeleaf.suffix=.html
以下就是我的專案目錄:
接下來就是我做的簡單的增刪改查:
//封裝的頭部header.html <!DOCTYPE html> <html xmlns:th="http://www.thymeleaf.org" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <div data-th-fragment="header"> <a href="/users">首頁</a> </div> </body> </html>
//首頁index.html <!DOCTYPE html> <html xmlns:th="http://www.thymeleaf.org" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout"> <head> <meta charset="utf-8"> <title th:text="${userModel.title}"></title> </head> <body> <div th:replace="~{fragments/header :: header}">...</div> <div th:text="${userModel.title}"></div> <div> <a href="/users/form">新增使用者</a> </div> <table border="1"> <thead> <tr> <td>ID</td> <td>名字</td> <td>電話</td> <td>性別</td> </tr> </thead> <tbody> <tr th:if="${userModel.userList.size()} eq 0"> <td colspan="3">沒有使用者資訊!</td> </tr> <tr th:each="user : ${userModel.userList}"> <td th:text="${user.userId}"></td> <td th:text="${user.userName}"></td> <td th:text="${user.phone}"></td> <td th:text="${user.sex}"></td> </tr> </tbody> </table> </body> </html>
//新增使用者add.html <!DOCTYPE html> <html xmlns:th="http://www.thymeleaf.org" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout"> <head> <meta charset="UTF-8"> <title th:text="${userModel.title}"></title> </head> <body> <div th:replace="~{fragments/header :: header}">...</div> <div th:text="${userModel.title}"></div> <form action="/users/add" method="post" th:object="${userModel.user}"> <input type="hidden" name="userId" th:value="*{userId}"> 名字: <input type="text" name="userName" th:value="*{userName}"> 電話: <input type="text" name="phone" th:value="*{phone}"> 性別: <input type="text" name="sex" th:value="*{sex}"> <br> <input type="submit" value="提交"> </form> </body> </html>
controller層
package com.example.springboot.controller; import com.example.springboot.pojo.UserInfo; import com.example.springboot.service.ExportService; import com.example.springboot.util.Log4j2Util; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import org.springframework.web.servlet.ModelAndView; import java.util.List; @RestController @RequestMapping("/users") public class UserInfoController { @Autowired private ExportService userservice; /** *獲取使用者列表 * @author qqg * @date * @param * @param model * @return */ private List<UserInfo> getUserList(){ List<UserInfo> lists = userservice.getUserList(); Log4j2Util.logger.info("查詢到的使用者資訊:\n"+lists); return lists; } @GetMapping public ModelAndView userList(Model model){ model.addAttribute("userList",getUserList()); model.addAttribute("title","使用者管理"); return new ModelAndView("index","userModel",model); } /** *建立表單 * @author qqg * @date * @param * @param model * @return */ @GetMapping("/form") public ModelAndView createForm(Model model){ model.addAttribute("user",new UserInfo()); model.addAttribute("title","新增使用者"); return new ModelAndView("add","userModel",model); } /** *功能描述 新增使用者 * @author qqg * @date * @param * @param user * @return */ @PostMapping("/add") public ModelAndView addUser(UserInfo user){ int result = userservice.saveUserInfo(user); Log4j2Util.logger.info("新增結果:\n"+result); return new ModelAndView("redirect:/users"); } }
服務層service
package com.example.springboot.service; import com.example.springboot.pojo.UserInfo; import java.util.List; public interface ExportService { List<UserInfo> getUserList(); Integer saveUserInfo(UserInfo user); } //服務實現impl package com.example.springboot.service.impl; import com.example.springboot.dao.UserInfoMapper; import com.example.springboot.pojo.UserInfo; import com.example.springboot.service.ExportService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import java.util.List; @Service public class ExportServiceImpl implements ExportService{ @Autowired private UserInfoMapper userinfomapper; @Override public List<UserInfo> getUserList() { List<UserInfo> lists = userinfomapper.getAllUserInfo(); return lists; } @Override public Integer saveUserInfo(UserInfo user) { return userinfomapper.saveUserInfo(user); } }
資料持久層dao
package com.example.springboot.dao; import com.example.springboot.pojo.UserInfo; import java.util.List; @Mapper public interface UserInfoMapper { List<UserInfo> getAllUserInfo(); Integer saveUserInfo(UserInfo user); }
UserInfoMapper.xml
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" > <mapper namespace="com.example.springboot.dao.UserInfoMapper" > <resultMap id="BaseResultMap" type="UserInfo" > <id column="USER_ID" property="userId" jdbcType="INTEGER" /> <result column="USER_NAME" property="userName" jdbcType="VARCHAR" /> <result column="PHONE" property="phone" jdbcType="VARCHAR" /> <result column="SEX" property="sex" jdbcType="VARCHAR" /> </resultMap> <sql id="Base_Column_List" > USER_ID, USER_NAME, PHONE, SEX </sql> <!--查詢所有使用者資訊--> <select id="getAll" resultMap="BaseResultMap" parameterType="String" > select <include refid="Base_Column_List" /> from user_info limit (#{page} - 1)* #{limit} ,#{limit} </select> <insert id="saveUserInfo" parameterType="UserInfo"> INSERT INTO user_info(USER_ID,USER_NAME,PHONE,SEX) VALUES (#{userId},#{userName},#{phone},#{sex}) </insert> <select id="findByphone" resultMap="BaseResultMap" parameterType="String" > select * from user_info where PHONE = #{phone} </select> <select id="getAllUserInfo" resultMap="BaseResultMap"> select * from user_info </select> </mapper>
實體類pojo
package com.example.springboot.pojo; public class UserInfo { private Integer userId; private String userName; private String phone; private String sex; public Integer getUserId() { return userId; } public void setUserId(Integer userId) { this.userId = userId; } public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } public String getPhone() { return phone; } public void setPhone(String phone) { this.phone = phone; } public String getSex() { return sex; } public void setSex(String sex) { this.sex = sex; } public UserInfo() { } public UserInfo(Integer userId, String userName, String phone, String sex) { this.userId = userId; this.userName = userName; this.phone = phone; this.sex = sex; } @Override public String toString() { return "UserInfo{" + "userId=" + userId + ", userName='" + userName + '\'' + ", phone='" + phone + '\'' + ", sex='" + sex + '\'' + '}'; } }
啟動類SpringbootApplication
package com.example.springboot; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration; import org.springframework.transaction.annotation.EnableTransactionManagement; @SpringBootApplication @EnableTransactionManagement public class SpringbootApplication { public static void main(String[] args) { SpringApplication.run(SpringbootApplication.class, args); System.out.println("啟動成功"); } }
此時,執行springboot專案,結果如下:
除了上面這些基本的操作之外,springboot專案還要做些配置,程式才能夠正常執行起來,
package com.example.springboot.config; import org.apache.ibatis.type.TypeAliasRegistry; import org.mybatis.spring.SqlSessionFactoryBean; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import javax.annotation.Resource; import javax.sql.DataSource; import java.io.IOException; /** *配置與連線池的會話 * @author Lrd * @date 2018/10/30 * @param * @param null * @return */ @Configuration public class MyBatisConfig { @Resource private DataSource dataSource; @Bean(name = "sqlSessionFactory") public SqlSessionFactoryBean sqlSessionFactoryBean(ApplicationContext applicationContext)throws IOException{ SqlSessionFactoryBean sqlSessionFactory = new SqlSessionFactoryBean(); sqlSessionFactory.setDataSource(dataSource); sqlSessionFactory.setMapperLocations(applicationContext.getResources("classpath*:mapping/*.xml")); sqlSessionFactory.setTypeAliasesPackage("com.example.springboot.pojo"); //別名註冊器 TypeAliasRegistry typeAliasRegistry = new TypeAliasRegistry(); typeAliasRegistry.registerAlias("STDOUT_LOGGING", MyBatisConfig.class); return sqlSessionFactory; } }
application.properties
server.port=8080 # 資料庫訪問配置 spring.datasource.type=com.alibaba.druid.pool.DruidDataSource spring.datasource.driver-class-name=com.mysql.jdbc.Driver spring.datasource.url=jdbc:mysql://localhost:3306/shop?useUnicode=true&characterEncoding=gbk&zeroDateTimeBehavior=convertToNull&useSSL=false spring.datasource.username=root spring.datasource.password=root # 下面為連線池的補充設定,應用到上面所有資料來源中 spring.datasource.initialSize=5 spring.datasource.minIdle=5 spring.datasource.maxActive=20 # 配置獲取連線等待超時的時間 spring.datasource.maxWait=60000 # 配置間隔多久才進行一次檢測,檢測需要關閉的空閒連線,單位是毫秒 spring.datasource.timeBetweenEvictionRunsMillis=60000 # 配置一個連線在池中最小生存的時間,單位是毫秒 spring.datasource.minEvictableIdleTimeMillis=300000 spring.datasource.validationQuery=SELECT 1 FROM DUAL spring.datasource.testWhileIdle=true spring.datasource.testOnBorrow=false spring.datasource.testOnReturn=false #Thymeleaf配置 spring.thymeleaf.cache=false spring.thymeleaf.encoding=utf-8 spring.thymeleaf.mode=HTML5 spring.thymeleaf.prefix=classpath:/templates/ spring.thymeleaf.suffix=.html
日誌log4j2的配置
先引入依賴
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter</artifactId> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-logging</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-log4j2</artifactId> </dependency>
然後,建立log4j2.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration status="OFF" monitorInterval="30">
<Properties>
<Property name="LOG_PATTERN">
%d{yyyy-MM-dd HH:mm:ss.SSS} %5p ${hostName} --- [%15.15t] %-40.40c{1.} : %m%n%ex
</Property>
<Property name="LOG_FILE_PATH">logs</Property>
</Properties>
<appenders>
<Console name="Console" target="SYSTEM_OUT" follow="true">
<PatternLayout pattern="${LOG_PATTERN}" />
</Console>
<RollingFile name="RollingFile" fileName="${LOG_FILE_PATH}/spring-boot-log4j2-demo.log" filePattern="${LOG_FILE_PATH}/spring-boot-log4j2-demo-%d{yyyy-MM-dd}-%i.log">
<PatternLayout>
<Pattern>${LOG_PATTERN}</Pattern>
</PatternLayout>
<Filters>
<!-- 只記錄ERROR級別日誌資訊,程式列印的其他資訊不會被記錄 -->
<!-- 此level設定的日誌級別,是過濾日誌檔案中打印出的日誌資訊,和Root的level有所區別 -->
<ThresholdFilter level="ERROR" onMatch="ACCEPT" onMismatch="DENY" />
</Filters>
<Policies>
<SizeBasedTriggeringPolicy size="10MB" />
<!-- 每天建立一個日誌檔案 -->
<TimeBasedTriggeringPolicy interval="1" />
</Policies>
<DefaultRolloverStrategy max="10"/>
</RollingFile>
</appenders>
<loggers>
<root level="INFO">
<appender-ref ref="RollingFile" />
<appender-ref ref="Console" />
</root>
</loggers>
</configuration>
最後,在util中建立工具類Log4j2Util
package com.example.springboot.util; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; public class Log4j2Util { public static final Logger logger = LogManager.getLogger(Log4j2Util.class); }