Spring代码片段

97 阅读9分钟

文章目录

《Spring Boot参考指南》:blog.didispace.com/books/sprin…

基础部分

自定义的bean用注解,非自定义的bean用xml配置文件

set方法使用xml让spring创建bean

xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"

<context:property-placeholder location="jdbc.properties"/>
<!--数据源对象-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <property name="driverClass" value="${jdbc.driver}"/>
    <property name="jdbcUrl" value="${jdbc.url}"/>
    <property name="user" value="${jdbc.user}"/>
    <property name="password" value="${jdbc.pwd}"/>
</bean>
<!--jdbc模板对象-->
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
    <property name="dataSource" ref="dataSource"/>
</bean>

// 把容器中的ref=jdbcTemplate通过class=AccountDaoImpl内部的一个name=setJdbcTemplate方法注入给AccountDaoImpl
// 目标bean是class=com.sxf.Dao.Impl.AccountDaoImpl
// 注入方法是name=jdbcTemplate中的setJdbcTemplate
// 注入内容是ref=jdbcTemplate,对应上面的id=jdbcTemplate这个bean
<bean id="accountDao" class="com.sxf.Dao.Impl.AccountDaoImpl">
    <property name="jdbcTemplate" ref="jdbcTemplate"/>
</bean>
public class AccountDaoImpl implements AccountDao {
    private JdbcTemplate jdbcTemplate;
    public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {
        this.jdbcTemplate = jdbcTemplate;
    }
}

public class AccountServiceImpl implements AccountService {
    private AccountDao accountDao;
    public void setAccountDao(AccountDao accountDao){
        this.accountDao = accountDao;
    }
}

// 从spring容器获取bean
public static void main(String[] args) {
    ApplicationContext app = new ClassPathXmlApplicationContext("applicationContext.xml");
    AccountService accountService = app.getBean(AccountService.class);
    accountService.transfer();
}
  • xmlbean中,id是唯一标识符,可以任意设置;class是要自动创建的类的路径;property是增加属性设置;nameset方法后面的内容(如setJdbcTemplate中的jdbcTemplate);ref是当前xml中已有的beanid名(对象的引用用ref)。
  • AccountDaoImpl 中,把容器中的ref=jdbcTemplate通过class=AccountDaoImpl内部的一个name=setJdbcTemplate方法注入给AccountDaoImpl

JdbcTemplate

<dependencies>
	<dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-test</artifactId>
            <version>5.2.7.RELEASE</version>
        </dependency>
    <dependency>
        <groupId>mysql</groupId>
        <artifactId>mysql-connector-java</artifactId>
        <version>8.0.21</version>
    </dependency>
    <dependency>
      <groupId>com.alibaba</groupId>
        <artifactId>druid</artifactId>
        <version>1.1.22</version>
    </dependency>
    <dependency>
        <groupId>c3p0</groupId>
        <artifactId>c3p0</artifactId>
        <version>0.9.1.2</version>
    </dependency>
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jdbc</artifactId>
        <version>5.2.7.RELEASE</version>
    </dependency>
    <dependency>
        <!-- 事务 -->
        <groupId>org.springframework</groupId>
        <artifactId>spring-tx</artifactId>
        <version>5.2.7.RELEASE</version>
    </dependency>
</dependencies>
// 创建数据源对象
ComboPooledDataSource dataSource = new ComboPooledDataSource();
dataSource.setDriverClass("com.mysql.cj.jdbc.Driver");
dataSource.setJdbcUrl("jdbc:mysql://localhost:3306/test");
dataSource.setUser("root");
dataSource.setPassword("1061700625");

JdbcTemplate jdbcTemplate = new JdbcTemplate();
// 设置数据源对象
jdbcTemplate.setDataSource(dataSource);
jdbcTemplate.update("insert into account values(?,?)", "tom", 5000);

spring产生JdbcTemplate对象

jdbc.driver=com.mysql.cj.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/test
jdbc.user=root
jdbc.pwd=1061700625
<context:property-placeholder location="jdbc.properties"/>

<!--数据源对象-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <property name="driverClass" value="${jdbc.driver}"/>
    <property name="jdbcUrl" value="${jdbc.url}"/>
    <property name="user" value="${jdbc.user}"/>
    <property name="password" value="${jdbc.pwd}"/>
