Spring Security OAuth2使用步骤(一)

本文详细介绍了在微服务架构中使用SpringCloud、SpringSecurity和OAuth2搭建认证授权服务的过程。涵盖依赖包、配置授权服务器、客户端信息、令牌访问端点、资源服务器等内容。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

写在前面:各位看到此博客的小伙伴,如有不对的地方请及时通过私信我或者评论此博客的方式指出,以免误人子弟。多谢!如果我的博客对你有帮助,欢迎进行评论✏️✏️、点赞👍👍、收藏⭐️⭐️,满足一下我的虚荣心💖🙏🙏🙏 。

  本系列将使用 Spring Cloud、 Spring Cloud Alibaba、SpringSecurity、OAuth2搭建一套包含认证服务、网关服务、服务提供者、服务调用者的简单微服务项目,目的是将设计到的相关技术综合应用。

目录

版本说明

依赖包

配置授权服务器

三个方法

配置客户端信息

配置令牌访问端点

配置授权端点

令牌端点的安全约束

Token存储

客户端信息存储

配置资源服务器

配置WebSecurityConfig


版本说明

首先说下我使用的Spring Cloud、 Spring Cloud Alibaba、SpringBoot等的版本,如下:

技术栈版本
Spring CloudHoxton.SR9
Spring Cloud Alibaba2.2.6.RELEASE
Spring Boot2.3.2.RELEASE
Mysql5.7
Nacos1.4.2
Sentinel1.8.1

版本的选择很重要,最好按照官网的版本对应关系选择,官网版本对应表如下:

版本说明 · alibaba/spring-cloud-alibaba Wiki · GitHub

第一篇先记录下认证授权的大体流程及需要引入的依赖。

依赖包

        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-oauth2</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-security</artifactId>
        </dependency>
        <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>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid-spring-boot-starter</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-jdbc</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>fastjson</artifactId>
        </dependency>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
        </dependency>

配置授权服务器

继承 AuthorizationServerConfigurerAdapter接口 并在实现类上加注解@EnableAuthorizationServer)标识这是一个授权服务器。

三个方法

 可以看到只有这三个方法 :

public class AuthorizationServerConfigurerAdapter implements AuthorizationServerConfigurer {

	@Override
	public void configure(AuthorizationServerSecurityConfigurer security) throws Exception{
	}

	@Override
	public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
	}

	@Override
	public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
	}

}

每个方法的作用如下:

ClientDetailsServiceConfigurer:

配置客户端详情服务(ClientDetailsService),客户端详情信息在这里进行初始化,客户端信息可以存到内存中,也可以通过数据库来存储调取详情信息。

AuthorizationServerEndpointsConfigurer:

用来配置令牌(token)的访问端点和令牌服务(token services)。

AuthorizationServerSecurityConfigurer:

用来配置令牌端点(Token Endpoint)的安全约束。

上述三个方法就是授权服务的主要配置,可以关联记忆,既然要完成认证。

它首先得知道客户端信息从哪读取,因此要进行客户端详情配置;

既然要颁发token,那必须得定义token的相关endpoint及token如何存取,以及客户端支持哪些类型的token;

既然暴露出了一些endpoint,那对这些endpoint可以定义一些安全上的约束等。

配置客户端信息

ClientDetailsServiceConfigurer可以使用内存或JDBC来实现客户端详情服务(ClientDetailsService),ClientDetailsService负责查找ClientDetails,而ClientDetails有如下几个重要属性:

  • clientId:标识客户的Id(必须的)。
  • secret:客户端密码。
  • scope:用来限制客户端的访问范围,默认为空,表示客户端拥有全部的访问范围。
  • authorizedGrantTypes:此客户端可以使用的授权类型,默认为空。
  • 其它属性参考下面客户端信息存储中的表结构字段说明。

 客户端信息存储在数据库中时,需要建表,建表语句可以从如下网站找到:

spring-security-oauth/schema.sql at main · spring-attic/spring-security-oauth · GitHub

我用的是Mysql,对于上面链接里的建表语句,有某些字段为`LONGVARBINARY`类型,它对应mysql的`blob`类型,这需要改下,另外主键是varchar(255),如果又用的utf8mb4编码,主键长度会超限制,所以这个主键长度最好也要改一下。

每个表的作用如下:

oauth_client_details :客户端账号密码、授权、回调地址等重要信息;核心表。
oauth_access_token :存储access_token。
oauth_refresh_token :存储refresh_token。
oauth_client_token :存储从服务端获取的token数据。
oauth_code :存储授权码。
oauth_approvals :存储授权成功的客户端信息。在这里插入图片描述

配置令牌访问端点

