当前位置: 首页 >Java技术 > OAuth2.0系列之密码模式实践教程(四)

OAuth2.0系列之密码模式实践教程(四)

@

OAuth2.0系列博客:

1、密码模式简介

1.1 前言简介

上一篇文章中我们学习了OAuth2的一些基本概念,对OAuth2有了基本的认识,接着学习OAuth2.0授权模式中的密码模式

ps:OAuth2.0的授权模式可以分为:

  • 授权码模式(authorization code)
  • 简化模式(implicit)
  • 密码模式(resource owner password credentials)
  • 客户端模式(client credentials)

密码模式(resource owner password credentials):密码模式中,用户向客户端提供自己的用户名和密码,这通常用在用户对客户端高度信任的情况

1.2 授权流程图

官网图片:
OAuth2.0系列之密码模式实践教程(四) _ JavaClub全栈架构师技术笔记

  • (A)用户访问客户端,提供URI连接包含用户名和密码信息给授权服务器
  • (B)授权服务器对客户端进行身份验证
  • (C)授权通过,返回acceptToken给客户端

从调接口方面,简单来说:

  • 第一步:直接传useame,password获取token

http://localhost:8888/oauth/token?client_id=cms&client_secret=secret&useame=admin&password=123456&grant_type=password&scope=all

  • 第二步:拿到acceptToken之后,就可以直接访问资源

http://localhost:8084/api/userinfo?access_token=${accept_token}

2、例子实践

2.1 实验环境准备

  • IntelliJ IDEA
  • Maven3.+版本
    新建SpringBoot Initializer项目,可以命名password
    OAuth2.0系列之密码模式实践教程(四) _ JavaClub全栈架构师技术笔记

OAuth2.0系列之密码模式实践教程(四) _ JavaClub全栈架构师技术笔记
主要是想引入:

 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency> <!-- Spring Cloud Oauth2--><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-oauth2</artifactId></dependency><!-- Spring Cloud Security--><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-security</artifactId></dependency>

2.2 OAuth2.0角色

前面的学习,我们知道了OAuth2.0主要包括如下角色,下面通过代码例子加深对理论的理解

  • 资源所有者(Resource Owner)
  • 用户代理(User Agent)
  • 客户端(Client)
  • 授权服务器(Authorization Server)
  • 资源服务器(Resource Server)

生产环境、资源服务器和授权服务器一般是分开的,不过学习的可以放在一起

定义资源服务器,用注解@EnableResourceServer;
定义授权服务器,用注解@EnableAuthorizationServer;

2.3 OAuth2.0配置类

package com.example.oauth2.password.config;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.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;/** * <pre> * OAuth2.0配置类 * </pre> * * <pre> * @author mazq * 修改记录 *修改后版本: 修改人:  修改日期: 2020/06/11 11:00  修改内容: * </pre> */@Configuration//开启授权服务@EnableAuthorizationServerpublic class OAuth2Config extends AuthorizationServerConfigurerAdapter {@Autowiredprivate AuthenticationManager authenticationManager;private static final String CLIENT_ID = "cms";private static final String SECRET_CHAR_SEQUENCE = "{noop}secret";private static final String SCOPE_READ = "read";private static final String SCOPE_WRITE = "write";private static final String TRUST = "trust";private static final String USER ="user";private static final String ALL = "all";private static final int ACCESS_TOKEN_VALIDITY_SECONDS = 2*60;private static final int FREFRESH_TOKEN_VALIDITY_SECONDS = 2*60;// 密码模式授权模式private static final String GRANT_TYPE_PASSWORD = "password";//授权码模式private static final String AUTHORIZATION_CODE = "authorization_code";//refresh token模式private static final String REFRESH_TOKEN = "refresh_token";//简化授权模式private static final String IMPLICIT = "implicit";//指定哪些资源是需要授权验证的private static final String RESOURCE_ID = "resource_id";@Overridepublic void configure(ClientDetailsServiceConfigurer clients) throws Exception {clients// 使用内存存储.inMemory()//标记客户端id.withClient(CLIENT_ID)//客户端安全码.secret(SECRET_CHAR_SEQUENCE)//为true 直接自动授权成功返回code.autoApprove(true).redirectUris("http://127.0.0.1:8084/cms/login") //重定向uri//允许授权范围.scopes(ALL)//token 时间秒.accessTokenValiditySeconds(ACCESS_TOKEN_VALIDITY_SECONDS)//刷新token 时间 秒.refreshTokenValiditySeconds(FREFRESH_TOKEN_VALIDITY_SECONDS)//允许授权类型.authorizedGrantTypes(GRANT_TYPE_PASSWORD );}@Overridepublic void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {// 使用内存保存生成的tokenendpoints.authenticationManager(authenticationManager).tokenStore(memoryTokenStore());}/** * 认证服务器的安全配置 * * @param security * @throws Exception */@Overridepublic void configure(AuthorizationServerSecurityConfigurer security) throws Exception {security//.realm(RESOURCE_ID)// 开启/oauth/token_key验证端口认证权限访问.tokenKeyAccess("isAuthenticated()")//  开启/oauth/check_token验证端口认证权限访问.checkTokenAccess("isAuthenticated()")//允许表单认证.allowFormAuthenticationForClients();}@Beanpublic TokenStore memoryTokenStore() {// 最基本的InMemoryTokenStore生成tokenretu new InMemoryTokenStore();}}