</bean>

<!--jdbc模板对象-->
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
    <property name="dataSource" ref="dataSource"/>
</bean>
ApplicationContext app = new ClassPathXmlApplicationContext("applicationContext.xml");
JdbcTemplate jdbcTemplate= app.getBean(JdbcTemplate.class);
int row = jdbcTemplate.update("insert into account values(?,?)", "ros", 5000);
System.out.println(row);
或
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class JdbcTempTest {
	@Test
    public void test2() {
        int row = jdbcTemplate.update("insert into account values(?,?)", "bob", 5000);
        System.out.println(row);
    }
}
// 查询所有
List<Account> query = jdbcTemplate.query("select * from account;", new BeanPropertyRowMapper<Account>(Account.class));
System.out.println(query);
// 查询单个
Account query2 = jdbcTemplate.queryForObject("select * from account where name=?", new BeanPropertyRowMapper<Account>(Account.class), "tom");
System.out.println(query2);
//聚合查询
Long aLong = jdbcTemplate.queryForObject("select count(*) from account", Long.class);
System.out.println(aLong);

基于XML的事务控制

切点:被增强的方法(业务方法)
通知:事务控制
切面:配置织入

配置要点:

  • 平台事务管理器配置
  • 事务通知配置
  • 事务aop织入配置
xmlns:context="http://www.springframework.org/schema/context"
xmlns:tx="http://www.springframework.org/schema/tx"
xmlns:aop="http://www.springframework.org/schema/aop"

http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd

<context:property-placeholder location="jdbc.properties"/>

<!--数据源对象-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <property name="driverClass" value="${jdbc.driver}"/>
    <property name="jdbcUrl" value="${jdbc.url}"/>
    <property name="user" value="${jdbc.user}"/>
    <property name="password" value="${jdbc.pwd}"/>
</bean>

<!--jdbc模板对象-->
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
    <property name="dataSource" ref="dataSource"/>
</bean>

<bean id="accountDao" class="com.sxf.Dao.Impl.AccountDaoImpl">
    <property name="jdbcTemplate" ref="jdbcTemplate"/>
</bean>

<!--业务层,目标对象,内部的方法就是切点-->
<bean id="accountService" class="com.sxf.Service.Impl.AccountServiceImpl">
    <property name="accountDao" ref="accountDao"/>
</bean>

<!--指定平台事务管理器,jdbc和mybatis使用DataSourceTransactionManager-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <!--内部控制事务时,需要通过DataSource.getConnection-->
    <property name="dataSource" ref="dataSource"/>
</bean>

<!--通知,事务的增强-->
<tx:advice id="txAdvice" transaction-manager="transactionManager">
    <!--设置事务的属性信息-->
    <tx:attributes>
        <!-- 哪些方法被增强-->
        <tx:method name="transfer" read-only="false"/>
        <tx:method name="update*" timeout="20"/>
        <!-- 所有方法-->
        <tx:method name="*" timeout="10"/>
    </tx:attributes>
</tx:advice>

<!--配置事务的AOP织入-->
<aop:config>
<!--spring为事务增强的提供配置,一个通知的切面;普通用aop:aspect-->
    <aop:advisor advice-ref="txAdvice" pointcut="execution(* com.sxf.Service.Impl.*.*(..))"></aop:advisor>
</aop:config>
public void out(String name, Double out) {
   jdbcTemplate.update("update account set money=money-? where name=?", out, name);
}

@Override
public void in(String name, Double in) {
    jdbcTemplate.update("update account set money=money+? where name=?", in, name);
}

public void transfer() {
	accountDao.out("tom", 100.0);
	int a = 1/0;   // 故意抛出异常
	accountDao.in("ros", 100.0);
}

基于注解的事务控制

<context:property-placeholder location="jdbc.properties"/>
<!--组件扫描,扫com.sxf这个包-->
<context:component-scan base-package="com.sxf"/>

<!--数据源对象-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
    <property name="driverClass" value="${jdbc.driver}"/>
    <property name="jdbcUrl" value="${jdbc.url}"/>
    <property name="user" value="${jdbc.user}"/>
    <property name="password" value="${jdbc.pwd}"/>
</bean>