AuthorizationServerEndpointsConfigurer这个对象的实例可以完成令牌服务及令牌endpoint配置。

AuthorizationServerEndpointsConfigurer通过设定以下属性决定支持的授权类型:

  • authenticationManager:认证管理器,密码模式需要。
  • authorizationCodeServices:授权码模式需要。
  • tokenGranter:如果设置了,那么授权将会交由你完全掌控,并忽略上面的几个属性,一般用作拓展用途,即标准的四种授权模式已经满足不了你的需求的时候,才会考虑使用这个。

配置授权端点

使用@EnableAuthorizationServer注解后,应用启动后将自动生成几个Endpoint:

/oauth/authorize:验证
/oauth/token:获取token
/oauth/confirm_access:用户授权
/oauth/error:认证失败
/oauth/check_token:资源服务器用来校验token
/oauth/token_key:如果使用JWT令牌,则公开用于令牌验证的公钥

说下/oauth/check_token和/oauth/token_key端点,他们都是用于检查令牌的,默认受保护denyAll()。使用tokenKeyAccess()和checkTokenAccess()方法会打开这些端点以供使用,如:

security.checkTokenAccess("permitAll()");

令牌端点的安全约束

AuthorizationServerSecurityConfigurer用来配置令牌端点的安全约束,如配置如下:

@Override
public void configure(AuthorizationServerSecurityConfigurer security){
    security
    .tokenKeyAccess("permitAll()") (1)
    .checkTokenAccess("permitAll()") (2)
    .allowFormAuthenticationForClients() (3);
}

 含义如下:

1 )tokenkey这个 endpoint 当使用 JwtToken 且使用非对称加密时,资源服务用于获取公钥  而开放的,这里指这个 endpoint完全公开。
2 checkToken 这个 endpoint 完全公开。
3 ) 允许表单认证。

Token存储

OAuth2存储token值的方式由多种,所有的实现方式都是实现了TokenStore接口,主要有一下几种:

InMemoryTokenStore:token存储在本机的内存之中。
JdbcTokenStore:token存储在数据库之中。
JwtTokenStore:token不会存储到任何介质中。
RedisTokenStore:token存储在Redis数据库之中。

客户端信息存储

内存中。

数据库中。

客户端信息存储到 oauth_client_details 表中,建表语句可以从如下网站找到:

spring-security-oauth/schema.sql at main · spring-attic/spring-security-oauth · GitHub

每个表的作用如下:

oauth_client_details :客户端账号密码、授权、回调地址等重要信息;核心表。
oauth_access_token :存储access_token。
oauth_refresh_token :存储refresh_token。
oauth_client_token :存储从服务端获取的token数据。
oauth_code :存储授权码。
oauth_approvals :存储授权成功的客户端信息。在这里插入图片描述

配置资源服务器

继承 ResourceServerConfigurerAdapter 接口并在实现类上添加注解 @EnableResourceServer标识这是一个资源服务器。

可以看到只有这两个方法 :

public class ResourceServerConfigurerAdapter implements ResourceServerConfigurer {

	@Override
	public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
	}

	@Override
	public void configure(HttpSecurity http) throws Exception {
		http.authorizeRequests().anyRequest().authenticated();
	}

}

每个方法的作用如下:

configure(HttpSecurity http):可以配置哪些可以访问,哪些不可访问,默认情况下所有不在/oauth/**下的资源都是受保护的资源。

configure(ResourceServerSecurityConfigurer resources):先看下这个方法的解释

它可以为资源服务器添加一个特定的属性,如resourceId,也就是说我们一个授权服务器可能对应多个资源服务器,可以为每个资源服务器添加一个resourceId属性进行区分,可选,但建议使用,如果存在,auth服务器将进行验证。

配置WebSecurityConfig

引入security的依赖并做相关的配置,对资源进行保护。

通常需要复写一下几个方法:

public void configure(WebSecurity web) throws Exception {}

protected void configure(HttpSecurity http) throws Exception {}

public void configure(AuthenticationManagerBuilder auth) throws Exception {}

public AuthenticationManager authenticationManagerBean() throws Exception {}

每个方法的作用如下:

configure(WebSecurity web):可以配置忽略某些请求。

configure(HttpSecurity http):配置安全拦截机制控制资源的访问,可配置匹配哪些请求、哪些可以直接访问、哪些需要授权后访问。

authenticationManagerBean():配置验证管理的Bean。

configure(AuthenticationManagerBuilder auth):配置验证的用户信息源和密码加密策略,并向容器注入AuthenticationManager对象,这需要在OAuth2中配置(授权服务器),配置了AuthenticationManager密码验证才会生效。

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值