2.4 Security配置类

为了测试,可以进行简单的SpringSecurity

package com.example.oauth2.password.config;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.core.annotation.Order;import org.springframework.security.authentication.AuthenticationManager;import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;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;/** * <pre> *  SpringSecurity配置类 * </pre> * * <pre> * @author mazq * 修改记录 *修改后版本: 修改人:  修改日期: 2020/06/11 11:23  修改内容: * </pre> */@Configuration@EnableWebSecurity@Order(1)public class SecurityConfig extends WebSecurityConfigurerAdapter {@Bean@Overridepublic AuthenticationManager authenticationManagerBean() throws Exception {retu super.authenticationManagerBean();}@Overrideprotected void configure(AuthenticationManagerBuilder auth) throws Exception {//auth.inMemoryAuthentication()auth.inMemoryAuthentication().withUser("nicky").password("{noop}123").roles("admin");}@Overridepublic void configure(WebSecurity web) throws Exception {//解决静态资源被拦截的问题web.ignoring().antMatchers("/asserts/**");web.ignoring().antMatchers("/favicon.ico");}@Overrideprotected void configure(HttpSecurity http) throws Exception {http// 配置登录页并允许访问//.formLogin().permitAll()// 配置Basic登录//.and().httpBasic()// 配置登出页面.logout().logoutUrl("/logout").logoutSuccessUrl("/")// 配置允许访问的链接.and().authorizeRequests().antMatchers("/oauth/**", "/login/**", "/logout/**","/api/**").permitAll()// 其余所有请求全部需要鉴权认证.anyRequest().authenticated()// 关闭跨域保护;.and().csrf().disable();}}

2.5 功能简单测试

接口测试,要用POST方式,在postman测试,response_type参数传password:

http://localhost:8888/oauth/token?password=123&grant_type=password&useame=nicky&scope=all

OAuth2.0系列之密码模式实践教程(四) _ JavaClub全栈架构师技术笔记

注意配置一下请求头的授权参数,useame即client_id,password即client_secret
OAuth2.0系列之密码模式实践教程(四) _ JavaClub全栈架构师技术笔记

代码方式请求,可以进行如下封装,即进行base64加密

HttpHeaders headers = new HttpHeaders();byte[] key = (clientId+":"+clientSecret).getBytes();String authKey = new String(Base64.encodeBase64(key));LOG.info("Authorization:{}","Basic "+authKey);headers.add("Authorization","Basic "+authKey);

拿到token直接去调业务接口:
http://localhost:8888/api/userinfo?access_token=61b113f3-f1e2-473e-a6d7-a0264bfdfa8d

例子代码下载:code download

作者:smileNicky
来源链接:https://www.cnblogs.com/mzq123/p/13094747.html

版权声明:
1、JavaClub(https://www.javaclub.cn)以学习交流为目的,由作者投稿、网友推荐和小编整理收藏优秀的IT技术及相关内容,包括但不限于文字、图片、音频、视频、软件、程序等,其均来自互联网,本站不享有版权,版权归原作者所有。

2、本站提供的内容仅用于个人学习、研究或欣赏,以及其他非商业性或非盈利性用途,但同时应遵守著作权法及其他相关法律的规定,不得侵犯相关权利人及本网站的合法权利。
3、本网站内容原作者如不愿意在本网站刊登内容,请及时通知本站(javaclubcn@163.com),我们将第一时间核实后及时予以删除。





本文链接:https://www.javaclub.cn/java/112653.html

标签:OAuth2
分享给朋友:

“OAuth2.0系列之密码模式实践教程(四)” 的相关文章

SpringBoot整合hibeate纯注解版 2022年05月15日 21:58:07
浅谈分布式与集群的概念 2022年05月15日 22:00:23
SpringCloud简单实例 2022年05月16日 20:38:34
【Linux:开源操作系统】 2022年05月23日 21:29:44
并发编程|彻底搞懂volatile 2022年05月27日 21:51:40
SpringBoot整合 mybatisPlus 2022年05月27日 21:55:24
java总结文章 2022年05月28日 23:33:52