<!--jdbc模板对象-->
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
    <property name="dataSource" ref="dataSource"/>
</bean>
    
<!--指定平台事务管理器,jdbc和mybatis使用DataSourceTransactionManager-->
<beanid="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <!--内部控制事务时,需要通过DataSource.getConnection-->
    <property name="dataSource" ref="dataSource"/>
</bean>

<!--事务的注解驱动-->
<tx:annotation-driven transaction-manager="transactionManager"/>
@Service("accountService")
public class AccountServiceImpl implements AccountService {
    @Autowired
    private AccountDao accountDao;
    
    @Override
    @Transactional
    public void transfer() {
        accountDao.out("tom", 100.0);
        int a = 1/0;   // 故意抛出异常
        accountDao.in("ros", 100.0);
    }
}

spring获取ApplicationContext

pom.xml

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-web</artifactId>
    <version>5.2.7.RELEASE</version>
</dependency>

web.xml

<!--设置全局变量-->
<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath:applicationContext.xml</param-value>
</context-param>
<!--配置spring内置的监听器-->
<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

applicationContext.xml

<bean id="userDao" class="com.sxf.dao.impl.UserDaoImpl"> </bean>
<bean id="userService" class="com.sxf.service.impl.UserServiceImpl">
    <property name="userDao" ref="userDao"/>
</bean>

UserServlet.java

@WebServlet("/")
public class UserServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) {
        ServletContext servletContext = req.getServletContext();
        WebApplicationContext app = WebApplicationContextUtils.getWebApplicationContext(servletContext);
        UserServiceImpl userService = app.getBean(UserServiceImpl.class);
        userService.save();
    }
}

spring mvc简单配置

在这里插入图片描述
导入springmvc相关坐标
pom.xml

<dependency>
	<groupId>org.springframework</groupId>
	<artifactId>spring-webmvc</artifactId>
	<version>5.2.7.RELEASE</version>
</dependency>

配置springmvc核心控制器DispatcherServlet
web.xml

<!--配置springmvc前端控制器-->
<servlet>
    <servlet-name>DispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <load-on-startup>1</load-on-startup>
    <init-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>classpath:spring-mvc.xml</param-value>
    </init-param>
</servlet>
<servlet-mapping>
    <servlet-name>DispatcherServlet</servlet-name>
    <url-pattern>/</url-pattern>
</servlet-mapping>

spring-mvc.xml

<!--controller的组件扫描-->
<context:component-scan base-package="com.sxf.controller"/>

创建controller类,使用注解配置controller类中业务方法的映射地址
UserController.java

@Controller
public class UserController {
    @RequestMapping("/save")
    public String save() {
        System.out.println("save");
        return "ok.jsp";
    }
}

创建视图页面
webapp/ok.jsp

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>Title</title>
</head>
<body>
	ok save
</body>
</html>

在这里插入图片描述

springmvc数据响应

页面跳转

request乱码:request.setCharacterEncoding("utf-8");
response乱码:resp.setContentType("text/html;charset=utf-8");

@Controller
public class UserController {
    @RequestMapping(value = "/save", method = RequestMethod.GET)
    public String save() {
        System.out.println("save");
        return "ok.jsp";
    }

    @RequestMapping(value = "/save2", method = RequestMethod.GET)
    public ModelAndView save2() {
        ModelAndView modelAndView = new ModelAndView();
        modelAndView.addObject("username", "gogogo");
        modelAndView.setViewName("save");
        return modelAndView;
    }

    @RequestMapping(value = "/save3", method = RequestMethod.GET)
    public ModelAndView save3(ModelAndView modelAndView) {
        modelAndView.addObject("username", "gogogo");
        modelAndView.setViewName("save");
        return modelAndView;
    }

    @RequestMapping(value = "/save4", method = RequestMethod.GET)
    public String save4(Model model) {
        model.addAttribute("username", "gogogo");
        return "ok.jsp";
    }

	// 不常见
    @RequestMapping(value = "/save5", method = RequestMethod.GET)
    public String save5(HttpServletRequest request) {
        request.setAttribute("username", "gogogo");
        return "ok.jsp";
    }
}

回写字符数据

添加注解:@ResponseBody

