个人做电商网站,较好网站建设公司,网站建设毕业设计综述,学校网站建设运行简介0. 导言 我们在浏览器上可以访问成百上千个网站#xff0c;使用每个网站的服务一般都要先注册账号#xff0c;那么我们为了更好地记忆#xff0c;一般都会在多个网站使用相同的账号和密码进行注册。那么问题就来了#xff0c;如果在你注册的网站中有某些个网站的系统设计不…0. 导言 我们在浏览器上可以访问成百上千个网站使用每个网站的服务一般都要先注册账号那么我们为了更好地记忆一般都会在多个网站使用相同的账号和密码进行注册。那么问题就来了如果在你注册的网站中有某些个网站的系统设计不够严谨和安全数据库的用户信息使用明文存储那么一旦这个网站遭到攻击或者是数据泄露那么一些不怀好意的人就可能通过使用这些泄露的数据“撞库”刚好就登录了你使用相同账号密码注册的其他网站。那么你的权益就有可能会受到损害。
由此行内大佬们便提出了 OAuth。
1. OAuth2 简介 OAuth 是一个开放的非常重要的认证标准/协议允许用户授权第三方应用访问其存储在其他网站上的资源而无需将用户名密码提供给第三方网站的开放标准/协议。OAuth2 是 OAuth 的最新版本同时也是被广泛应用的一个版本。我们在网站上常见的QQ登录微信扫码登录GitHub 授权登录就是基于 OAuth2.0 实现的。
官方文档RFC 6749 - The OAuth 2.0 Authorization Framework
2. OAuth2 认证授权总体流程 整体认证授权流程如下 从这张图中我们可以看出整个 OAuth2 的认证授权流程中有4个不同角色
Client客户端也就是第三方网站(相对于认证网站来说)。 Resource Owner资源拥有者也就是“我”。 Authorization Server认证服务器或者说授权服务器。 Resource Server资源服务器。 3. OAuth2 标准接口 /oauth/authorize授权端点
/oauth/token获取令牌端点
/oauth/confirm_access用户确认授权提交端点
/oauth/error授权服务错误信息端点
/oauth/check_token用于资源服务访问的令牌解析端点
/oauth/token_key提供公有密匙的端点如果使用JWT令牌的话
4. OAuth2 四种授权模式 4.1 授权码模式 授权码模式(Authorization Code)这是最常用的授权模式。在模式下用户通过将重定向到授权服务器来进行身份验证并获一个授权码。然后应程序使用授权码与授权服务器进行交互以获取访问牌和刷新令牌。访问令牌用于问受保护的资源而刷新令牌用于获取新的访问令牌。微信扫码登录就是典型的授权码模式。
授权码模式的授权流程如下图所示 具体流程如下:
A用户访问第三方应用第三方应用通过浏览器导向认证服务器。
B用户选择是否给予客户端授权。
C假设用户给予授权认证服务器将用户导向客户端事先指定的重定向URIredirection URI同时附上一个授权码。
D客户端收到授权码附上早先的重定向URI向认证服务器申请令牌。这一步是在客户端的后台的服务器上完成的对用户不可见。
E认证服务器核对了授权码和重定向URI确认无误后向客户端发送访问令牌access token和更新令牌refresh token。
核心参数(假设第三方网站的地址为:wx.com)
https://wx.com/oauth/authorize?response_typetokenclient_idCLIENT_IDredirect_urihttp://www.baidu.comscoperead 1 字段 描述 client_id 授权服务器注册应用后的唯一标识 response_type 必须 固定值 在授权码中必须为 token redirect_uri 必须 通过客户端注册的重定向URL scope 必须 令牌可以访问资源权限 state 可选 存在原样返回客户端 用来防止 CSRF跨站攻击 申请令牌的请求示例(地址栏中的client表示client_id,secret表示密钥值) 刷新令牌请求示例 4.2 简化模式 简化模式(Implicit Grant)简化模式不通过第三方应用程序的服务器直接在浏览器中向认证服务器申请令牌跳过了授权码这个步骤因此得名。所有步骤在浏览器中完成令牌对访问者是可见的且客户端不需要认证。其具体的授权流程如图所示 具体步骤如下:
A第三方应用将用户导向认证服务器。 B用户决定是否给于客户端授权。 C假设用户给予授权认证服务器将用户导向客户端指定的重定向URI并在URI的Hash部分包含了访问令牌。#token D浏览器向资源服务器发出请求其中不包括上一步收到的Hash值。 E资源服务器返回一个网页其中包含的代码可以获取Hash值中的令牌。 F浏览器执行上一步获得的脚本提取出令牌。 G浏览器将令牌发给客户端。 核心参数:
https://wx.com/oauth/authorize?response_typetokenclient_idCLIENT_IDredirect_urihttp://www.baidu.comscoperead 1 字段 描述 client_id 授权服务器注册应用后的唯一标识 response_type 必须 固定值 在授权码中必须为 token redirect_uri 必须 通过客户端注册的重定向URL scope 必须 令牌可以访问资源权限 state 可选 存在原样返回客户端 用来防止 CSRF跨站攻击 4.3 密码模式 **密码模式Resource Owner Password Credentials Grant**中用户向客户端提供自己的用户名和密码。客户端使用这些信息向服务商提供商索要授权。在这种模式中用户必须把自己的密码给客户端但是客户端不得储存密码。这通常用在用户对客户端高度信任的情况下比如客户端是操作系统的一部分或者由一个相同公司出品。而认证服务器只有在其他授权模式无法执行的情况下才能考虑使用这种模式。
授权流程图如下所示 具体步骤如下:
A用户向客户端提供用户名和密码。
B客户端将用户名和密码发给认证服务器向后者请求令牌。
C认证服务器确认无误后向客户端提供访问令牌。
核心参数:
https://wx.com/token?grant_typepasswordusernameUSERNAMEpasswordPASSWORDclient_idCLIENT_ID 1 申请令牌的请求示例(地址栏中的client表示client_id,secret表示密钥值) 刷新令牌的请求示例
4.4 客户端模式 **客户端模式Client Credentials Grant**指客户端以自己的名义而不是以用户的名义向服务提供商进行认证。严格地说客户端模式并不属于OAuth框架所要解决的问题。在这种模式中用户直接向客户端注册客户端以自己的名义要求服务提供商提供服务其实不存在授权问题。 具体步骤如下:
A客户端向认证服务器进行身份认证并要求一个访问令牌。
B认证服务器确认无误后向客户端提供访问令牌。
https://wx.com/token?grant_typeclient_credentialsclient_idCLIENT_IDclient_secretCLIENT_SECRET 1 申请令牌的请求示例(地址栏中的client表示client_id,secret表示密钥值) 5. GitHub授权登录 GitHub 授权登录流程
1打开 GitHub 网站在头部导航栏点击头像再点击 Settings。 2找到 Developer settings (3)先点击左侧 OAuth Apps 再点击 New OAuth App
4输入信息点击 Register application (5)注册成功点击生成密钥 (6)保存好密钥之后不会完整显示了 7创建一个springboot项目
依赖如下
?xml version1.0 encodingUTF-8?
project xmlnshttp://maven.apache.org/POM/4.0.0 xmlns:xsihttp://www.w3.org/2001/XMLSchema-instancexsi:schemaLocationhttp://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsdmodelVersion4.0.0/modelVersionparentgroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-parent/artifactIdversion2.6.4/versionrelativePath/ !-- lookup parent from repository --/parentgroupIdcom.hmblogs/groupIdartifactIdoauth-test/artifactIdversion0.0.1-SNAPSHOT/versionnameoauth-test/namedescriptionhmblogs/descriptionpropertiesjava.version8/java.versiondruid.version1.2.8/druid.versionlog4jdbc.version1.16/log4jdbc.versiones.version7.9.2/es.version/propertiesdependenciesdependencygroupIdcom.alibaba/groupIdartifactIddruid-spring-boot-starter/artifactIdversion${druid.version}/version/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter/artifactId/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-test/artifactId/dependencydependencygroupIdjunit/groupIdartifactIdjunit/artifactId/dependencydependencygroupIdcom.baomidou/groupIdartifactIdmybatis-plus-boot-starter/artifactIdversion3.5.3.1/version/dependencydependencygroupIdorg.bgee.log4jdbc-log4j2/groupIdartifactIdlog4jdbc-log4j2-jdbc4.1/artifactIdversion${log4jdbc.version}/version/dependencydependencygroupIdorg.projectlombok/groupIdartifactIdlombok/artifactIdoptionaltrue/optional/dependencydependencygroupIdmysql/groupIdartifactIdmysql-connector-java/artifactIdscoperuntime/scope/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-security/artifactId/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-oauth2-client/artifactId/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-web/artifactId/dependency/dependenciesbuildpluginsplugingroupIdorg.springframework.boot/groupIdartifactIdspring-boot-maven-plugin/artifactId/plugin/plugins/build/projectyml配置文件如下所示
server:port: 8080servlet.context-path: /spring:security:oauth2:client:registration:github:client-id: Iv1.3a0f77a8ae06e98cclient-secret: deb634113d4bd06a735437ad3f2b95f1ba83f9e4redirect-uri: http://localhost:8080/login/oauth2/code/githubdatasource:druid:db-type: com.alibaba.druid.pool.DruidDataSourcedriverClassName: net.sf.log4jdbc.sql.jdbcapi.DriverSpyurl: jdbc:log4jdbc:mysql://${DB_HOST:localhost}:${DB_PORT:3306}/${DB_NAME:hmblogs}?serverTimezoneAsia/ShanghaicharacterEncodingutf8useSSLfalseusername: ${DB_USER:root}password: ${DB_PWD:123456}
创建一个配置类(这是新版本SpringSecurity的配置写法废弃了WebSecurityConfigurerAdapter)
package com.hmblogs.backend.util;import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.web.SecurityFilterChain;Configuration
EnableWebSecurity
public class SecurityConfig {Beanpublic SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {http.authorizeRequests().anyRequest().authenticated().and().oauth2Login();//使用 oauth2 认证// ...return http.build();}}
再创建一个控制器类
package com.hmblogs.backend.controller;import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.oauth2.core.user.DefaultOAuth2User;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;RestController
public class HelloController {GetMapping(/hello)public DefaultOAuth2User hello(){System.out.println(hello );Authentication authentication SecurityContextHolder.getContext().getAuthentication();return (DefaultOAuth2User) authentication.getPrincipal();}
}
启动项目在浏览器中访问“http://localhost:8080”跳转到github授权端点。