视频出处:动力节点springboot视频教程
为什么要使用Spring Boot?
Spring使用XML作为容器配置文件,在3.0之后加入了JavaConfig,使得可以用java类作为配置文件使用。
这一点就是Spring Boot移除SSM中大量配置文件所用到的重要技术。
**JavaConfig:**使用java类作为xml配置文件的代替,是配置Spring容器的纯java方法。在这个java类中可以创建java对象,把对象注入Spring容器中。
优点:
①创建maven工程,添加依赖
<dependencies>
<dependency>
<groupId>org.springframeworkgroupId>
<artifactId>spring-contextartifactId>
<version>5.3.1version>
dependency>
<dependency>
<groupId>junitgroupId>
<artifactId>junitartifactId>
<version>4.12version>
<scope>testscope>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<artifactId>maven-compiler-pluginartifactId>
<version>3.5.1version>
<configuration>
<source>1.8source>
<target>1.8target>
<encoding>UTF-8encoding>
configuration>
plugin>
plugins>
build>
②创建数据类
package com.tsccg.pojo;
public class Student {
private String name;
private Integer age;
private String sex;
//get和set...
//toString
}
③resources 目录下创建 Spring 的配置文件 :beans.xml
声明一个Student对象:
<bean id="student" class="com.tsccg.pojo.Student">
<property name="name" value="张三"/>
<property name="age" value="20"/>
<property name="sex" value="男"/>
bean>
单元测试:
/**
* 使用xml方式创建对象
*/
@Test
public void beanTest01() {
ApplicationContext app = new ClassPathXmlApplicationContext("beans.xml");
Student student = (Student) app.getBean("student");
System.out.println("xml方式创建对象:"+student);
}
结果:
xml方式创建对象:Student{name='张三', age=20, sex='男'}
需要使用两个注解:
@Configuration
:放在类上,声明当前类为配置类。@Bean
:放在方法上,将方法返回的对象注入到容器中。创建配置类:
package com.tsccg.javaconfig;
import com.tsccg.pojo.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.ImportResource;
/**
* @Author: TSCCG
* @Date: 2021/12/13 18:12
*/
@Configuration//声明此类为配置类,在这个类中有很多方法, 方法的返回值是对象。
public class SpringConfig {
/**
* 创建Student对象并返回
* 通过@Bean注解将对象注入容器,对象默认id为方法名
*/
@Bean
public Student createStudent() {
Student student = new Student();
student.setName("李四");
student.setAge(22);
student.setSex("女");
return student;
}
/**
* 自定义Bean对象id
*/
@Bean(name = "liSiStudent")
public Student createStudent2() {
Student student = new Student();
student.setName("李四");
student.setAge(22);
student.setSex("女");
return student;
}
}
单元测试:
/**
* 使用javaConfig创建Student对象
*/
@Test
public void beanTest02() {
ApplicationContext app = new AnnotationConfigApplicationContext(SpringConfig.class);
Student student = (Student) app.getBean("createStudent");
System.out.println("javaConfig方式创建对象:"+student);
}
/**
* 自定义bean对象id
*/
@Test
public void beanTest03() {
ApplicationContext app = new AnnotationConfigApplicationContext(SpringConfig.class);
Student student = (Student) app.getBean("liSiStudent");
System.out.println("自定义id:"+student);
}
结果:
javaConfig方式创建对象:Student{name='李四', age=22, sex='女'}
自定义id:Student{name='李四', age=22, sex='女'}
@ImporResource是在配置类里导入其他的xml配置文件,等同于xml配置的
<import resource="classpath:xxx.xml"/>
用法:
①在beans.xml文件中声明一个Student对象
<bean id="wangWuStudent" class="com.tsccg.pojo.Student">
<property name="name" value="王五"/>
<property name="age" value="18"/>
<property name="sex" value="女"/>
bean>
②在配置类上添加@ImporResource
注解,导入beans.xml文件
@Configuration
@ImportResource(value="classpath:beans.xml")//导入beans.xml配置文件,指定从类路径下导入
public class SpringConfig {
...
}
③单元测试
/**
* 配置类导入xml配置文件
*/
@Test
public void beanTest04() {
ApplicationContext app = new AnnotationConfigApplicationContext(SpringConfig.class);
Student student = (Student) app.getBean("wangWuStudent");
System.out.println("JavaConfig导入xml配置文件:"+student);
}
结果:
JavaConfig导入xml配置文件:Student{name='王五', age=18, sex='女'}
④导入多个配置文件
@Configuration
@ImportResource(value={"classpath:beans.xml","classpath:applicationContext.xml"})
public class SpringConfig {
...
}
@PropertySource用于在配置类里读取properties属性配置文件,等同于xml配置里的:
<context:property-placeholder location="classpath:xxx.properties"/>
用法:
①在resources目录下创建属性配置文件config.properties
dog.name=小哈
dog.type=哈士奇
dog.age=1
②创建数据类
使用@Component注解创建对象并放入容器,使用@Value注解读取配置文件中的数据并注入对象属性
package com.tsccg.pojo;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
/**
* @Author: TSCCG
* @Date: 2021/12/13 19:59
*/
@Component("myDog")//创建对象并注入容器中
public class Dog {
@Value("${dog.name}")//读取属性配置文件中的数据,注入到对象属性中
private String name;
@Value("${dog.type}")
private String type;
@Value("${dog.age}")
private Integer age;
@Override
public String toString() {
return "Dog{" +
"name='" + name + '\'' +
", type='" + type + '\'' +
", age=" + age +
'}';
}
}
③修改配置类
1)使用@PropertySource注解读取属性配置文件
2)使用@ComponentScan注解扫描数据类,等同于
@Configuration//声明此类为配置类。
@PropertySource(value="classpath:config.properties")//读取属性配置文件
@ComponentScan(basePackages = "com.tsccg.pojo")//组件扫描器
public class SpringConfig {
...
}
④单元测试
/**
* @PropertySource 读取属性配置文件
*/
@Test
public void beanTest05() {
ApplicationContext app = new AnnotationConfigApplicationContext(SpringConfig.class);
Dog myDog = (Dog) app.getBean("myDog");
System.out.println("外部属性配置文件注入:"+myDog);
}
结果:
外部属性配置文件注入:Dog{name='小哈', type='哈士奇', age=1}
Spring Boot是Spring家族的一个成员,可以简化Spring和SpringMVC的使用。核心还是IOC容器。
特性:
翻译:
mybatis-spring-boot-starter
依赖即可。国外地址:https://start.spring.io/
国内地址:https://start.springboot.io/
步骤:
①新建项目
②初始化设置
③添加依赖
④设置项目路径并创建
⑤项目结构
启动类:Application.java
package com.tsccg;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
测试类:ApplicationTests.java
package com.tsccg;
import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;
@SpringBootTest
class ApplicationTests {
@Test
void contextLoads() {
}
}
⑥项目依赖
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.6.1version>
<relativePath/>
parent>
<groupId>com.tsccggroupId>
<artifactId>02-springboot-demo-firstartifactId>
<version>0.0.1-SNAPSHOTversion>
<name>02-springboot-demo-firstname>
<description>Demo project for Spring Bootdescription>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-testartifactId>
<scope>testscope>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
web起步依赖相关jar:
⑦也可以通过浏览器打开初始化器页面
下载自动生成的项目文件,导入本地即可。
使用Maven向导的方式就是直接创建一个maven项目,按Spring Boot项目结构添加所需文件和配置。
使用Maven创建的好处是可以不用联网。
步骤:
①创建一个空的Maven项目
②修改pom.xml文件
1)添加spring-boot-starter-parent坐标
2)添加web启动依赖及其他配置
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.6.1version>
<relativePath/>
parent>
<groupId>com.tsccggroupId>
<artifactId>03-springboot-demo-secondartifactId>
<version>1.0-SNAPSHOTversion>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-testartifactId>
<scope>testscope>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
③修改项目结构
1)创建启动类Application.java
,加入@SpringBootApplication 注解
package com.tsccg;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
2)在resources目录下创建static
、templates
文件夹,springboot核心配置文件application.properties
3)创建测试类ApplicationTests.java
,加入@SpringBootTest注解
package com.tsccg;
import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;
@SpringBootTest
class ApplicationTests {
@Test
void contextLoads() {
}
}
在Spring Boot项目中,使用SpringMVC时,不需要提前在配置文件中进行配置,直接使用就行。
步骤:
①基于前面创建的Spring Boot项目,我们直接写一个Controller类:HelloController
②启动Application类的main方法
可以发现内嵌的Tomcat已启动,默认为8080端口。
③在浏览器访问 http://localhost:8080/hello
启动类Application上的@SpringBootApplication注解是Spring Boot项目的重要注解。
其为一个复合注解,内部主要包含@SpringBootConfiguration、@EnableAutoConfiguration、@ComponentScan三个注解:
Spring Boot 的核心配置文件用于配置 Spring Boot 程序。
名字必须以 application
开始,后缀有两种格式:
.properties
:
student.name=张三
student.age=21
.yml
/.yaml
:
#属性与上级属性之间留两个空格,值与前面的冒号之间必须留一个空格
student:
name: 张三
age: 21
.properties
文件(默认)基于前面2.3的web例子进行修改。
①修改application.properties属性配置文件,设置Tomcat启动时开放的端口号以及上下文路径
application.properties:
#设置端口号
server.port=8082
#设置上下文路径
server.servlet.context-path=/boot
②启动应用:
③在浏览器访问 http://localhost:8082/boot/hello
.yml
文件(推荐)同基于前面2.3的web例子进行修改。
①对原有的application.properties文件进行删除或修改文件名称
若两种格式的文件同时存在,则优先用application.properties
②在resource目录下创建一个application.yml文件,在其中设置端口号和上下文路径
#设置端口号与上下文路径
#属性与上级属性之间留两个空格,值与前面的冒号之间留一个空格
server:
port: 8083
servlet:
context-path: /boot2
③启动应用
若配置未生效则用maven执行clean–>install操作。
④在浏览器访问 http://localhost:8083/boot2/hello
在实际开发的过程中,我们的项目会经历很多的阶段(开发->测试->上线),每个阶段的配置也会不同。例如:端口、上下文路径、数据库等。
为了方便在不同的环境之间切换,SpringBoot 提供了多环境配置,具体操作如下:
基于2.3的web项目进行修改。
①分别为开发、测试、生产环境创建一个配置文件
命名必须以application-自定义环境标识.properties|yml
为准
②在application.yml中指定使用哪个环境的配置,如下:
启动应用,在浏览器访问 http://localhost:9081/dev/hello
③修改application.yml,指定为测试环境
重启应用,在浏览器中访问 http://localhost:9082/test/hello
SpringBoot 的核心配置文件中,除了使用内置的配置项之外,我们还可以添加自定义配置项,然后采用@Value或@ConfigurationProperties读取配置项的属性。
用法:@Value("${key}") , key 来自 application.properties(yml)
例子:基于2.3web案例进行修改
①在application.properties核心配置文件中加入内置配置项和自定义配置项
#内置配置项
server.port=8081
server.servlet.context-path=/read
#自定义配置项
student.name=张三
student.age=18
wite=www.xxx.com
②修改HelloController
1)添加私有属性并用@Value注解读取application.properties文件的数据进行注入
2)添加处理器方法将属性响应到浏览器
@RestController
public class HelloController {
@Value("${server.port}")
private String port;
@Value("${student.name}")
private String name;
@Value("${student.age}")
private Integer age;
@Value("${wite}")
private String wite;
@RequestMapping("/data")
public String readData() {
return name + "由于年龄未到" + age + ",所以不能从" + port + "端口访问" + wite;
}
}
③启动应用,在浏览器访问 http://localhost:8081/read/data
@ConfigurationProperties:可以把配置文件中的数据映射为java对象,适用于自定义配置项较多的情况。用在类上或配置类方法上。
属性:prefix,用于匹配配置文件中某些配置项开头的内容,如:指定prefix为student,那么就会匹配student.name、student.age等以student开头的配置项。
prefix可以不指定,如果不指定,那么会去配置文件中寻找与该类的属性名一致的配置项,prefix的作用是区分同名配置。
案例演示:(基于上一个例子)
①创建一个java类Student
1)使用@Component注解创建对象并注入容器
2)使用@ConfigurationProperties注解从配置文件中读取配置数据为该类注入属性
package com.tsccg.pojo;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
@Component
@ConfigurationProperties(prefix = "student")
public class Student {
private String name;
private Integer age;
//get set
//toString
}
使用ConfigurationProperties 注解,IDEA 会出现一个警告,但是不影响程序的执行。在pom中加入如下依赖后,重启项目即可消除。
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-configuration-processorartifactId>
<optional>trueoptional>
dependency>
②创建StudentController类
@RestController
public class StudentController {
@Resource//自动注入
private Student student;
@RequestMapping("/student")
public String readStudent() {
return student.toString();
}
}
③开启应用,在浏览器访问http://localhost:8081/read/student
Spring Boot默认不支持JSP,而是使用模板技术代替jsp。
若要使用jsp需要进行以下配置:
①添加依赖
<dependency>
<groupId>org.apache.tomcat.embedgroupId>
<artifactId>tomcat-embed-jasperartifactId>
dependency>
<dependency>
<groupId>javax.servletgroupId>
<artifactId>javax.servlet-apiartifactId>
dependency>
<dependency>
<groupId>javax.servlet.jspgroupId>
<artifactId>javax.servlet.jsp-apiartifactId>
<version>2.3.1version>
dependency>
<dependency>
<groupId>javax.servletgroupId>
<artifactId>jstlartifactId>
dependency>
②指定jsp文件编译后的存放目录
SpringBoot 要求 jsp 文件必须编译到指定的 META-INF/resources 目录下才能访问,否则访问不到。
在pom.xml的build标签配置如下信息
<resources>
<resource>
<directory>src/main/webappdirectory>
<targetPath>META-INF/resourcestargetPath>
<includes>
<include>**/*.*include>
includes>
resource>
<resource>
<directory>src/main/resourcesdirectory>
<includes>
<include>**/*.*include>
includes>
resource>
resources>
③在src/main/目录下创建存放jsp文件的目录:webapp ,并在项目中指定为Web Resource Directory,创建一个jsp文件index.jsp
④在index.jsp中获取请求作用域的数据
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
Title
${data}
⑤在application.properties配置文件中配置SpringMVC中的视图解析器
server.port=9090
#视图前缀
spring.mvc.view.prefix=/
#视图后缀
spring.mvc.view.suffix=.jsp
⑥创建JspController,返回视图
package com.tsccg.controller;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class JspController {
@RequestMapping("/doSome")
public String doSome(Model model) {
//向请求作用域中放入数据
model.addAttribute("data","Spring Boot整合Jsp");
return "index";
}
}
⑦开启应用,访问 http://localhost:9090/doSome
我们点进启动类中SpringApplication的run方法,发现run方法中返回了一个ConfigurationApplicationContext类型对象,继续点开ConfigurationApplicationContext,发现是一个接口,继承了ApplicationContext。
ApplicationContext为Spring的容器对象,通过该对象可以直接获取容器中的Bean对象。
当我们在不想启动整个项目的前提下测试部分代码时,可以通过main方法中的SpringApplication.run()语句获取返回的Spring容器对象,获取业务bean进行调用。
演示:
①创建业务接口 HelloService
package com.tsccg.service;
public interface HelloService {
void sayHello(String name);
}
②创建业务接口实现类 HelloServiceImpl
package com.tsccg.service.impl;
import com.tsccg.service.HelloService;
import org.springframework.stereotype.Service;
@Service(value = "helloService")
public class HelloServiceImpl implements HelloService {
@Override
public void sayHello(String name) {
System.out.println("Hello " + name);
}
}
③在启动类main方法中,获取容器对象,取出业务bean对象调用其方法
@SpringBootApplication
public class Application {
public static void main(String[] args) {
//获取容器对象
ConfigurableApplicationContext app = SpringApplication.run(Application.class, args);
//获取业务bean对象
HelloService helloService = (HelloService) app.getBean("helloService");
//调用方法
helloService.sayHello("张三");
}
}
④启动应用
开发中可能会有这样的情景:需要在容器启动后执行一些内容,比如读取配置文件,数据库连接之类的。SpringBoot 给我们提供了两个接口来帮助我们实现这种需求,使用任意一个都可以
它们的执行时机为容器启动完成的时候,这两个接口中都有一个 run 抽象方法,我们只需要实现这个方法即可。这两个接口的不同之处在于 :
@FunctionalInterface
public interface CommandLineRunner {
void run(String... args) throws Exception;
}
@FunctionalInterface
public interface ApplicationRunner {
void run(ApplicationArguments args) throws Exception;
}
演示使用:
以2.7中的例子为基础,进行修改。
①修改启动类
使启动类实现CommandLineRunner接口,实现其run方法
@SpringBootApplication
public class Application implements CommandLineRunner {
@Resource
private HelloService helloService;
public static void main(String[] args) {
System.out.println("准备创建容器对象");
SpringApplication.run(Application.class, args);
System.out.println("创建容器对象后");
}
@Override
public void run(String... args) throws Exception {
System.out.println("容器对象创建好后,执行的方法");
String result = helloService.sayHello("李四");
System.out.println("调用容器对象中的方法:" + result);
}
}
②开启应用
三个内容:
拦截器是SpringMVC中的一种对象,能够拦截对Controller的请求,实现对请求的预先处理。
①自定义拦截器,实现HandlerInterceptor接口
public interface HandlerInterceptor {
default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
return true;
}
default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
}
default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
}
}
②在SpringMVC配置文件中注册拦截器类
<mvc:interceptors>
<mvc:interceptor>
<mvc:mapping path="拦截的url" />
<bean class="拦截器类全限定名称"/>
mvc:interceptor>
mvc:interceptors>
在Spring Boot中使用拦截器与SpringMVC中使用的步骤大体一致,都是先自定义拦截器,然后将其注册到项目中。
只不过在Spring Boot中要把拦截器注册到@Configuration修饰的配置类中。
具体步骤:
①自定义拦截器
创建java类实现 HandlerInterceptor 接口,实现preHandle方法
package com.tsccg.handlerInterceptor;
import org.springframework.web.servlet.HandlerInterceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class MyLoginInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("执行了自定义拦截器的preHandle方法");
return true;
}
}
②注册拦截器
package com.tsccg.config;
import com.tsccg.handlerInterceptor.MyLoginInterceptor;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
/**
* 相当于SpringMVC配置文件
*/
@Configuration
public class MyAppConfig implements WebMvcConfigurer {
/**
* 注册拦截器
* @param registry 登记系统中可以使用的拦截器对象
*/
@Override
public void addInterceptors(InterceptorRegistry registry) {
//拦截的url
String path = "/user/**";
//放行的url
String excludePath = "/user/login";
registry.addInterceptor(new MyLoginInterceptor())
.addPathPatterns(path).excludePathPatterns(excludePath);
}
}
③创建测试用的Controller
@RestController
public class UserController {
@RequestMapping("/user/account")
public String account() {
return "10000";
}
@RequestMapping("/user/login")
public String login() {
return "登录界面";
}
}
④启动应用
1)通过浏览器访问受拦截的url: http://localhost:8080/user/account
可见,在发送请求后,后台执行了自定义的拦截器方法
2)通过浏览器访问放行的url: http://localhost:8080/user/login
可见,在发送请求后,后台没有执行拦截器方法
ServletRegistrationBean用来注册Servlet对象
使用步骤:
①创建Servlet
public class MyServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
resp.setContentType("text/html;charset=utf-8");
PrintWriter out = resp.getWriter();
out.print("使用Servlet对象");
out.flush();
out.close();
}
}
②注册Servlet
@Configuration
public class MyAppConfig{
/**
* 注册Servlet
* @return
*/
@Bean
public ServletRegistrationBean servletRegistrationBean() {
//ServletRegistrationBean reg = new ServletRegistrationBean(new MyServlet(),"/myServlet");
ServletRegistrationBean reg = new ServletRegistrationBean();
//注册Servlet对象
reg.setServlet(new MyServlet());
//设置请求路径
reg.addUrlMappings("/myServlet");
return reg;
}
}
③启动应用,在浏览器中访问 http://localhost:8080/myServlet
FilterRegistrationBean 用来注册 Filter 对象
使用步骤:
①自定义过滤器,实现javax.servlet.Filter接口
public class MyFilter implements Filter {
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
System.out.println("执行了自定义过滤器,方法:doFilter");
chain.doFilter(request,response);
}
}
②注册过滤器
@Configuration
public class MyAppConfig{
/**
* 注册过滤器对象
* @return
*/
@Bean
public FilterRegistrationBean filterRegistrationBean() {
FilterRegistrationBean bean = new FilterRegistrationBean();
//注册自定义过滤器对象
bean.setFilter(new MyFilter());
//设置过滤的url
bean.addUrlPatterns("/user/*");
return bean;
}
}
③创建Controller
@RestController
public class MyController {
@RequestMapping("/user/account")
public String userAccount() {
return "过滤器使用测试";
}
@RequestMapping("/member/account")
public String memberAccount() {
return "过滤器使用测试2";
}
}
④启动应用
1)访问过滤器指定范围内的地址: http://localhost:8080/user/account
2)访问过滤器指定范围外的地址: http://localhost:8080/member/account
CharacterEncodingFilter是框架提供的字符集过滤器,解决post方式请求中文字符乱码的问题。
在通过SpringMVC框架使用该过滤器时,需要在web.xml中注册该过滤器,配置其属性:
<filter>
<filter-name>characterEncodingFilterfilter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilterfilter-class>
<init-param>
<param-name>encodingparam-name>
<param-value>utf-8param-value>
init-param>
<init-param>
<param-name>forceRequestEncodingparam-name>
<param-value>trueparam-value>
init-param>
<init-param>
<param-name>forceResponseEncodingparam-name>
<param-value>trueparam-value>
init-param>
filter>
<filter-mapping>
<filter-name>characterEncodingFilterfilter-name>
<url-pattern>/*url-pattern>
filter-mapping>
使用的方式有两种:
1.在配置类中注册
2.在Spring Boot核心配置文件中设置
步骤:
①创建Servlet,在不设置utf-8的情况下响应中文字符
public class MyServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doPost(req,resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
resp.setContentType("text/html");//不设置utf-8字符集
PrintWriter out = resp.getWriter();
out.print("====中文测试数据====");//响应中文字符
out.flush();
out.close();
}
}
②注册Servlet
@Configuration
public class MyAppConfig{
/**
* 注册Servlet
* @return
*/
@Bean
public ServletRegistrationBean servletRegistrationBean() {
ServletRegistrationBean bean =
new ServletRegistrationBean(new MyServlet(),"/user/inf");
return bean;
}
}
③开启应用,在浏览器访问 http://localhost:8080/user/inf
可见,响应的中文字符发生乱码。
④在配置类中注册字符集过滤器
@Configuration
public class MyAppConfig{
/**
* 注册Servlet
* @return
*/
@Bean
public ServletRegistrationBean servletRegistrationBean() {
ServletRegistrationBean bean =
new ServletRegistrationBean(new MyServlet(),"/user/inf");
return bean;
}
/**
* 注册过滤器
* @return
*/
@Bean
public FilterRegistrationBean filterRegistrationBean() {
FilterRegistrationBean bean = new FilterRegistrationBean();
//创建框架提供的字符集过滤器类
CharacterEncodingFilter filter = new CharacterEncodingFilter();
filter.setEncoding("utf-8");//设置encoding属性为utf-8
filter.setForceEncoding(true);//设置请求对象和响应对象的字符编码集与encoding属性一致
bean.setFilter(filter);//注册字符集过滤器
bean.addUrlPatterns("/user/*");//设置过滤的url
return bean;
}
}
⑤在application.properties中添加如下配置
server.servlet.encoding.enabled=false
⑥重启应用,重新访问
Spring Boot 项目默认启用了 CharacterEncodingFilter, 直接在application.properties中设置他的属性就可以:
#设置 spring boot 中 CharacterEncodingFitler 的属性值
server.servlet.encoding.enabled=true
server.servlet.encoding.charset=utf-8
#强制 request, response 使用 charset 他的值 utf-8
server.servlet.encoding.force=true
重启应用,重新访问:
对象关系映射(Object Relational Mapping,简称ORM),是一种程序设计技术,用于实现面向对象程序语言里不同类型系统的数据之间的转换。
MyBatis就是ORM的一种,下面将展示在Spring Boot项目中使用MyBatis操作MySQL数据库。
建表:
步骤分析:
其中,创建Dao代理对象的方式有两种:
①创建Spring Boot项目,勾选Web、MyBatis、MySQL Driver起步依赖
②在application.properties中配置数据库连接信息
#项目端口号
server.port=9090
#数据库连接信息
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/db_mybatis?useUnicode=true&characterEncoding=UTF-8&serverTimezone=GMT%2B8
spring.datasource.username=root
spring.datasource.password=123456
③创建Student实体类
package com.tsccg.pojo;
public class Student {
private Integer id;
private String name;
private String email;
private Integer age;
//get set
//toString
}
④创建Controller
package com.tsccg.controller;
@RestController
public class StudentController {
@Resource
private StudentService studentService;
@RequestMapping("/find")
public String findStudent(Integer id) {
Student student = studentService.findById(id);
return student.toString();
}
}
⑤创建Service
StudentService接口:
package com.tsccg.service;
import com.tsccg.pojo.Student;
public interface StudentService {
Student findById(Integer id);
}
接口实现类:
package com.tsccg.service.impl;
import javax.annotation.Resource;
@Service
public class StudentServiceImpl implements StudentService {
@Resource
private StudentDao studentDao;
@Override
public Student findById(Integer id) {
return studentDao.findById(id);
}
}
⑥创建Dao
StudentDao接口:
package com.tsccg.dao;
import com.tsccg.pojo.Student;
import org.apache.ibatis.annotations.Mapper;
@Mapper//告诉MyBatis这是dao接口,创建此接口的代理对象。
public interface StudentDao {
Student findById(Integer id);
}
在同级目录下创建StudentDao.xml
DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.tsccg.dao.StudentDao">
<select id="findById" parameterType="int" resultType="com.tsccg.pojo.Student">
select id,name,email,age from t_student where id = #{id}
select>
mapper>
⑦由于是在src/main/java目录下创建的mapper映射文件,故需要在pom.xml中指定把src/main/java目录中的xml文件包含到classpath中
在build标签内添加如下语句:
<resources>
<resource>
<directory>src/main/javadirectory>
<includes>
<include>**/*.xmlinclude>
includes>
resource>
resources>
⑧开启应用,在浏览器访问 http://localhost:9090/find?id=1001
第一种方式需要在每一个Dao接口上都加@Mapper,当Dao接口较多时不方便。
而这种方式只需要在启动类上添加@MapperScan(basePackages = “com.tsccg.dao”)即可。
@SpringBootApplication
@MapperScan(basePackages = "com.tsccg.dao")
//@MapperScan(basePackages = {"com.tsccg.dao","com.tsccg.dao2"})
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
我们在项目中更偏向于将mapper文件与java代码分开管理,就是将mapper文件都放在src/main/resources目录下,将java代码都放在src/main/java目录下。
有两种分离方式:
在resources目录下创建com.tsccg.dao目录,将mapper文件都放进去。
这种分离方式可以在项目编译后,将mapper文件与StudentDao.class文件放在一起,如下:
步骤:
①在resources目录下创建com.tsccg.dao目录,将mapper文件移动至该目录下。
注意,在resources目录下创建com.tsccg.dao目录时,必须用/
表示分层,如下:
不然会将com.tsccg.dao当作一个目录名,编译后不会将mapper文件与StudentDao.class放在一起。
②在pom.xml中注释掉原先设置的resources标签,不然会编译报错
③重启应用,通过浏览器重新访问
第二种方式可以告诉程序从什么位置找到mapper文件,无需让mapper文件与编译后的StudentDao.class位于同级目录。
步骤:
①在resources目录下创建自定义的子目录,如mapper,然后将mapper文件放入。
②在application.properties核心配置文件中指定mapper文件所在位置
#指定mapper文件的位置
mybatis.mapper-locations=classpath:mapper/*.xml
#指定使用mybatis的日志
mybatis.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl
③同样需要在pom.xml中注释掉原先设置的resources标签,不然会编译报错
④重启应用,重新访问地址
在Spring Boot中使用事务很简单,底层用的还是Spring提供的事务管理。
使用步骤:
@EnableTransactionManagement
注解开启事务支持(默认开启,但最好添上)@Transactional
注解即可实例演示:
以4.1中的例子为基础进行修改。
①分别在入口类上和Service接口实现类上添加事务注解
②在Controller里添加删除方法
使用try…catch语句监控Service中是否抛出异常,响应相应信息。
@RestController
public class StudentController {
@Resource
private StudentService studentService;
@RequestMapping("/delete")
public String deleteStudentById(Integer id) {
try {
//通过id删除学生信息
studentService.deleteById(id);
return "删除成功";
} catch (Exception e) {
e.printStackTrace();
return "删除失败";
}
}
}
③在Service接口中添加删除方法并在实现类中实现
StudentService:
public interface StudentService {
//通过id删除学生信息
void deleteById(Integer id);
}
StudentServiceImpl:
@Service
@Transactional//开启事务
public class StudentServiceImpl implements StudentService {
@Resource
private StudentDao studentDao;
@Override
public void deleteById(Integer id) {
studentDao.deleteById(id);//调用Dao删除数据
int a = 10 / 0;//抛出运行时异常
}
}
④在Dao接口中定义删除方法并在Mapper文件中添加对应sql语句
StudentDao:
public interface StudentDao {
void deleteById(Integer id);
}
StudentDao.xml:
DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.tsccg.dao.StudentDao">
<delete id="deleteById" parameterType="int">
delete from t_student where id = #{id}
delete>
mapper>
⑤测试
开启应用,通过浏览器访问 http://localhost:9090/delete?id=1006
REST(Representational State Transfer),表现层资源状态转移。
REST是一种互联网软件架构设计的风格,并不是标准,可用也可不用。它只是提出了一组客户端与服务器交互时的架构理念和设计原则,基于这种理念和原则设计的接口可以更简洁,更有层次。说白了,就是一种统一的url命名格式,将CRUD操作的url命名规范化,统一化。
表现层资源状态转移 概念说明:
我们过去访问一个资源所用的url五花八门,如访问一个用户信息:
http://localhost:8080/findUserById?id=1001 GET //查询一个用户信息
http://localhost:8080/addUser POST //添加用户信息
http://localhost:8080/updateUser POST //更新用户信息
http://localhost:8080/deleteUserById?id=1001 GET //删除一个用户信息
以上这些url所操作的都是同一个资源,在url内就写明了对该资源的操作。
而REST是面向资源的,资源是通过url进行暴露的。REST中,url的设计只需要把资源通过合理的方式暴露出来即可,对资源的操作与url无关,操作是通过HTTP动词来体现的。
HTTP协议中,GET、POST、DELETE、PUT都是表示操作方式的动词。
它们分别对应四种基本操作:
REST风格提倡url地址使用统一的风格设计,用名词表示资源,以及访问资源的信息,在url中,使用/
分隔对资源的访问信息。
修改上面的url为REST风格:
http://localhost:8080/user/1001 GET //查询一个用户信息
http://localhost:8080/user POST //添加用户信息
http://localhost:8080/user/1001 DELETE //删除一个用户信息
http://localhost:8080/user PUT //更新用户信息
现在问题有两个问题:
在SpringMVC中 有一个过滤器,支持将POST请求转换为DELETE、PUT请求。
过滤器:org.springframework.web.filter.HiddenHttpMethodFilter
核心方法:
从过滤器方法中得出,我们可以在页面上用表单方式发送POST请求,在携带的请求参数中添加一个名为_method
的参数,值为DELETE
或PUT
。
如下:
<form action="/user" method="POST">
id:<input type="text" name="id"><br/>
姓名:<input type="text" name="name"><br/>
<input type="hidden" name="_method" value="PUT"><br/>
<input type="submit" value="更新">
form>
然后在项目中注册该过滤器即可将POST请求转换为PUT请求。
在application.properties中注册HiddenHttpMethodFilter过滤器:
spring.mvc.hiddenmethod.filter.enabled=true
此外,我们也可以通过ajax发送DELETE或PUT请求,但只有部分浏览器支持。
在Spring Boot中开发RESTful主要由如下几个注解实现
① @PathVariable:获取拼接到url中的参数数据,是实现RESTful最主要的一个注解
② @GetMapping:接收和处理GET方式的请求,等同于 @RequestMapping(method=RequestMethod.GET)
③ @PostMapping:接收和处理POST方式的请求,等同于 @RequestMapping(method=RequestMethod.POST)
④ @DeleteMapping:接收和处理DELETE方式的请求,等同于 @RequestMapping(method=RequestMethod.DELETE)
⑤ @PutMapping:接收和处理PUT方式的请求,等同于 @RequestMapping(method=RequestMethod.PUT)
以4.4中的例子为基础进行修改。
①在application.properties中注册HiddenHttpMethodFilter过滤器:
#设置端口号
server.port=9090
#注册HiddenHttpMethodFilter过滤器
spring.mvc.hiddenmethod.filter.enabled=true
②编写前端页面
在resources/static目录下新建index.html,发送crud四种请求
DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Titletitle>
head>
<body>
<div id="app">
<h3>查询h3>
<a href="/student/1001">查询a>
<hr>
<h3>删除h3>
<form action="/student/1007" method="POST">
<input type="hidden" name="_method" value="DELETE"><br>
<input type="submit" value="删除"><br/>
form>
<hr>
<h3>添加h3>
<form action="/student" method="POST">
id:<input type="text" name="id"><br/>
姓名:<input type="text" name="name"><br/>
<input type="submit" value="添加"><br/>
form>
<hr>
<h3>更新h3>
<form action="/student" method="POST">
id:<input type="text" name="id"><br/>
姓名:<input type="text" name="name"><br/>
<input type="hidden" name="_method" value="PUT"><br/>
<input type="submit" value="更新"><br/>
form>
div>
body>
html>
③编写Controller
package com.tsccg.controller;
@RestController
public class StudentController {
/**
* 根据id获取学生信息
* @PathVariable
* 1.作用:获取url中的数据
* 2.位置:处理器形参前
* 3.value:路径变量值 {studentId}
*/
@GetMapping("/student/{studentId}")//处理GET请求
public String findStudent(@PathVariable(value="studentId") Integer id) {
return "执行查询操作,id="+id;
}
/**
* 添加学生
*/
@PostMapping("/student")//处理POST请求
public String addStudent(@RequestParam Map<String,String> student) {
return "执行添加操作,student="+student;
}
/**
* 根据id删除学生信息
*/
@DeleteMapping("/student/{studentId}")//处理DELETE请求
public String deleteStudent(@PathVariable("studentId") Integer id) {
return "执行删除操作,id="+id;
}
/**
* 更新学生信息
*/
@PutMapping("/student")//处理PUT请求
public String updateStudent(@RequestParam Map<String,String> student) {
return "执行更新操作,student="+student;
}
}
④测试
开启应用,从浏览器访问 http://localhost:9090/index.html
在REST中,必须保证URL+请求方式是唯一的,若出现如下情况,会报错。
@GetMapping("/student/{studentId}")
public String findStudentById(@PathVariable(value="studentId") Integer id) {
return "根据id查询学生信息";
}
@GetMapping("/student/{studentName}")
public String findStudentByName(@PathVariable(value="studentName") String name) {
return "根据姓名查询学生信息";
}
Redis是一个NoSQL数据库,常用作缓存使用。通过Redis客户端可以使用多种语言在程序中访问Redis数据。其中,java语言使用的客户端库有:Jedis、Lettuce、Redisson等。
那么在Spring Boot中,使用的Redis客户端库是什么呢?
创建一个Spring Boot项目,勾选Web和Redis起步依赖:
查看项目导入的Redis相关依赖:
可以看出,在Spring Boot中,默认使用的Redis客户端库为lettuce
①创建Spring Boot项目,勾选web和redis起步依赖
其中,Spring Boot会根据redis的起步依赖在容器中创建两个对象:
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-data-redisartifactId>
dependency>
在程序中使用RedisTemplate类的方法 操作redis数据, 实际就是调用的lettuce 客户端中的方法
②在核心配置文件application.properties中配置连接redis信息
#配置端口号
server.port=9090
#配置redis
spring.redis.host=localhost
spring.redis.port=6379
#spring.redis.password=123
③创建Controller
注入RedisTemplate对象,通过该对象的以ops
开头的几个方法获取操作redis中各种类型数据的对象
如:
然后就可以通过获取的对象执行set/get方法,管理redis中的数据了。
package com.tsccg.controller;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
@RestController
public class RedisController {
//注入RedisTemplate对象
@Resource
private RedisTemplate redisTemplate;
//向redis中添加String类型数据
@PostMapping("/student/{name}")
public String setKey(@PathVariable String name) {
//获取管理redis中String类型的对象
ValueOperations valueOperations = redisTemplate.opsForValue();
//执行添加操作
valueOperations.set("name",name);
return "添加了学生:"+name;
}
//从redis中获取添加的数据
@GetMapping("/student")
public String getValue() {
//获取管理redis中String类型的对象
ValueOperations valueOperations = redisTemplate.opsForValue();
//执行获取操作
return (String)valueOperations.get("name");
}
}
④测试
1)开启windows版redis服务
2)开启项目服务,通过postman客户端软件,以POST方式发送: http://localhost:9090/student/小明
3)再以GET方式发送请求:http://localhost:9090/student
4)通过Redis Desktop Manager桌面工具查看刚刚插入的数据
发现在redis中添加的数据为序列化的数据。
⑤修改Controller,注入StringRedisTemplate对象
package com.tsccg.controller;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
@RestController
public class RedisController {
//修改注入StringRedisTemplate对象
@Resource
private StringRedisTemplate stringRedisTemplate;
//修改添加的数据为age
@PostMapping("/student/{age}")
public String setKey(@PathVariable String age) {
//通过StringRedisTemplate对象获取操作Stirng类型数据的对象
ValueOperations valueOperations = stringRedisTemplate.opsForValue();
valueOperations.set("age",age);
return "添加了年龄:"+age;
}
//修改获取的数据为age
@GetMapping("/student")
public String getValue() {
ValueOperations valueOperations = stringRedisTemplate.opsForValue();
return (String)valueOperations.get("age");
}
}
⑥重新测试
重启应用,重新发送添加请求:
再次查看redis库中存入的数据:
发现这次在redis中存入的数据是正常的。
RedisTemplate:把key和value经过序列化存到redis中,key和value是序列化的内容,不能直接识别。默认使用的是jdk的序列化方式,可以修改为其它的系列化方式。
StringRedisTemplate:把key和value作为String处理,使用的是String的序列化,可读性好。
序列化与反序列化:
为什么要进行序列化?
我们在实际项目开发中,使用的redis都是放在linux上的,而为了让数据对象可以从其它地方跨平台存放到linux系统上去,就必须将对象序列化。
序列化最终的目的就是为了让对象可以跨平台存储,可以通过网络传输。而我们进行跨平台存储和网络传输的方式就是IO,IO支持的数据格式就是字节数组。我们必须在把对象转换为字节数组前就指定一种规则(序列化),那么我们从IO流读取数据的时候再以这种规则把对象还原。(反序列化)
序列化的常见方式:
序列化只是一种拆装组装对象的规则,这种规则也多种多样。比如现在常用的序列化方式有:JDK(不支持跨语言)、JSON、XML、Hessian、Kryo(不支持跨语言)、Thrift、Protofbuff 等。
jdk的序列化: 把java对象转为byte[], 二进制数据
json序列化:json序列化能将对象转换为 JSON 格式或从 JSON 格式转换为对象。例如把一个Student对象转换为JSON字符串{“name”:“李四”, “age”:29} ),反序列化(将JSON字符串 {“name”:“李四”, “age”:29} 转换为Student对象)
Redis数据序列化方式有:
其中,默认的序列化方式为jdk的序列化,将key和value转换为二进制字节数组。
①修改Controller
@RestController
public class RedisController {
@Resource
private RedisTemplate redisTemplate;
@PostMapping("/student/{key}/{value}")
public String setKey(@PathVariable String key,@PathVariable String value) {
// 使用RedisTemplate ,在存取值之前,设置序列化
//设置key的序列化方式为String
redisTemplate.setKeySerializer(new StringRedisSerializer());
//设置value的序列化方式为String
redisTemplate.setValueSerializer(new StringRedisSerializer());
ValueOperations valueOperations = redisTemplate.opsForValue();
valueOperations.set(key,value);
return "添加:" + "key=" + key + ",value=" + value;
}
@GetMapping("/student/{key}")
public String getValue(@PathVariable String key) {
ValueOperations valueOperations = redisTemplate.opsForValue();
return (String)valueOperations.get(key);
}
}
②发送POST请求:http://localhost:9090/student/email/[email protected]
③查看redis库:
①设置Idea自动生成序列化版本号
②创建实体类,实现序列化接口,在实体类中自动生成序列化版本号
③修改Controller,设置value为JSON序列化方式
@Resource
private RedisTemplate redisTemplate;
@PostMapping("/student")
public String addJson() {
//创建一个Student对象
Student student = new Student();
student.setName("Tom");
student.setAge(40);
student.setEmail("[email protected]");
//设置key的序列化方式为String
redisTemplate.setKeySerializer(new StringRedisSerializer());
//设置value的序列化方式为JSON
redisTemplate.setValueSerializer(new Jackson2JsonRedisSerializer(Student.class));
//添加操作
redisTemplate.opsForValue().set("myStudent",student);
return "添加:"+student.toString();
}
@GetMapping("/student")
public String getValue() {
//设置key的序列化方式为String
redisTemplate.setKeySerializer(new StringRedisSerializer());
//设置value的序列化方式为JSON
redisTemplate.setValueSerializer(new Jackson2JsonRedisSerializer(Student.class));
ValueOperations valueOperations = redisTemplate.opsForValue();
return valueOperations.get("myStudent").toString();
}
④发送post请求: http://localhost:9090/student (序列化)
⑤查看redis库
⑥发送get请求: http://localhost:9090/student 反序列化
创建一个普通maven模块作为父模块,模块名:16-dubbo-parent
进行如下操作:
1)删除src目录
2)修改pom.xml,指定打包方式为pom
3)继承spring-boot-starter-parent模块
4)添加dubbo和zookeeper起步依赖
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.6.1version>
<relativePath/>
parent>
<groupId>com.tsccggroupId>
<artifactId>16-dubbo-parentartifactId>
<version>0.0.1-SNAPSHOTversion>
<packaging>pompackaging>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.apache.dubbogroupId>
<artifactId>dubbo-spring-boot-starterartifactId>
<version>2.7.8version>
dependency>
<dependency>
<groupId>org.apache.dubbogroupId>
<artifactId>dubbo-dependencies-zookeeperartifactId>
<version>2.7.8version>
<type>pomtype>
<exclusions>
<exclusion>
<groupId>org.slf4jgroupId>
<artifactId>slf4j-log4j12artifactId>
exclusion>
exclusions>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
创建一个普通maven模块,无父模块,在此模块中只定义公共的接口和实体类。
模块名:common-interface
GAV坐标:
<groupId>com.tsccggroupId>
<artifactId>common-interfaceartifactId>
<version>0.0.1-SNAPSHOTversion>
创建实体类Student,实现序列化接口
package com.tsccg.pojo;
import java.io.Serializable;
public class Student implements Serializable {
private String name;
private Integer age;
private String email;
//get set
//toString
}
创建公共接口 StudentService,定义方法
package com.tsccg.pojo.com.tsccg.service;
import com.tsccg.pojo.Student;
public interface StudentService {
//获取Studnet数据
Student getStudent();
}
创建普通maven模块:server-consumer,继承父模块 16-dubbo-parent
然后进行如下操作:
①在pom.xml中添加依赖
1)声明Spring Boot的web起步依赖
2)添加公共接口模块依赖
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>com.tsccggroupId>
<artifactId>common-interfaceartifactId>
<version>0.0.1-SNAPSHOTversion>
dependency>
dependencies>
②在resources目录下创建application.properties核心配置文件,配置dubbo
#服务暴露接口
server.port=8081
##配置dubbo
#服务名称
spring.application.name=server-consumer
#扫描dubbo注解所在包
dubbo.scan.base-packages=com.tsccg.service
#指定注册中心地址,此处用的是本地的zookeeper
dubbo.registry.address=zookeeper://localhost:2181
③在java目录下创建com.tsccg.Application 启动类
添加开启Dubbo的注解:@EnableDubbo
package com.tsccg;
import org.apache.dubbo.config.spring.context.annotation.EnableDubbo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
@EnableDubbo//开启dubbo
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class,args);
}
}
④创建Controller
使用@DubboReference注解远程注入StudentService对象
package com.tsccg.controller;
import com.tsccg.pojo.Student;
import com.tsccg.pojo.com.tsccg.service.StudentService;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class StudentController {
@DubboReference(version = "1.0")//dubbo远程注入
private StudentService studentService;
@GetMapping("/student")
public String getStudent() {
//调用服务方法
Student student = studentService.getStudent();
return student.toString();
}
}
同服务消费者,创建一个普通maven模块:server-provider,继承父模块
进行如下操作:
①添加依赖
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>com.tsccggroupId>
<artifactId>common-interfaceartifactId>
<version>0.0.1-SNAPSHOTversion>
dependency>
dependencies>
②创建核心配置文件:application.properties,配置dubbo
#暴露服务接口
server.port=8080
##配置dubbo
#服务名称
spring.application.name=server-provider
#扫描dubbo注解所在包
dubbo.scan.base-packages=com.tsccg.service
#指定注册中心地址
dubbo.registry.address=zookeeper://localhost:2181
③创建启动类:Application,添加开启dubbo注解
package com.tsccg;
import org.apache.dubbo.config.spring.context.annotation.EnableDubbo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
@EnableDubbo//开启dubbo
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
④创建服务实现类
package com.tsccg.service.impl;
import com.tsccg.pojo.Student;
import com.tsccg.pojo.com.tsccg.service.StudentService;
import org.apache.dubbo.config.annotation.DubboService;
//使用Dubbo提供的@DubboService注解,指定接口class为StudentService.class
@DubboService(interfaceClass = StudentService.class,version = "1.0")
public class StudentServiceImpl implements StudentService{
@Override
public Student getStudent() {
//创建一个Student对象
Student student = new Student();
student.setName("杰瑞");
student.setAge(30);
student.setEmail("[email protected]");
return student;
}
}
①开启zookeeper
②先后运行服务提供者和服务消费者应用
③在浏览器中发送请求: http://localhost:8081/student
Spring Boot 可以打包为 war 或 jar 文件。 以两种方式发布应用。
步骤:
1.创建一个Spring Boot项目,添加Web起步依赖
2.修改pom.xml
1)添加内嵌 Tomcat 对 jsp 的解析包依赖
<dependency>
<groupId>org.apache.tomcat.embedgroupId>
<artifactId>tomcat-embed-jasperartifactId>
dependency>
2)指定jsp编译目录
<build>
<resources>
<resource>
<directory>src/main/webappdirectory>
<targetPath>META-INF/resourcestargetPath>
<includes>
<include>**/*.*include>
includes>
resource>
<resource>
<directory>src/main/resourcesdirectory>
<includes>
<include>**/*.*include>
includes>
resource>
resources>
build>
3)指定打包方式为war
4)指定打包后生成war包的名称
在build标签内添加如下语句:
<finalName>myBootfinalName>
5)完整的pom.xml内容
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.6.1version>
<relativePath/>
parent>
<groupId>com.tsccggroupId>
<artifactId>17-package-warartifactId>
<version>0.0.1-SNAPSHOTversion>
<packaging>warpackaging>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>org.apache.tomcat.embedgroupId>
<artifactId>tomcat-embed-jasperartifactId>
dependency>
dependencies>
<build>
<resources>
<resource>
<directory>src/main/webappdirectory>
<targetPath>META-INF/resourcestargetPath>
<includes>
<include>**/*.*include>
includes>
resource>
<resource>
<directory>src/main/resourcesdirectory>
<includes>
<include>**/*.*include>
includes>
resource>
resources>
<finalName>myBootfinalName>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
3.创建webapp并引入项目,在其中创建index.jsp作为视图
4.配置视图解析器
在核心配置文件 application.properties中添加如下内容:
#前缀
spring.mvc.view.prefix=/
#后缀
spring.mvc.view.suffix=.jsp
5.创建Controller
package com.tsccg.controller;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.ModelAndView;
@Controller
public class WarController {
@RequestMapping("/doSome")
public String doSome(Model model) {
model.addAttribute("data","war包");
return "index";
}
}
6.测试,开启应用,在浏览器中访问 http://localhost:8080/doSome
7.让启动类继承SpringBootServletInitializer
只有继承了此类,重写其configure方法后,生成的war包才能单独部署到外部的服务器中。
SpringBootServletInitializer就是原有的web.xml文件的替代。使用了嵌入式Servlet,默认不支持jsp。
package com.tsccg;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
@SpringBootApplication
public class Application extends SpringBootServletInitializer {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
return builder.sources(Application.class);
}
}
8.部署至外部独立服务器
1)将生成的war包部署到外部的Tomcat服务器中
通过maven执行clean---->package后,将target 目录下的 war 文件拷贝到 tomcat 服务器 webapps 目录中
2)启动Tomcat
3)在浏览器中访问 http://localhost:8080/myBoot/doSome
多出的/myBoot
是由于我们开启tomcat后,会自动将war文件解压缩,我们的项目文件都在解压缩的文件夹中。
以前面打war包的例子为基础进行修改。
1.修改pom.xml
1)指定打包方式为jar
默认打包类型就是jar,删除原先指定的war包语句即可
2)指定springboot-maven-plugin版本
打包jar,有jsp文件时,必须指定maven-plugin插件的版本是 1.4.2.RELEASE
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
<version>1.4.2.RELEASEversion>
plugin>
plugins>
3)修改Controller
@RequestMapping("/doOther")
public String doOther(Model model) {
model.addAttribute("data","jar包");
return "index";
}
4)修改主启动类不继承SpringBootServletInitializer
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
2.执行打包,通过cmd窗口执行命令运行jar包,启动内置的Tomcat
1)通过maven执行clean–>package,生成myBoot.jar
2)进入myBoot.jar包所在目录,打开cmd窗口
3)运行启动命令,启动内置的Tomcat
java -jar myBoot.jar
4)在浏览器中发送请求 http://localhost:8080/doOther
war包必须部署到独立的外部服务器上,占用资源较多。但独立的服务器功能较多,这种方式能更好的利用服务器。
jar包可以通过内置的tomcat单独运行,占用资源少。但内置的服务器功能较少,性能不如war包方式。
在IDEA中直接运行主启动类的main方法。
1.打jar包
在IDEA中通过maven插件将项目打成jar包,可用java -jar xxx.jar
命令启动内置的Tomcat。
上线部署到Linux系统上时,可以将该命令封装到一个Shell脚本中,步骤如下:
①在jar包同级目录里创建一个shell脚本,编写如下内容
run.sh:
#!/bin/sh
java -jar xxx.jar
②赋予权限
chmod 777 run.sh
③启动shell脚本
./run.sh
2.打war包
在IDEA中通过maven插件将项目打成war包,单独部署到tomcat等服务器的发布目录下运行