@ResponseBody
@RequestMapping(value = "/save7", method = RequestMethod.GET)
public String save7() {
    return "kkk";
}

回写对象、集合(json)数据

使用<mvc:annotation-driven/>默认底层就会集成jackson进行对象或集合的json格式字符串的转换。
spring-mvc.xml:

<mvc:annotation-driven/>
@ResponseBody
@RequestMapping(value = "/save7", method = RequestMethod.GET)
public User save7() {
    User user = new User();
    /*...*/
    return user;
}

静态资源访问

添加路径
spring-mvc.xml

<mvc:resources mapping="/js/**" location="/js/"/>


由Tomcat访问
spring-mvc.xml

<mvc:default-servlet-handler/>

ajax发送集合参数

index.html

<script src="js/jquery-3.1.1.min.js"></script>
<script>
    var userList = new Array();
    userList.push({username:"zhangsan", age:18});
    userList.push({username:"lisi", age:19});
    $.ajax({
        url: "/demo_war_exploded/save8",
        type: "POST",
        data: JSON.stringify(userList),
        contentType: "application/json;charset=utf-8"
    });
</script>

UserController.java
注意要加: @RequestBody

@ResponseBody
@RequestMapping(value = "/save8")
public void save8(@RequestBody List<User> users) {
    System.out.println(users);
}

全局乱码过滤器

web.xml

<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>
</filter>
<filter-mapping>
    <filter-name>CharacterEncodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

自定义类型转换器

1、定义转换器类实现Converter接口
DateConverter.java

public class DateConverter implements Converter<String, Date> {
    @Override
    public Date convert(String s) {
        DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
        Date date = null;
        try {
            date = dateFormat.parse(s);
        } catch (ParseException e) {
            e.printStackTrace();
        }
        return date;
    }
}

2、xml中声明转换器
spring-mvc.xml

<bean id="conversionService" class="org.springframework.context.support.ConversionServiceFactoryBean">
    <property name="converters">
        <list>
            <bean class="com.sxf.converter.DateConverter"> </bean>
        </list>
    </property>
</bean>

3、引用转换器
spring-mvc.xml

<mvc:annotation-driven conversion-service="conversionService" />

文件上传

1、导入upload和io
pom.xml

<dependency>
    <groupId>commons-fileupload</groupId>
    <artifactId>commons-fileupload</artifactId>
    <version>1.4</version>
</dependency>
<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.6</version>
</dependency>

2、配置文件上传解析器
spring-mvc.xml

<!--注意id="multipartResolver"-->
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
    <property name="maxUploadSize" value="50000"/>
    <property name="defaultEncoding" value="utf-8"/>
</bean>

3、编写文件上传代码
upload.html

<form action="/demo_war_exploded/save10" method="post" enctype="multipart/form-data">
    <input type="text" name="username"><br/>
    <input type="file" name="uploadFile"><br/>
    <input type="file" name="uploadFile"><br/>
    <input type="submit"><br/>
</form>

UserController.java

@ResponseBody
@RequestMapping(value = "/save10")
// username 与 <input type="text" name="username"> 中的name相同
// uploadFile 与 <input type="file" name="uploadFile"> 中的name相同
public void save10(String username, MultipartFile[] uploadFile) throws IOException {
    System.out.println(username);
    for (MultipartFile multipartFile: uploadFile) {
        String filename = multipartFile.getOriginalFilename();
        System.out.println(filename);
        File file = new File(".", filename);
        multipartFile.transferTo(file);
        System.out.println(file.getAbsolutePath());
    }
}

配置拦截器

1、定义拦截类实现HandlerInterceptor接口
MyInterceptor1.java

public class MyInterceptor1 implements HandlerInterceptor {

    @Override
    // 目标方法执行之前
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("preHandle");
        // false: 拒绝继续执行
        return true;
    }

    @Override
    // 目标方法执行之后,视图对象返回之前
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("postHandle");
    }

    @Override
    // 流程都执行完毕之后
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("afterCompletion");
    }
}

2、配置拦截器
spring-mvc.xml

<mvc:interceptors>
    <mvc:interceptor>
        <!--对哪些资源执行拦截操作-->
        <mvc:mapping path="/**"/>
        <bean class="com.sxf.interceptor.MyInterceptor1"> </bean>
    </mvc:interceptor>
