常用注解
1.创建项目
项目名称:01-spring-boot-MVC
2.@SpringBootApplication
@SpringBootApplication 用在 SpringBoot 项目的启动程序上,整个 SpringBoot 只有且必须有一个这样的注解,是项目的入口程序。
如下代码所示:
源代码:src/main/java/com/springboot/codingstudty/MainApplication.java
@SpringBootApplication
public class MainApplication {
public static void main(String[] args) {
SpringApplication.run (Demo01Application.class, args);
}
}
复制代码
@SpringBootApplication 是以下 3 个注解的整合:
@Configuration
@EnableAutoConfiguration
@ComponentScan
复制代码
@SpringBootApplication 同等于这 3 个注解,以上清单也有介绍。
3.@Controller
@Controller 是让 URL 请求返回具体的页面,如返回 html、jsp 页面等。这个注解在类头上添加。
如下是“http://localhost 跳转到 index.html”示例,需要 3 步骤完成。
(1)要让 SpringBoot 中能访问到 HTML、JSP 等页面,需要在 application.properties 配置
源代码:src/main/resources/application.properties
#默认找到 static 下,只需如下配置即可:
spring.mvc.view.prefix=/
spring.mvc.view.suffix=.html
复制代码
(2)在 static 下创建 index.html
源代码:src/main/resources/static/index.html
<div>
<h3>首页</h3>
<div>首页的内容。。。。。</div>
</div>
复制代码
(3)编写 CodingStudyIndexController 控制器
源代码:
src/main/java/com/springboot/codingstudty/controller/CodingStudyIndexController.java
@Controller
public class CodingStudyIndexController {
}
复制代码
(4)配合@RequestMapping 进行具体页面跳转控制:
跳转到 index.html 页面
源代码:
src/main/java/com/springboot/codingstudty/controller/CodingStudyIndexController.java
/**
* 没有数据渲染的返回
* @return
*/
@RequestMapping("/")
public String index01() {
return "index";
}
复制代码
注意:Controller 数据渲染到页面上需要返回 ModelAndView 类型,如下:
源代码:
src/main/java/com/springboot/codingstudty/controller/CodingStudyIndexController.java
/**
* 返回 ModelAndView
* 通过 ModelAndView 可以带入数据,并渲染到页面
* @return
*/
@RequestMapping("/index")
public ModelAndView index(){
ModelAndView modelAndView = new ModelAndView ();
//可以设置数据
String data = "这个数据来自 IndexController...";
modelAndView.addObject("data",data);
//跳转到 index.html 页面
modelAndView.setViewName ("index");
return modelAndView;
}
复制代码
此时,在 index.html 页面获取 data 数据,有多种方案。
- 第一种方案:引入 freemark 模板;
- 第二种方案:引入 thymeleaf 模板;
- 第三种方案:建立 JSP 页面,等等;
由于第一种方案的语法简单,使用频率高,下面简单说第一种方案。
在 pom.xml 中引入依赖:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-freemarker</artifactId>
</dependency>
复制代码
在 application.properties 配置:
##################freemarker 模板配置
#后缀
spring.freemarker.suffix=.html
#默认在 templates 下
spring.freemarker.template-loader-path=classpath:/static/
#req 访问 request
spring.freemarker.request-context-attribute=req
spring.freemarker.content-type=text/html
spring.freemarker.enabled=true
复制代码
这样配置之后,在 index.html 中获取 data 数据的代码是:
<div>
<h3>首页</h3>
<div>首页的内容.${data}</div>
</div>
复制代码
由于本章重点不是介绍 freemarker 如何使用,这里点到为止。
还有一些注意的地方:让@Controller 能找到页面的前提是需要配置路径,配置映射 HTML页面有多种方案,下面介绍四种方案:
1)默认放在 static 下:
#映射 html 页面
#========1、默认===============================
#默认找到 static 下,只需如下配置即可:
spring.mvc.view.prefix=/
spring.mvc.view.suffix=.html
复制代码
2)指向新的路径,如 views 路径下
#当然可以改变 static-locations 映射路径,如下:
#========2、会在 views 下找文件====================
spring.mvc.view.prefix=/
spring.mvc.view.suffix=.html
spring.resources.static-locations=classpath:/views/
复制代码
3)指向新的路劲,如 public 路径下
#========3、会在 public 下找文件====================
spring.mvc.view.prefix=/
spring.mvc.view.suffix=.html
spring.resources.static-locations=classpath:/public/
复制代码
4)指向新的路劲,如 ENTA-INF/resource 下
#========4、会在/META-INF/resources/下找文件======
spring.mvc.view.prefix=/
spring.mvc.view.suffix=.html
spring.resources.static-locations=classpath:/META-INF/resources/
复制代码
不管怎么设置,以上路径必须在 src/main/resource 下.
4.@RestController
@RestController 是 新 增 的 注 解 , 是 @Controller 和 @ResponseBody 组 合 。
@RestController 注解后,其方法内再配合@RequestMapping,即可返回 Json 格式的数据。
(1) 新建 CodingStudyRestController 控制器:
源代码:
src/main/java/com/springboot/codingstudty/controller/CodingStudyRestController.java
@RestController
public class CodingStudyRestController {
/**
* 假设是获取用户信息
* @return
*/
@GetMapping("user")
public Map<String,Object> getUser() {
//模拟一个用户
Map<String,Object> user = new HashMap<>();
user.put ("id",1);
user.put ("name","张三");
user.put ("age",18);
//返回这个用户
return user;
}
}
复制代码
运行结果:
5.@RequestMapping
@RequestMapping 注解要在 Controller 控制器中的方法头使用,如下:
源代码:src/main/java/com/springboot/codingstudty/controller/CodingStudyIndexController.java
@RequestMapping("/index")
public ModelAndView index(){
ModelAndView modelAndView = new ModelAndView ();
//可以设置数据
String data = "这个数据来自 IndexController...";
modelAndView.addObject("data",data);
//跳转到 index.html 页面
modelAndView.setViewName ("index");
return modelAndView;
}
复制代码
Spring Boot 有 GetMapping、PostMapping、PutMapping、DeleteMapping 代替它。
6.@RequestParam
在参数前面设置,格式是:
@RequestParam(value=“变量名”, required=true/false, defaultVale=默认值 )
复制代码
- value:请求参数名(必须配置)
- required:是否必需,默认为 true,即 请求中必须包含该参数,如果没有包含,将会抛出异常(可选配置)
- defaultValue:默认值,如果设置了该值,required 将自动设为 false,无论你是否配置了 required,配置了什么值,都是 false(可选配置)
设置 required = false
举例,新建 RequestParamController 控制器:
源代码:
src/main/java/com/springboot/codingstudty/controller/RequestParamController.java
@GetMapping("param")
public String param(
@RequestParam("id") String id,
@RequestParam(value = "name", required = false) String name,
@RequestParam(value = "age", required = false) int age){
String data = "";
try {
//返回ID,NAME,age
data = "id=" + id + ",name=" + name + ",age=" + age;
} catch (Exceptione){
data = e.getMessage();
}
return data;
}
复制代码
第一参数:如下 url 必须有 id 这个参数,否则报错(即:?id=1)。
@RequestParam("id") String id
复制代码
- 当只设置 value 的时候,value 可以省略;
- 当要设置多个参数值,value 不能省略;
- required 默认是 true,也就是必须传值,没有则报错;
第二个参数:如下 url 可以没有 userName 这个参数,请求不报错。
@RequestParam(value="userName", required=false) String userName
复制代码
第三个参数:如下设置 required = false,age 不传值,此时 age 等于 null,因 int 是基础类型不能接收 null 所以报错,所以一般可以使用 Integer 声明,避免错误。
@RequestParam(value="age", required=false) int age
复制代码
运行结果:
7.@PathVariable
新建 PathVariableController 控制器类。
源代码:
src/main/java/com/springboot/codingstudty/controller/PathVariableController.java
在参数前面设置,格式是:
@PathVariable(value=“变量名”, required=true/false)
复制代码
- value:请求参数名(必须配置)
- required:是否必需,默认为 true,即 请求中必须包含该参数,如果没有包含,将会
抛出异常(可选配置)
具体方法:
@GetMapping("path/{id}/{name}")
public String pathVar(
@PathVariable("id") String id,
@PathVariable(value = "name",required = false) String userName){
return "id="+id+",userName="+userName;
}
复制代码
传递参数:如:http://localhost:8086/path/1/张三
注意:请求路径必须是完整,否则报错。
运行结果
8.@GetMapping
以下@GetMapping、@PostMapping、@PutMapping、@DeleteMapping 测试示例,新建一个控制器类:UserController
源代码:
src/main/java/com/springboot/codingstudty/controller/UserController.java
@GetMapping 是一个组合注解,是@RequestMapping(method = RequestMethod.GET)的缩写,只接收前端 get 请求。
@GetMapping
public Map<String,Object> getUser() {
Map<String,Object> user = new HashMap<>();
user.put("id",1);
user.put("name","ming206");
return user;
}
复制代码
9.@PostMapping
@PostMapping 是一个组合注解,是@RequestMapping(method = RequestMethod.POST)的缩写,只接收前端 post 提交,一般用于数据的新增。
@PostMapping
public boolean insert(@RequestBody User user) {
//insert ...
return true;
}
复制代码
10. @PutMapping
@PutMapping 是一个组合注解,是@RequestMapping(method = RequestMethod.PUT)的缩写,只接收前端 PUT 提交,一般用于数据的修改。
@PutMapping
public boolean update(@RequestBody User user) {
//update .....
return true;
}
复制代码
11. @DeleteMapping
@DeleteMapping 是一个组合注解,是@RequestMapping(method = RequestMethod.DELETE)的缩写,只接收前端 DELETE 提交,用于数据删除。
@DeleteMapping
public boolean del(@PathVariable("id") String id) {
System.out.println(id);
//delete ....
return true;
}
复制代码
12. @ResponseBody
@ResponseBody 注解通常使用在控制层(controller)的方法上,其作用是将方法的返回值以特定的格式写入到 response 的 body 区域,进而将数据返回给客户端。当方法上面没有写 ResponseBody,底层会将方法的返回值封装为 ModelAndView 对象。
在 Spring Boot 的@RestController 中就不需要再加这个注解了,上面提到@RestController是@controller 和@ResponseBody 的组合,请阅读 RestController。
如下是在@Controller 修饰的类(控制器类)里的方法体前面加这个注解:
源代码:src/main/java/com/springboot/codingstudty/controller/UserViewController.java
@GetMapping("json")
@ResponseBody
public Map<String,Object> getJson(){
//模拟一个用户
Map<String,Object> user = new HashMap<> ();
user.put ("id",100);
user.put("name","ResponseBody");
user.put("age",25);
//返回这个用户
return user;
}
复制代码
运行结果:
13. @RequestBody
@RequestBody 主要用来接收前端传递给后端的 json 字符串中的数据的(请求体中的数据的);GET 方式无请求体,所以使用@RequestBody 接收数据时,前端不能使用 GET 方式提交数据,而是用 POST 方式进行提交。
在后端的同一个接收方法里,@RequestBody 与@RequestParam()可以同时使用,@RequestBody 最多只能有一个,而@RequestParam()可以有多个。
举例:
源代码:src/main/java/com/springboot/codingstudty/controller/UserController.java
@PutMapping
public boolean update(@RequestBody User user) {
//update .....
return true;
}
@PostMapping("save")
public String save(
@RequestParam("id") String id,
@RequestParam(value="age", required=false) int age,
@RequestBody User user){
return "id="+id+",age="+age+"。user 对象==>"+user.toString ();
}
复制代码
User 模型:
@Data
public class User {
int id;
String name;
String age;
}
复制代码
运行结果:
以上 API 测试工具是 PostMan
14. @CrossOrigin
前后端分离之后前端 Ajax 请求后端经常碰到的问题就是跨域问题。可以有多种方式解决这个问题,下面介绍 2 个解决方法:
方法 1:在方法头加@CrossOrigin 注解
@GetMapping("isCheck")
@CrossOrigin
public R<List<Resource>> selectAll(@RequestParam("ids") String ids) {
return R.ok (this.resourceService.getListByIds (ids));
}
复制代码
方法 2:使用过滤器设置:
源代码: src/main/java/com/springboot/codingstudty/configuration/AccessControlAllowOriginFilter.java
package com.springboot.codingstudty.configuration;
import org.springframework.context.annotation.Configuration;
import javax.servlet.*;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* 解决跨域问题
*/
@Configuration
public class AccessControlAllowOriginFilter implements Filter {
@Override
public void doFilter( ServletRequest req,
ServletResponse res,
FilterChain chain)
throws IOException, ServletException {
HttpServletResponse response = (HttpServletResponse) res;
response.setHeader("Access-Control-Allow-Origin", "*");
response.setHeader("Access-Control-Allow-Methods","POST, GET, OPTIONS, DELETE");
response.setHeader("Access-Control-Allow-Credentials", "true");
chain.doFilter(req, response);
}
public void init(FilterConfig filterConfig) {
System.out.println("初始化配置......");
}
public void destroy() {
System.out.println("销毁......");
}
}
复制代码
15. @Configuration
@Configuration 是定义配置类,一般在该类内部通过@bean 注册,也就是说将来在调用时,不需要手工 new。下面我们按照 3 步骤试一试。
(1)定义一个类,这是一个普通类。
源代码:src/main/java/com/springboot/codingstudty/configuration/UserAction.java
public class UserAction {
public String display(){
return "执行 UserAction display.... ";
}
}
复制代码
(2)定义配置类,并注册 bean
源代码:src/main/java/com/springboot/codingstudty/configuration/MyConfiguration.java
@Configuration
public class MyConfiguration {
//默认
@Bean
UserAction userAction(){
System.out.println ("默认名字是 userAction");
return new UserAction();
}
//……
}
复制代码
注意:
- 类头注解@Configuration
- 里面的方法加有@Bean(@Bean 下面单独说)
(3) 调用 UserAction 类
在 Controller 类上调用测试。注意不管在哪里调用,最终运行必须依赖于 Spring 容器,否则是运行不了的。例如在普通的 main 方法中是报空指针异常的,但是在 Controller、Test测试类上是可以的,因为它们的环境都是依赖于 Spring 容器。
调用时在变量上加注解@Autowired,即可取到 bean 实例。
创建 UserActionController 类
源代码:
src/main/java/com/springboot/codingstudty/controller/UserActionController.java
//加了 Autowired 注解后,不需要 new 对象
@Autowired
UserAction userAction;
@GetMapping("user/display")
public String getDisplay() {
return userAction.display();
}
复制代码
在浏览器端请求打印效果:
也可以手工编写获取 bean 的方法,下面新建一个类,CreateBean 类
源代码:src/main/java/com/springboot/codingstudty/configuration/CreateBean.java
@Component
public class CreateBean implements ApplicationContextAware {
private ApplicationContext applicationContext;
@Override
public void setApplicationContext(ApplicationContext applicationContext)
throws BeansException {this.applicationContext=applicationContext;}
public ApplicationContext getApplicationContext() {
return applicationContext;
}
}
复制代码
此时,在 UserActionController 内调用:
源代码:src/main/java/com/springboot/codingstudty/controller/UserActionController.java
@Autowired
CallBean callBean;
@GetMapping("user/display2")
public String getDisplay2(){
//注册 bean 时的名字,是一个字符串
String beanName = "userAction";
UserAction userAction = callBean.getApplicationContext ()
.getBean (beanName,UserAction.class);
String msg = userAction.display ();
return "手工获取 bean==》"+msg;
}
复制代码
在浏览器端请求打印效果:
16. @Bean
以上已经多次使用到@Bean 注解,这里就不多介绍了,直接上示例吧。
(1)默认注册 bean,以上的代码也有,如下
源代码:src/main/java/com/springboot/codingstudty/configuration/MyConfiguration.java
//默认
@Bean
UserAction userAction(){
System.out.println ("默认名字是 userAction");
return new UserAction();
}
复制代码
(2)指定一个 bean 名字
源代码:src/main/java/com/springboot/codingstudty/configuration/MyConfiguration.java
@Bean(value = "userAction1")
UserAction userAction1(){
System.out.println ("名字为 userAction1");
return new UserAction();
}
复制代码
(3)调用是制定 bean 的名字
源代码:src/main/java/com/springboot/codingstudty/controller/UserActionController.java
用@Resource
@Resource(name = "userAction1")
UserAction userAction;
复制代码
或@Autowired+@Qualifier
@Autowired
@Qualifier(value = "userAction1")
UserAction userAction;
复制代码
17. @Service
用于修饰 service 层的组件,标注在类上。注意不是标在接口上。
/**
* 描述:service 层
* @author ming
*/
@Service
public class UserService {
//TODO
}
复制代码
之后,调用时和用@Bean 注册是一样用@Autowired 即可。
用@Service 标注的类一般都是明确是业务服务层,从业务角度清晰的划分。
18. @Component
@component 和@Service 没有本质的区别,@Service 内部还是去引用了@component,他们是没有什么区别的。
业务无法明确划分或不能归类清晰时,对该功能进行组件封装,并希望交给 IOC 管理,这时候用@component 注解。@component 和@Service 仅仅是从业务功能上有所划分,他们的本质都是“把对象的生命周期交给 IOC 管理”的目的。
例如下面这个示例,使用@component 注解
源代码:src/main/java/com/springboot/codingstudty/configuration/CreateBean.java
@Component
public class CreateBean implements ApplicationContextAware {
//……
}
复制代码
19. @Repository
@Repository 和@Controller、@Service、@Component 的作用差不多,都是把对象交给 IOC管理。@Repository 用在持久层的接口上,这个注解是将接口的一个实现类交给 spring 管理,使用了@Repository 注解后,就具备可以将原生的数据库异常转为 Spring 处理得异常。
有两个地方需要这个注解,在普通的 Spring 项目中的持久层和在使用 JPA 时的接口上使用,在 Spring Boot 项目中更多的是使用在 JPA 接口上。
在 JPA 接口上的使用如下:
/**
* 描述:dao 层
* @author ming
*/
@Repository
public interface UserDao extends JpaRepository<User,String>{
//TODO
}
复制代码
有时候不用@Repository 来注解,也可以得到这个接口的实现类,有几个原因:
- spring 配置文件中配置了 MapperScannerConfigurer 这个 bean,它会扫描持久层接口创建实现类并交给 spring 管理。
- 接口上使用了@Mapper 注解或者 springboot 中主类上使用了@MapperScan 注解,它和MapperScannerConfigurer 作用一样。
例如使用 SSM 框架时候,经常在 Dao 层注入@Mapper 即可(这时候需要引入 MyBatis 或者 MyBatisPlus 依赖包)。
20. @Autowired
在上面提到多次@Autowired,是用来“new 实例”的。加了该注解的对象直接调用即可,无需手工 new 对象。
//注意,加了@Autowired 就相当于 new UserAction
@Autowired
UserAction userAction;
复制代码
当多个同类型 bean 时,可以这样使用@Resource,如下介绍.
21. @Resource
用@Resource 和@Autowired 类似
@Resource(name = "userAction1")
UserAction userAction;
复制代码
22. @Autowired+@Qualifier
@Autowired+@Qualifier
@Autowired
@Qualifier(value = "userAction1")
UserAction userAction;
复制代码
23. @Value
@Value 是获取 application.properties 中的配置信息,例如 application.properties 中有相关的配置如下:
(1)application.properties:
server.port=8086
spring.datasource.url=jdbc:mysql://localhost:3309/db01
复制代码
(2)用@Value 取值
新建控制器类 ValueController
源代码:src/main/java/com/springboot/codingstudty/controller/ValueController.java
@RestController
public class ValueController {
@Value("${server.port}")
public String port;
public static String DATA_SOURCE_URL;
/**
* @value 给静态变量赋值,需要增加 set 方法
* 方法名称和参数可任意。
* @param val
*/
@Value ("${spring.datasource.url}")
public void setDataSourceUrl(String val){
DATA_SOURCE_URL = val;
}
@GetMapping("val")
public String getVal(){
return "端口号="+ port+",DataSource URL ="+DATA_SOURCE_URL;
}
}
复制代码
注意@value 给静态变量赋值的方法。
运行结果:
作者:淡若清风丶
链接:https://juejin.cn/post/6993137390000799752
来源:掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。