繼續上篇,本章介紹springBoot Web入門篇,本章會介紹SpringBoot Web的入門配置
web開發
spring boot web開發非常的簡單,其中包括常用的json輸出、filters、property、log等
json 接口開發
在以前的spring 開發的時候需要我們提供json接口的時候需要做那些配置呢
- 添加 jackjson 等相關jar包
- 配置spring controller掃描
- 對接的方法添加@ResponseBody
就這樣我們會經常由於配置錯誤,導致406錯誤等等,spring boot如何做呢,只需要類添加@RestController
即可,默認類中的方法都會以json的格式返回
@RestController
public class HelloWorldController {
@RequestMapping("/getUser")
public User getUser() {
User user=new User();
user.setUserName("小明");
user.setPassWord("xxxx");
return user;
}
}
如果我們需要使用頁面開發只要使用@Controller
,下面會結合模板來說明
自定義Filter
我們常常在項目中會使用filters用於錄調用日誌、排除有XSS威脅的字符、執行權限驗證等等。Spring Boot自動添加了OrderedCharacterEncodingFilter和HiddenHttpMethodFilter,並且我們可以自定義Filter。
兩個步驟:
- 實現Filter接口,實現Filter方法
- 添加
@Configuration
註解,將自定義Filter加入過濾鏈- 可以直接添加多個過濾器。
好吧,直接上代碼
@Configuration
public class WebConfiguration {
@Bean
public RemoteIpFilter remoteIpFilter() {
return new RemoteIpFilter();
}
@Bean
public FilterRegistrationBean testFilterRegistration() {
FilterRegistrationBean registration = new FilterRegistrationBean();
registration.setFilter(new MyFilter());
registration.addUrlPatterns("/*");
registration.addInitParameter("paramName", "paramValue");
registration.setName("MyFilter");
registration.setOrder(1);
return registration;
}
public class MyFilter implements Filter {
@Override
public void destroy() {
// TODO Auto-generated method stub
}
@Override
public void doFilter(ServletRequest srequest, ServletResponse sresponse, FilterChain filterChain)
throws IOException, ServletException {
// TODO Auto-generated method stub
HttpServletRequest request = (HttpServletRequest) srequest;
System.out.println("this is MyFilter,url :"+request.getRequestURI());
filterChain.doFilter(srequest, sresponse);
}
@Override
public void init(FilterConfig arg0) throws ServletException {
// TODO Auto-generated method stub
}
}
}
我們在Controller中也可以獲取到addInitParameter中的參數,如下:
@RestController
public class MainController {
// 如果項目沒有定義過濾器,則此處直接進來此對象會報錯
@Autowired
private FilterRegistrationBean registration;
@RequestMapping("/find")
public Map<String, Object> find(){
// 獲取自定義Filter中的參數
Map<String, Object> map = registration.getInitParameters()
return map;
}
}
添加攔截器
添加攔截器需要添加一個configuration
@Configuration
@ComponentScan(basePackageClasses = Application.class, useDefaultFilters = true)
public class ServletContextConfig extends WebMvcConfigurationSupport { ... }
爲了方便掃描位置,我們可以寫一個接口或者入口類Application放置於最外一層的包內,這樣就會掃描該類以及子包的類。
resources配置
# 設置靜態訪問資源的路徑
spring.mvc.static-path-pattern=/static/**
# 上述設置中是將http://<path>:<port>/<prefix>/static/, 轉接到項目的resources文件夾下的static目錄
但當我們繼承了WebMvcConfigurationSupport 並配置掃描後,上述resources的配置失效,還原默認配置。那麼我們需要在這個類中再次指定靜態資源位置:
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/").addResourceLocations("/**");
// 將路徑訪問static下的資源,全部轉移到項目目錄下resources下的static目錄下
registry.addResourceHandler("/static/**").addResourceLocations("classpath:/static/");
}
這樣訪問classpath下的static包下的靜態資源的url匹配爲/static/xxx.js。默認匹配static下的靜態文件url爲/xxx.js,雖然清潔,但我感覺idea不會識別這種路徑,還是改成完整的路徑比較好。
Interceptor配置
配置登錄攔截或者別的。需要創建一個攔截器類來繼承HandlerInterceptorAdapter,然後只需要覆蓋你想要攔截的位置就可以了。比如,我只是攔截訪問方法之前:
package com.common.interceptor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class LoginInterceptor extends HandlerInterceptorAdapter {
private Logger logger = LoggerFactory.getLogger(LoginInterceptor.class);
/**
* 攔截器方法,在這裏處理攔截邏輯
*/
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String authorization = request.getHeader("Authorization");
logger.info("The authorization is: {}",authorization);
return super.preHandle(request, response, handler);
}
}
寫好interceptor之後需要在開始創建的ServletContextConfig中添加這個攔截器:
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new LoginInterceptor())
.addPathPatterns("/**")
.excludePathPatterns(FAVICON_URL);
}
完整的ServletContextConfig爲:
package com.config;
import hello.Application;
import hello.interceptor.LoginInterceptor;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurationSupport;
@Configuration
@ComponentScan(basePackageClasses = Application.class, useDefaultFilters = true)
public class ServletContextConfig extends WebMvcConfigurationSupport {
static final private String FAVICON_URL = "/favicon.ico";
static final private String PROPERTY_APP_ENV = "application.environment";
static final private String PROPERTY_DEFAULT_ENV = "dev";
/**
* 發現如果繼承了WebMvcConfigurationSupport,則在yml中配置的相關內容會失效。
* @param registry
*/
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/").addResourceLocations("/**");
registry.addResourceHandler("/static/**").addResourceLocations("classpath:/static/");
}
/**
* 配置servlet處理
*/
@Override
public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
configurer.enable();
}
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new LoginInterceptor())
.addPathPatterns("/**")
.excludePathPatterns(FAVICON_URL);
}
}
自定義Property
在web開發的過程中,我經常需要自定義一些配置文件,如何使用呢
配置application.properties文件
ps.name=小明
ps.age=15
ps.address=北京市 懷柔區
第一種讀取方式:
/**
* 默認請求application.properties的配置,可選擇
* 如果想設置讀取的文件,則添加下面的屬性
* @PropertySource("classpath:demo.properties")
*/
@RestController
public class MainController {
@Value("${ps.name}")
private String name;
@Value("${ps.age}")
private Integer age;
@Value("${ps.address}")
private Integer address;
// 直接在請求方法中使用
}
第二種讀取方式:
/*
*默認請求application.properties的配置,可選擇
* @PropertySource("classpath:demo.properties")
*/
@Component
public class NeoProperties {
@Value("${ps.name}")
private String name;
@Value("${ps.age}")
private Integer age;
@Value("${ps.address}")
private Integer address;
// 聲明get方法
}
第三種讀取方式:
/*
* 默認請求application.properties的配置,可選擇
* @PropertySource("classpath:demo.properties")
*/
@Component
public class MainController {
@Autowired
private Environment env;
@RequestMapping("/find")
public Map<String, Object> find(){
Map<String, Object> map = new HashMap<>();
map.put("name", env.getProperty("yu.a"));
map.put("age", env.getProperty("ps.address"));
return map;
}
}
log配置
見下一章