</mvc:interceptors>

session

在这里插入图片描述

简单映射异常处理

spring-mvc.xml

<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver">
    <property name="exceptionMappings">
        <map>
            <entry key="java.lang.ClassCastException" value="/web/error.jsp"/>
        </map>
    </property>
    <!--默认的错误视图-->
    <property name="defaultErrorView" value="/web/error.jsp"/>
</bean>

自定义异常处理

1、创建异常处理器实现HandlerExceptionResolver
MyExceptionResolver .java

public class MyExceptionResolver implements HandlerExceptionResolver {
    @Override
    public ModelAndView resolveException(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) {
        ModelAndView modelAndView = new ModelAndView();
        if (e instanceof ClassCastException) {
            modelAndView.addObject("info", "转换异常");
            modelAndView.setViewName("/web/error.jsp");
        }
        return modelAndView;
    }
}

2、配置处理器
spring-mvc.xml

<bean class="com.sxf.resolver.MyExceptionResolver"> </bean>

mybatis配置

在这里插入图片描述
1、导入mybatis坐标
pom.xml

<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis</artifactId>
    <version>3.4.6</version>
</dependency>

2、创建user实体类
User.java

public class User {
    private Long id;
    private String username;
    private String password;
	/.../
}

3、编写映射文件UserMapper.xml
UserMapper.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="userMapper">
    <select id="findAll" resultType="com.sxf.domain.User">
        select * from sys_user;
    </select>
	<insert id="save" parameterType="com.sxf.domain.User">
        insert into sys_user values (#{id}, #{username}, #{password})
    </insert>
</mapper>

4、编写核心配置文件SqlMapConfig.xml
SqlMapConfig.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd" >
<configuration>
    <!--配置数据源环境,默认环境=development-->
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"></transactionManager>
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.cj.jdbc.Driver"/>
                <property name="url" value="jdbc:mysql://localhost:3306/test"/>
                <property name="username" value="root"/>
                <property name="password" value="root"/>
            </dataSource>
        </environment>
    </environments>

    <!--加载映射文件-->
    <mappers>
        <mapper resource="com/sxf/mapper/UserMapper.xml"></mapper>
    </mappers>
</configuration>

5、编写测试类
MyBatisTest.java

public void test1() throws IOException{
    // 加载核心配置文件
    InputStream resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");
    // 获得session工厂对象
    SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(resourceAsStream);
    // 获得session会话对象
    SqlSession sqlSession = sqlSessionFactory.openSession();
    // 执行操作,参数:namespace + id
    List<User> userList = sqlSession.selectList("userMapper.findAll");
    System.out.println(userList);
    // 释放资源
    sqlSession.close();
}

@Test
public void test2() throws IOException{
    User user = new User();
    user.setUsername("my");
    user.setPassword("batis");
    // 加载核心配置文件
    InputStream resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");
    // 获得session工厂对象
    SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(resourceAsStream);
    // 获得session会话对象
    SqlSession sqlSession = sqlSessionFactory.openSession();
    // 执行操作,参数:namespace + id
    sqlSession.insert("userMapper.save", user);
    // 提交事务,插入操作涉及数据库数据变化。所以要使用sqlSession对象显示的提交事务,
    sqlSession.commit();
    // 释放资源
    sqlSession.close();
}

mybatis代理方式

在这里插入图片描述
1、mapper.xml文件中的namespace与mapper接口的全限定名相同
2、mapper接口方法名和mapper.xml中定义的每个statement的id相同
3、mapper接口方法的输入参数类型和mapper.xml中定义的每个sql的parameterType的类型相同
4、mapper接口方法的输出参数和mapper.xml中定义的每个sql的resultType的类型相同
UserMapper.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.sxf.mapper.UserMapper">
    <select id="findAll" resultType="com.sxf.domain.User">
        select * from sys_user;
    </select>

    <insert id="save" parameterType="com.sxf.domain.User">
        insert into sys_user values (#{id}, #{username}, #{email}, #{password},#{phoneNum})
    </insert>
</mapper>

UserMapper.java

public interface UserMapper {
    List<User> findAll();
}

Main.java

public static void main(String[] args) throws IOException {
    InputStream resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");
    SqlSessionFactory sessionFactory = new SqlSessionFactoryBuilder().build(resourceAsStream);
    SqlSession sqlSession = sessionFactory.openSession();
    // 获得mybatis框架生成的UserMapper接口的实现类
    UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
    // 使用UserMapper接口中的方法执行操作
    List<User> all = userMapper.findAll();
    System.out.println(all);
    sqlSession.close();
}

mybatis动态sql

UserMapper.xml

<select id="findByConditon" parameterType="com.sxf.domain.User" resultType="com.sxf.domain.User">
    select * from sys_user
    <where>
        <if test="id!=null">
            and id=#{id}
        </if>
        <if test="username!=null">
            and username=#{username}
        </if>
    </where>
</select>

<select id="findByIds" parameterType="list" resultType="com.sxf.domain.User">
    select * from sys_user # where id IN(1,2,3)
    <where>
        # collection:如果是数组就用array,如果是list集合就用list
        # open:以什么开始
        # close:以什么结束
        # item:每一项,名称自定,负责接收集合中的每一个值
        # separator:分隔符
        <foreach collection="list" open="id in(" close=")" item="id" separator=",">
            #{id}
        </foreach>
    </where>
</select>

PageHelper分页插件

1、导入坐标
pom.xml

<dependency>
    <groupId>com.github.pagehelper</groupId>
    <artifactId>pagehelper</artifactId>
    <version>5.1.8</version>
</dependency>
<dependency>
    <groupId>com.github.jsqlparser</groupId>
    <artifactId>jsqlparser</artifactId>
    <version>1.2</version>
</dependency>

2、mybatis配置文件中配置pagehelper插件

<plugins>
    <plugin interceptor="com.github.pagehelper.PageHelper">
        <!--不同的数据库使用不同的语句,当前指定mysql-->
        <property name="dialect" value="mysql"/>
    </plugin>
</plugins>

3、测试分页数据

// 获得mybatis框架生成的UserMapper接口的实现类
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);

// 设置分页相关参数,当前页页码+当前页条数
PageHelper.startPage(1, 2);
List<User> userList = userMapper.findAll();
System.out.println(userList);
// 查询分页相关信息
PageInfo<User>  pageInfo = new PageInfo<>(userList);
pageInfo.getPages();
pageInfo.getPrePage();

一对一的多表查询

关键在于手动指定字段与实体属性的映射关系:resultMap
OrderMapper.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.sxf.mapper.OrderMapper">
    
    <resultMap id="orderMap" type="com.sxf.domain.Order">
        <!--手动指定字段与实体属性的映射关系-->
        <!--column:数据表的字段名称-->
        <!--property:实体属性的名称-->
        <!--oid:在下方查询语句中已经定义了oid这个别名-->
        <id column="oid" property="id"/>
        <result column="ordertime" property="orderTime"/>
        <result column="total" property="total"/>
        <result column="uid" property="user.id"/>
        <result column="username" property="user.username"/>
        <result column="password" property="user.password"/>
    </resultMap>

    <select id="findAll" resultMap="orderMap">
        SELECT *,o.id oid FROM orders o, user u WHERE o.uid=u.id
    </select>
</mapper>

或者

<resultMap id="orderMap" type="com.sxf.domain.Order">
    <id column="oid" property="id"/>
    <result column="ordertime" property="orderTime"/>
    <result column="total" property="total"/>
    
    <association property="user" javaType="com.sxf.domain.User">
        <id column="uid" property="id"/>
        <result column="username" property="username"/>
        <result column="password" property="password"/>
    </association>
</resultMap>

SqlMapConfig.xml

<!-- ... -->
<!--加载映射文件-->
<mappers>
    <mapper resource="com/sxf/mapper/UserMapper.xml"></mapper>
    <mapper resource="com/sxf/mapper/OrderMapper.xml"></mapper>
</mappers>

Order.java

private int id;
private String orderTime;
private double total;
private User user;

User.java

private Long id;
private String username;
private String password;

Spring Boot

手动创建工程

1、添加依赖
pom.xml

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.3.5.RELEASE</version>
</parent>

<dependencies>
    <!--spring-boot依赖-->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
</dependencies>

2、编写启动引导类
Applicatiion.java

@SpringBootApplication
public class Applicatiion {
    public static void main(String[] args) {
        // 指定入口类为Applicatiion
        SpringApplication.run(Applicatiion.class, args);
    }
}

3、编写处理器
DemoController.java

@RestController
public class DemoController {

    @RequestMapping("/")
    public String hello() {
        return "hello";
    }
}

配置修改流程

1、查找spring-boot-autoconfigure-xxx.jar文件
在这里插入图片描述
2、查找当前组件对应在上述jar包中的package
在这里插入图片描述
3、查看xxxProperties配置项类
在这里插入图片描述
4、在application.yml中修改配置参数
在这里插入图片描述
在这里插入图片描述

自定义拦截器

1、编写拦截器,实现HandlerInterceptor
MyInterceptor .java

public class MyInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("preHandle");
        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("postHandle");
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("afterCompletion");
    }
}

