创建认证服务
在business
新建项目business-oauth2
POM
<?xml version="1.0" encoding="UTF-8"?>
<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.0</modelVersion>
<parent>
<groupId>ml.yompc.myshop.plus</groupId>
<artifactId>business</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>business-oauth2</artifactId>
<packaging>jar</packaging>
<url>http://www.yompc.ml</url>
<inceptionYear>2018-Now</inceptionYear>
<licenses>
<license>
<name>Apache 2.0</name>
<url>https://www.apache.org/licenses/LICENSE-2.0.txt</url>
</license>
</licenses>
<developers>
<developer>
<id>yompc</id>
<name>FengJia Liu</name>
<email>yom535@outlook.com</email>
</developer>
</developers>
<dependencies>
<!-- Spring Boot -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- Spring Cloud -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-oauth2</artifactId>
</dependency>
<!-- Spring Cloud Alibaba -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!-- Apache Dubbo -->
<dependency>
<groupId>com.alibaba.nacos</groupId>
<artifactId>nacos-client</artifactId>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-registry-nacos</artifactId>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-spring-boot-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework</groupId>
<artifactId>spring</artifactId>
</exclusion>
<exclusion>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
</exclusion>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-serialization-kryo</artifactId>
<exclusions>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
<exclusion>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-common</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.alibaba.spring</groupId>
<artifactId>spring-context-support</artifactId>
</dependency>
<!-- Commons -->
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
</dependency>
<dependency>
<groupId>io.github.openfeign</groupId>
<artifactId>feign-okhttp</artifactId>
</dependency>
<!-- Projects -->
<dependency>
<groupId>ml.yompc.myshop.plus</groupId>
<artifactId>commons-dto</artifactId>
<version>${project.parent.version}</version>
</dependency>
<dependency>
<groupId>ml.yompc.myshop.plus</groupId>
<artifactId>ums-admin-provider-api</artifactId>
<version>${project.parent.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<mainClass>ml.yompc.myshop.plus.business.BusinessOAuth2Application</mainClass>
</configuration>
</plugin>
</plugins>
</build>
</project>
与之前相比增加了oauth2的依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-oauth2</artifactId>
</dependency>
后加载进business
模块下面
创建Application
并开启认证服务器@EnableAuthorizationServer
package ml.yompc.myshop.plus.business;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
/**
* @email yom535@outlook.com
* @author: 有民(yom535)
* @date: 2019/9/27
* @time: 23:36
*/
@SpringBootApplication
@EnableAuthorizationServer
public class BusinessOAuth2Application {
public static void main(String[] args) {
SpringApplication.run(BusinessOAuth2Application.class,args);
}
}
创建配置文件appilcation.yml
spring:
application:
name: business-oauth2
main:
allow-bean-definition-overriding: true
jackson:
time-zone: GMT+8
date-format: yyyy-MM-dd HH:mm:ss
cloud:
nacos:
discovery:
server-addr: nacos.yompc.ml:30848
dubbo:
scan:
base-packages: ml.yompc.myshop.plus.business.controller, ml.yompc.myshop.plus.business.service
protocol:
name: dubbo
port: -1
serialization: kryo
registry:
address: nacos://nacos.yompc.ml
port: 30848
server:
port: 9001
management:
endpoints:
web:
exposure:
include: "*"
business:
oauth2:
grant_type: password
client_id: client
client_secret: secret
feign:
okhttp:
enabled: true
httpclient:
enabled: false
创建configure包并配置认证服务器AuthorizationServerConfiguration
package ml.yompc.myshop.plus.business.configure;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer;
import org.springframework.security.oauth2.provider.token.TokenStore;
import org.springframework.security.oauth2.provider.token.store.InMemoryTokenStore;
/**
* @email yom535@outlook.com
* @author: 有民(yom535)
* @date: 2019/9/27
* @time: 23:44
*/
@EnableAuthorizationServer
@Configuration
public class AuthorizationServerConfiguration extends AuthorizationServerConfigurerAdapter {
@Autowired
private BCryptPasswordEncoder passwordEncoder;
/**
* 注入用于支持 password 模式
*/
@Autowired
private AuthenticationManager authenticationManager;
@Bean
public TokenStore tokenStore() {
return new InMemoryTokenStore();
}
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints
// 用于支持密码模式
.authenticationManager(authenticationManager)
.tokenStore(tokenStore());
}
@Override
public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
security
// 允许客户端访问 /oauth/check_token 检查 token
.checkTokenAccess("isAuthenticated()")
.allowFormAuthenticationForClients();
}
/**
* 配置客户端
*
* @param clients
* @throws Exception
*/
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients
// 使用内存设置
.inMemory()
// client_id
.withClient("client")
// client_secret
.secret(passwordEncoder.encode("secret"))
// 授权类型,密码模式和刷新令牌
.authorizedGrantTypes("password", "refresh_token")
// 授权范围
.scopes("backend")
// 可以设置对哪些资源有访问权限,不设置则全部资源都可以访问
.resourceIds("backend-resources")
// 设置访问令牌的有效期,这里是 1 天
.accessTokenValiditySeconds(60 * 60 * 24)
// 设置刷新令牌的有效期,这里是 30 天
.refreshTokenValiditySeconds(60 * 60 * 24 * 30);
}
}
创建WebSecurityConfiguration
配置
package ml.yompc.myshop.plus.business.configure;
import ml.yompc.myshop.plus.business.service.UserDetailsServiceImpl;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
/**
* @email yom535@outlook.com
* @author: 有民(yom535)
* @date: 2019/9/27
* @time: 23:46
*/
@EnableWebSecurity
@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true, jsr250Enabled = true)
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
@Bean
public BCryptPasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
@Bean
@Override
public UserDetailsService userDetailsServiceBean() throws Exception {
return new UserDetailsServiceImpl();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsServiceBean());
}
/**
* 用于支持 password 模式
*
* @return
* @throws Exception
*/
@Bean
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Override
public void configure(WebSecurity web) throws Exception {
web.ignoring()
.antMatchers("/user/login");
}
@Override
protected void configure(HttpSecurity http) throws Exception {
/**
* 将授权访问配置改为注解方式
* @see LoginController#info()
*/
http.exceptionHandling()
.and()
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
http.exceptionHandling()
.and()
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS)
.and()
.authorizeRequests()
// 授权访问
.antMatchers("/user/info").hasAuthority("USER")
.antMatchers("/user/logout").hasAuthority("USER");
}
}
并且在Postman测试获取到Token