2、编写配置类,实现WebMvcConfigurer,在该类中添加各种组件
Myconfig .java

@Configuration
public class Myconfig implements WebMvcConfigurer {
    @Bean
    // 注册拦截器
    public MyInterceptor myInterceptor() {
        return new MyInterceptor();
    }

    @Override
    // 添加拦截器到spring mvc拦截器链中
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(myInterceptor()).addPathPatterns("/*");
    }
}

整合mybatis

1、添加mybatis启动器依赖
pom.xml

<dependency>
    <groupId>org.mybatis.spring.boot</groupId>
    <artifactId>mybatis-spring-boot-starter</artifactId>
    <version>2.1.3</version>
</dependency>

2、配置mybatis
application.yml

mybatis:
  # 配置实体类的别名,实体类的包路径
  type-aliases-package: com.sxf.entity
  # 映射文件路径
  # mapper-locations: classpath:mapper/*.xml
  configuration:
    # 日志
    log-impl: org.apache.ibatis.logging.stdout.StdOutImpl

若启动报错,则将中文注释删掉即可。
3、设置启动类中的mapper扫描
DemoApplication.java

@SpringBootApplication
@MapperScan("com.sxf.mapper")
public class DemoApplication {
    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }
}

整合通用mapper

通用mapper可以自动拼接sql语句,不用用户编写。
1、添加启动器依赖
pom.xml

<dependency>
    <groupId>tk.mybatis</groupId>
    <artifactId>mapper-spring-boot-starter</artifactId>
    <version>2.1.5</version>
</dependency>

2、将UserMapper接口继承Mapper<User>
UserMapper.java

import tk.mybatis.mapper.common.Mapper;
public interface DemoMapper extends Mapper<User> {
}

3、修改启动引导类Application中的Mapper扫描注解(修改为tk.mybatis.spring.annotation.MapperScan的)
DemoApplication.java

import tk.mybatis.spring.annotation.MapperScan;

@SpringBootApplication
@MapperScan("com.sxf.mapper")
public class DemoApplication {
    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }
}

4、修改User实体类添加JPA注解
User.java

@Data
// 数据表名称
@Table(name = "user")
public class User {
    @Id
    // 主键回调
    @KeySql(useGeneratedKeys = true)
    private int id;
    
    // 普通列名,可以不用
    @Column(name = "username")
    private String username;
    private String password;
}

5、实现业务功能

@Autowired
private UserMapper userMapper;
// ...
userMapper.selectByPrimaryKey(id);
// 选择性新增,如果属性为空则该属性不会出现在insert语句上
userMapper.insertSelective(user);

整合Junit

1、添加依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
</dependency>

2、编写测试类,注意需要添加@SpringBootTest@RunWith(SpringRunner.class)

@RunWith(SpringRunner.class)
@SpringBootTest
class UserControllerTest {
    @Test
    void hello() {
    // ...
    }
}

整合redis

1、添加依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

2、配置参数

spring:
  redis:
    host: localhost
    port: 6379

3、使用

@Autowired
private RedisTemplate redisTemplate;
// ...
redisTemplate.opsForValue().set("str", "sss");
System.out.println(redisTemplate.opsForValue().get("str"));

部署

1、添加maven打包插件,若不添加,则无法产生jar清单文件,导致打包出来的jar文件无法使用命令运行
pom.xml

<build>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
        </plugin>
    </plugins>
</build>

2、使用maven的命令package打包

其余部分