精华内容
下载资源
问答
  • spring security 基于oauth 2.0 实现 sso 单点登录Demo 使用 spring security 基于oauth 2.0 实现 sso 单点登录Demo spring boot + spring security + spring security oauth
  • spring security + oauth 2.0 实现单点登录、认证授权,直接贴代码
  • vue-admin:oauth2.0单点登录实现

    千次阅读 2020-01-14 20:56:05
    现在有一个需求是客户要求使用oauth2.0方式的单点登录进入系统,原先我们都是使用cas方式的单点登录。这里整理下代码: 1.oauth2.0 分为4个步骤: 获取第三方token。 为了安全性(不暴露第三方token和secretKey),c...

    背景:
    现在有一个需求是客户要求使用oauth2.0方式的单点登录进入系统,原先我们都是使用cas方式的单点登录。这里整理下代码:

    1.oauth2.0

    分为4个步骤:

    1. 获取第三方token。
      为了安全性(不暴露第三方token和secretKey),c此处是后端对第三方提供的API进行处理,前端只去公司后端提供的接口中拿token。
    2. 拿到第三方token后,跳转到第三方认证平台。
    3. 跳转到第三方认证平台后,第三方平台在URL地址栏中携带ticket票据返回。
    4. 从地址栏中拿到票据,绑定用户信息。

    拿到token后要把token保存到缓存中,在绑定用户信息时使用。

    permission.js中代码实现:

    if (window.g.OAUTH_URL) {
      if (window.g.OAUTH_URL && !window.location.search) {
        let oauthToken = ''
        getOauthToken().then((res) => {
          if (res.data.status) {
            // 1.获取token
            if (res.data.data.content) {
              oauthToken = res.data.data.content.token
              // 2.跳转到认证平台,不可以写在异步获取token的函数外面
              window.location.href = window.g.OAUTH_URL + `/unified_identity_logon/#/login?pcToken=${oauthToken}&applicationCode=${window.$oauthCmccr}`
              localStorage.setItem('Oauth_Token', oauthToken)
            }
          }
        })
      } else {
        // axios.get(`${window.g.OAUTH_URL}/unified_identity_logon/#/login?ticket=${window.location.search.split('=')[1]}`).then(res => {})
        // 3.认证平台跳回,并在地址栏包含ticket,获取ticket
        // const ticket = window.location.search.split('=')[1]
        var reg = new RegExp('ticket' + '=([^&]*)(&|$)', 'i') // /ticket=([^&]*)(&|$)/i
        var ticket = window.location.search.substr(1).match(reg)[1]
        // 4.获取用户信息
        const token = localStorage.getItem('Oauth_Token')
        getOauthUserInfo(ticket, token).then((res) => {
          if (res.data.status && res.data.content.hasOwnProperty('userId')) {
            const username = res.data.content.userId
            if (username) {
              // 5.绑定
              casBind(ticket, username).then(res => {
                if (res.data.code === 0) {
                  axios.get(`${window.g.BASE_CCR}/oauth/token?client_id=xxxxx&client_secret=xxxxx&grant_type=password&username=${username}&password=${ticket}`).then(response => {
                  //token和刷新token存到缓存中,各端保持登陆状态
                    setToken(response.data.access_token, res.data.expires_in)
                    setRefreshToken(response.data.refresh_token)
                    autoGetToken(response.data.refresh_token)
                    window.location.search = ''
                    next('/')
                  }).catch(() => {
                    Message({
                      type: 'error',
                      message: '登录失败'
                    })
                    // 登陆失败再次跳到认证中心
                    window.location.href = window.g.OAUTH_URL + `/unified_identity_logon/#/login?pcToken=${token}&applicationCode=${window.$oauthCmccr}`
                  })
                }
              }).catch(() => {
                next()
              })
            } else {
              Message({
                type: 'error',
                message: '登录超时'
              })
              window.location.href = window.g.OAUTH_URL + `/unified_identity_logon/#/login?pcToken=${token}&applicationCode=${window.$oauthCmccr}`
            }
          }
        })
      }
    }
    

    在main.js中请求后端接口拿到登录地址。

    axios.get(window.g.BASE_CCR + '/center/xxx/v1/xxxx/xxxxx').then(res => {
      if (res.data.code === 0) {
        var data = JSON.parse(res.data.data)
        // 应用码
        window.$oauthCmccr = data.userConfig.oauthCmccr
        // cas方式
        if (data.userConfig.authType === 'cas') {
          window.g.CAS_URL = data.userConfig.casLoginUrl || ''
          window.g.CAS_LOGOUT = data.userConfig.casLogout || ''
        } else {
          // oauth2.0方式
          window.g.OAUTH_URL = data.userConfig.oauthLoginUrl || ''
          // window.g.OAUTH_LOGOUT = data.userConfig.casLogout || ''
        }
      } else {
        Message({
          type: 'error',
          message: '配置信息获取失败'
        })
      }
    
    展开全文
  • 站在巨人的肩膀上进行的测试,线上也有很多例子,但是不知道你们看不看的懂,反正我是看懂了,并做了些修改,应该都能看得懂了
  • OAuth2.0单点登录接口调用

    千次阅读 2019-09-19 17:25:08
    OAuth2.0介绍 OAuth 2 是一个授权框架,或称授权标准,它可以使第三方应用程序或客户端获得对HTTP服务上(例如 Google,GitHub )用户帐户信息的有限访问权限。OAuth 2 通过将用户身份验证委派给托管用户帐户的服务...

    • OAuth2.0介绍

    OAuth 2 是一个授权框架,或称授权标准,它可以使第三方应用程序或客户端获得对HTTP服务上(例如 GoogleGitHub )用户帐户信息的有限访问权限。OAuth 2 通过将用户身份验证委派给托管用户帐户的服务以及授权客户端访问用户帐户进行工作。综上,OAuth 2 可以为 Web 应用 和桌面应用以及移动应用提供授权流程。

    注:使用OAuth2 认证的好处就是你只需要一个账号密码,就能在各个网站进行访问,而免去了在每个网站都进行注册的繁琐过程

    授权模式:授权码模式

    授权码模式是功能最完整、流程最严密的授权模式,它的特点是通过客户端的后台服务器,与“服务器提供”的认证服务器进行互动

    授权流程

    代码实现

    package com.smartdot.grcsp.common.servlet;
    
    import com.smartdot.commons.util.PropertyGetter;
    import net.sf.json.JSONObject;
    import org.apache.commons.httpclient.HttpClient;
    import org.apache.commons.httpclient.NameValuePair;
    import org.apache.commons.httpclient.methods.GetMethod;
    import org.apache.commons.httpclient.methods.PostMethod;
    import org.apache.http.HttpEntity;
    import org.apache.http.client.methods.CloseableHttpResponse;
    import org.apache.http.client.methods.HttpGet;
    import org.apache.http.client.methods.HttpPost;
    import org.apache.http.conn.ssl.*;
    import org.apache.http.entity.StringEntity;
    import org.apache.http.impl.client.CloseableHttpClient;
    import org.apache.http.impl.client.HttpClients;
    import org.apache.http.util.EntityUtils;
    import org.apache.log4j.Logger;
    import javax.servlet.http.Cookie;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import java.io.BufferedReader;
    import java.io.IOException;
    import java.io.InputStream;
    import java.io.InputStreamReader;
    import java.net.URLEncoder;
    import java.security.KeyManagementException;
    import java.security.KeyStoreException;
    import java.security.NoSuchAlgorithmException;
    
    /**
     * @author xxx
     * @date 2019/09/10
     * @description 单点登录OAuth2.0操作类
     * 步骤:
     *      1.门户系统获取临时授权码
     *      2.通过授权码获取token令牌
     *      3.通过令牌获取用户信息
     */
    public class LoginUtil {
        private static Logger logger = Logger.getLogger(LoginInterceptor.class);
        //测试
        private final static String CLIENT_SECRET= PropertyGetter.getString("client_secret");
        private final static String CLIENT_ID=PropertyGetter.getString("client_id");
        private final static String PORTAL_URL = PropertyGetter.getString("portal_url");
        //生产
        private final static String PRO_CLIENT_SECRET= PropertyGetter.getString("pro_client_secret");
        private final static String PRO_CLIENT_ID=PropertyGetter.getString("pro_client_id");
        private final static String PRO_PORTAL_URL = PropertyGetter.getString("pro_portal_url");
        /**
         * @param grant_type表示使用的授权模式,必选,此处固定值为“authorization_code
         * @param code表示上一步获得的授权吗,必选
         * @param client_id 表示客户端ID,必选
         * @param client_secret表示客户端密钥,必选
         * @method post
         * @return idpEntity
         * @Description: 获取Token
         */
        public static JSONObject getToken(String portalUrl,String code,String clientId,String clientSecret) {
            String url = portalUrl + "/o/oauth2/token";
            System.out.println("url============" + url);
            HttpClient client = new HttpClient();
            client.getHttpConnectionManager().getParams().setConnectionTimeout('썐');
            PostMethod postMethod = new PostMethod(url);
            postMethod.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
            NameValuePair[] pairs = new NameValuePair[]{new NameValuePair("client_id", clientId), new NameValuePair("client_secret", clientSecret), new NameValuePair("grant_type", "authorization_code"), new NameValuePair("code", code)};
            postMethod.setRequestBody(pairs);
            int status = 0;
    
            try {
                System.out.println("查询token=============");
                status = client.executeMethod(postMethod);
                System.out.println("查询token结束=============");
            } catch (IOException var14) {
                var14.printStackTrace();
            }
    
            System.out.println("status:="+status);
            String result;
            if(status == 200) {
                result = null;
                String var9 = "";
    
                try {
                    result = postMethod.getResponseBodyAsString();
                    logger.debug("result======" + result);
                    InputStream inputStream = postMethod.getResponseBodyAsStream();
                    BufferedReader br = new BufferedReader(new InputStreamReader(inputStream));
                    StringBuffer stringBuffer = new StringBuffer();
                    String str = "";
    
                    while((str = br.readLine()) != null) {
                        stringBuffer.append(str);
                    }
    
                    var9 = stringBuffer.toString();
                    return  JSONObject.fromObject(var9);
                } catch (IOException var15) {
                    var15.printStackTrace();
                }
            }
            return null;
        }
    
        /**
         * @param portalUrl 门户系统域名
         * @param code 临时授权码
         * @param clientId
         * @param clientSecret
         * @return
         * @throws KeyStoreException
         * @throws NoSuchAlgorithmException
         * @throws IOException
         * @throws KeyManagementException
         * @description 生产环境获取token
         */
        public static JSONObject getRroToken(String portalUrl,String code,String clientId,String clientSecret) throws KeyStoreException, NoSuchAlgorithmException, IOException, KeyManagementException {
            String url = portalUrl + "/o/oauth2/token";
            SSLContextBuilder builder = new SSLContextBuilder();
            builder.loadTrustMaterial(null, new TrustSelfSignedStrategy());
            SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(builder.build());
            CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build();
            String parma = "client_id="+clientId+"&client_secret="+clientSecret+"&code="+code+"&grant_type=authorization_code";
            HttpPost httpPost = new HttpPost(url);
            httpPost.setHeader("Content-Type", "application/x-www-form-urlencoded");
            System.out.println("parma========"+parma);
            StringEntity postingString = new StringEntity(parma,"utf-8");
            httpPost.setEntity(postingString);
            CloseableHttpResponse response = httpclient.execute(httpPost);
            try {
                if(response!=null){
                    System.out.println("status============="+response.getStatusLine());
                    HttpEntity entity = response.getEntity();
                    if(entity==null){
                        System.out.println("entity==="+entity);
                        return null;
                    }
                    return JSONObject.fromObject(EntityUtils.toString(entity));
                }
            } finally {
                response.close();
            }
            return null;
        }
        /**
         * @param token 表示上一步获得的访问令牌
         * @param token_type 表示令牌类型。该值大小写不敏感,必选项,可以是bearer类型或mac类型
         * @method post
         * @return idpEntity
         * @Description: 获取用戶信息
         */
        public static JSONObject getUseInfo(String portalUrl, String tokenType, String accessToken) {
            logger.info("portalUrl======" + portalUrl + "tokenType=" + tokenType + "accessToken=" + accessToken);
            String url = portalUrl + "/api/jsonws/user/get-current-user";
            logger.info("url==" + url);
            HttpClient client = new HttpClient();
            client.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
            GetMethod getMethod = new GetMethod(url);
            getMethod.setRequestHeader("Content-Type", "application/json");
            getMethod.setRequestHeader("Authorization","Bearer "+accessToken);
            int status = 0;
            try {
    
                status = client.executeMethod(getMethod);
            } catch (IOException var14) {
                logger.debug(var14);
            }
    
            System.out.println("status:="+status);
            String result;
            if(status == 200) {
                String var9 = "";
                try {
                    result = getMethod.getResponseBodyAsString();
                    logger.debug("result======" + result);
                    InputStream inputStream = getMethod.getResponseBodyAsStream();
                    BufferedReader br = new BufferedReader(new InputStreamReader(inputStream));
                    StringBuffer stringBuffer = new StringBuffer();
                    String str = "";
    
                    while((str = br.readLine()) != null) {
                        stringBuffer.append(str);
                    }
    
                    var9 = stringBuffer.toString();
                    return  JSONObject.fromObject(var9);
                } catch (IOException var15) {
                    logger.debug(var15);
                }
            }
            return null;
        }
    
        /**
         * @param portalUrl
         * @param tokenType
         * @param accessToken
         * @return
         * @throws KeyStoreException
         * @throws NoSuchAlgorithmException
         * @throws IOException
         * @throws KeyManagementException
         * @description 生产环境获取用户信息
         */
        public static JSONObject getProUseInfo(String portalUrl, String tokenType, String accessToken) throws KeyStoreException, NoSuchAlgorithmException, IOException, KeyManagementException{
            logger.info("portalUrl======" + portalUrl + "tokenType=" + tokenType + "accessToken=" + accessToken);
            String url = portalUrl + "/api/jsonws/user/get-current-user";
            logger.info("url==" + url);
            SSLContextBuilder builder = new SSLContextBuilder();
            builder.loadTrustMaterial(null, new TrustSelfSignedStrategy());
            SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(builder.build());
            CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build();
            HttpGet httpGet = new HttpGet(url);
            httpGet.setHeader("Content-Type", "application/x-www-form-urlencoded");
            httpGet.setHeader("Authorization","Bearer "+accessToken);
            CloseableHttpResponse response = httpclient.execute(httpGet);
            try {
                if(response!=null){
                    System.out.println("status============="+response.getStatusLine());
                    HttpEntity entity = response.getEntity();
                    if(entity==null){
                        System.out.println("entity==="+entity);
                        return null;
                    }
                    return JSONObject.fromObject(EntityUtils.toString(entity));
                }
            } finally {
                response.close();
            }
            return null;
        }
    
        //登录调用
        public static JSONObject getLogin(HttpServletRequest request, HttpServletResponse response) {
            String portalUrl = "";
            String clientId = "";
            String clientSecret = "";
            Boolean mark = false;
            if("生产环境应用域名".equalsIgnoreCase(request.getServerName())){
                portalUrl = PRO_PORTAL_URL;
                clientId = PRO_CLIENT_ID;
                clientSecret = PRO_CLIENT_SECRET;
                System.out.println("生产环境");
                System.out.println("portalUrl==="+portalUrl);
                System.out.println("clientId==="+clientId);
                System.out.println("clientSecret==="+clientSecret);
                mark = true;
            }else if("测试环境应用域名".equalsIgnoreCase(request.getServerName())){
                portalUrl = PORTAL_URL;
                clientId = CLIENT_ID;
                clientSecret = CLIENT_SECRET;
                System.out.println("测试环境");
            }else{
                System.out.println("========非测试或者正式环境无法调用单点登录=======");
                return null;
            }
            try {
                //获取临时授权码
                String code = request.getParameter("code");
                System.out.println("--------------------------------------------code is:" + code);
                //token类型
                String accessToken;
                //token令牌
                String tokenType;
                JSONObject obj = null;
                if(org.apache.commons.lang.StringUtils.isNotBlank(code)) {
                    //获取token令牌
                    if(mark){
                        obj = getRroToken(portalUrl,code,clientId,clientSecret);
                    }else{
                        obj  = getToken(portalUrl,code,clientId,clientSecret);
                    }
                    System.out.println("--------------------------------------------obj is:" + obj);
                    if(obj != null) {
                        accessToken = obj.getString("access_token");
                        new Cookie("idp_token", accessToken);
                        tokenType = obj.getString("token_type");
                        System.out.println("accessToken:" + accessToken + "   tokenType:" + tokenType);
                        //获取用户信息
                        JSONObject json;
                        if(mark){
                            json = getProUseInfo(portalUrl, tokenType, accessToken);
                        }else{
                            json = getUseInfo(portalUrl, tokenType, accessToken);
                        }
                        if(json != null) {
                            System.out.println("json===" + json);
                            //return json.getString("screenName");
                            return json;
                        }
                    }
                } else {
                    (new StringBuilder()).append("http://").append(request.getServerName()).append(":").append(request.getServerPort()).append(request.getContextPath()).toString();
    
                    String appUrl = "http://" + request.getServerName() + ":" + request.getServerPort() + request.getContextPath()+"/rest/ssologin";
                    if(mark){
                        appUrl = "http://" + request.getServerName() + request.getContextPath()+"/rest/ssologin";
                    }
                    System.out.println("appUrl========="+appUrl);
                    String liferayDomain = portalUrl + "/o/oauth2/authorize/" + "?client_id=" + clientId;
                    String clientDomain = "&redirect_uri=" + URLEncoder.encode(appUrl) + "&response_type=code" + "&state=fkLiferay";
                    System.out.println("clientDomain encode前===&redirect_uri=" + appUrl + "&response_type=code" + "&state=fkLiferay");
                    System.out.println("clientDomain encode后===&redirect_uri=" + URLEncoder.encode(appUrl) + "&response_type=code" + "&state=fkLiferay");
                    String destUrl = liferayDomain+clientDomain;
                    System.out.println("destUrl===" + destUrl);
                    response.sendRedirect(destUrl);
                }
            } catch (Exception var10) {
                System.out.println("e.getMessage():" + var10.getMessage());
                var10.printStackTrace();
            }
            return null;
    
        }
    
    
    
    }
    

     

    展开全文
  • 实现OAuth2授权,并且实现单点登录的小例子,请使用vs2015打开
  • 基于Microsoft.Owin.Security.OAuth实现OAuth 2.0所有应用场景,可集成单点登录功能
  • sso OAuth2.0 单点登录实现

    千次阅读 2018-08-28 14:48:58
    https://www.jianshu.com/p/d94bb118aa43
    展开全文
  • Java的oauth2.0 服务端与客户端的实现.zip 封装了oauth2.0的基本架构和实现,对照我的博客http://blog.csdn.net/jing12062011/article/details/78147306使用该源码。 下载项目压缩包,解压,里面两个maven项目:...
  • oauth2.0单点登录

    千次阅读 2021-02-26 15:03:17
    1、什么是 OAuth2.0 OAuth 是一个开放标准,该标准允许用户让第三方应用访问该用户在某一网站上存储的私密资源(如头像、照片、视频等),而在这个过程中无需将用户名和密码提供给第三方应用。实现这一功能是通过...

    1、什么是 OAuth2.0

    OAuth (Open Authority的缩写)是一个开放标准,该标准允许用户让第三方应用访问该用户在某一网站上存储的私密资源(如头像、照片、视频等),而在这个过程中无需将用户名和密码提供给第三方应用。实现这一功能是通过提供一个令牌(token),而不是用户名和密码来访问他们存放在特定服务提供者的数据。采用令牌(token)的方式可以让用户灵活的对第三方应用授权或者收回权限。

    OAuth2.0 是 OAuth 协议的下一版本,但不向下兼容 OAuth 1.0。传统的 Web 开发登录认证一般都是基于 session 的,但是在前后端分离的架构中继续使用 session 就会有许多不便,因为移动端(Android、iOS、微信小程序等)要么不支持 cookie(微信小程序),要么使用非常不便,对于这些问题,使用 OAuth2 认证都能解决。

    对于大家而言,我们在互联网应用中最常见的 OAuth2 应该就是各种第三方登录了,例如 QQ 授权登录、微信授权登录、微博授权登录、GitHub 授权登录等等。
     

    1.1、Auth2协议中,共有四个参与方(角色):

    • 1.resource owner:资源拥有者,即用户。
    • 2.resource server:资源服务器。即存储用户数据的服务器,一般对外都以RESTFul API的形式暴露用户数据,client使用access token访问resource server申请被保护起来的用户数据。
    • 3.client:客户端。即第三方应用。
    • 4.authorization server:授权服务器。用来鉴权第三方应用合法性,并对用户登录、是否授权第三方应用获取数据进行响应,并根据用户操作,向第三应用颁发code 或 用户token或者告知授权失败。

    2、什么是单点登录?

    单点登录的英文名是 Single Sign On,因此一般简称为SSO。它的用途在于,不管多么复杂的应用群,只要在用户权限范围内,那么就可以做到,用户只需要登录一次就可以访问权限范围内的所有应用子系统。对于用户而言,访问多个应用子系统只需要登录一次,同样在需要注销的时候也只需要注销一次。举个简单的例子,你在百度首页登录成功之后,你再访问百度百科、百度知道、百度贴吧等网站也会处于登录状态了,这就是一个单点登录的真实案例。

    重要的是理解:

    • SSO服务端SSO客户端直接是通过授权以后发放Token的形式来访问受保护的资源;
    • 相对于浏览器来说,业务系统是服务端,相对于SSO服务端来说,业务系统是客户端;
    • 浏览器和业务系统之间通过会话正常访问;
    • 不是每次浏览器请求都要去SSO服务端去验证,只要浏览器和它所访问的服务端的会话有效它就可以正常访问。

    2.2.  OAuth2

    3、OAuth2.0授权与单点登录的区别

      根据OAuth2.0授权与单点登录的概念,我们可以得知二者至少存在以下几点区别:

    1. 从信任角度来看。OAuth2.0授权服务端和第三方客户端不属于一个互相信任的应用群(通常都不是同一个公司提供的服务),第三方客户端的用户不属于OAuth2.0授权服务端的官方用户;而单点登录的服务端和接入的客户端都在一个互相信任的应用群(通常是同一个公司提供的服务),各个子系统的用户属于单点登录服务端的官方用户。
    2. 从资源角度来看。OAuth2.0授权主要是让用户自行决定——“我”在OAuth2.0服务提供方的个人资源是否允许第三方应用访问;而单点登录的资源都在客户端这边,单点登录的服务端主要用于登录,以及管理用户在各个子系统的权限信息。
    3. 从流程角度来看。OAuth2.0授权的时候,第三方客户端需要拿预先“商量”好的密码去获取Access Token;而单点登录则不需要。

    4、OAuth2 协议一共支持 4 种不同的授权模式:

    1. 授权码模式:常见的第三方平台登录功能基本都是使用这种模式。

    2. 简化模式:简化模式是不需要客户端服务器参与,直接在浏览器中向授权服务器申请令牌(token),一般如果网站是纯静态页面则可以采用这种方式。

    3. 密码模式:密码模式是用户把用户名密码直接告诉客户端,客户端使用说这些信息向授权服务器申请令牌(token)。这需要用户对客户端高度信任,例如客户端应用和服务提供商就是同一家公司,我们自己做前后端分离登录就可以采用这种模式。

    4. 客户端模式:客户端模式是指客户端使用自己的名义而不是用户的名义向服务提供者申请授权,严格来说,客户端模式并不能算作 OAuth 协议要解决的问题的一种解决方案,但是,对于开发者而言,在一些前后端分离应用或者为移动端提供的认证授权服务器上使用这种模式还是非常方便的。

    4.1、授权码模式

    授权码模式是最安全并且使用最广泛的一种模式。以www.javaboy.org 为例,假如我要引入微信登录功能,那么我的流程可能是这样:

    在授权码模式中,我们分授权服务器和资源服务器,授权服务器用来派发 Token,拿着 Token 则可以去资源服务器获取资源,这两个服务器可以分开,也可以合并。

    上面这张流程图的含义,具体是这样:

    1. 首先,我会在我的 www.javaboy.org 这个网页上放一个超链接(我的网站相当于是第三方应用),用户 A (服务方的用户,例如微信用户)点击这个超链接就会去请求授权服务器(微信的授权服务器),用户点击的过程其实也就是我跟用户要授权的过程,这就是上图中的 1、2 步。

    2. 接下来的第三步,就是用户点击了超链接之后,像授权服务器发送请求,一般来说,我放在 www.javaboy.org 网页上的超链接可能有如下参数:

    https://wx.qq.com/oauth/authorize?response_type=code&client_id=javaboy&redirect_uri=www.javaboy.org&scope=all

    这里边有好几个参数,在后面的代码中我们都会用到,这里先和大家简单解释一下:

    • response_type 表示授权类型,使用授权码模式的时候这里固定为 code,表示要求返回授权码(将来拿着这个授权码去获取 access_token)。

    • client_id 表示客户端 id,也就是我应用的 id。有的小伙伴对这个不好理解,我说一下,如果我想让我的 www.javaboy.org 接入微信登录功能,我肯定得去微信开放平台注册,去填入我自己应用的基本信息等等,弄完之后,微信会给我一个 APPID,也就是我这里的 client_id,所以,从这里可以看出,授权服务器在校验的时候,会做两件事:1.校验客户端的身份;2.校验用户身份。

    • redirect_uri 表示用户登录在成功/失败后,跳转的地址(成功登录微信后,跳转到 www.javaboy.org 中的哪个页面),跳转的时候,还会携带上一个授权码参数。

    • scope 表示授权范围,即 www.javaboy.org 这个网站拿着用户的 token 都能干啥(一般来说就是获取用户非敏感的基本信息)。

    3、接下来第四步,www.javaboy.org 这个网站,拿着第三步获取到的 code 以及自己的 client_id 和 client_secret 以及其他一些信息去授权服务器请求令牌,微信的授权服务器在校验过这些数据之后,就会发送一个令牌回来。这个过程一般是在后端完成的,而不是利用 js 去完成。

    4、接下来拿着这个 token,我们就可以去请求用户信息了。

    一般情况下我们认为授权码模式是四种模式中最安全的一种模式,因为这种模式我们的 access_token 不用经过浏览器或者移动端 App,是直接从我们的后台发送到授权服务器上,这样就很大程度减少了 access_token 泄漏的风险。

    OAuth2.0最典型的授权码认证方式:


    资源服务器和鉴权服务器都是属于资源所有方,也就是最终的服务提供方,第三接入方需要先与鉴权服务器申请合作获取客户编码。

    对于资源服务器来说,需要做的是

    1 accessToken和clientId的校验

    2 token校验通过后要对token访问权限做好限制

    对于鉴权服务器来说,需要做的是

    1 接受第三方应用的申请,维护clientId

    2 提供登入页面,做用户、密码鉴权

    3 授权码生成和验证

    4 token的生成

    5 clientId、token的维护,一般clientId入库,token入内存

    5、基于oauth2.0的sso单点登录

    OAuth2有 授权服务器、资源服务器、客户端、用户(资源拥有者)这样几个角色,当我们用它来实现SSO的时候是不需要资源服务器这个角色的。授权服务器当然是用来做认证的,客户端就是各个应用系统,我们只需要登录成功后拿到用户信息以及用户所拥有的权限即可。

     

     

    展开全文
  • oauth2.0单点登录

    2018-11-15 08:45:02
    记录一下使用oauth2搭建单点登录过程中踩过的一些坑 项目是基于springboot架构搭建,使用了springcloud的一系列组件,项目安全维护方面使用的是springcloud的子组件spring cloud security和Spring Cloud Security ...
  • ssm搭建、Oauth2.0客户端和服务端

    热门讨论 2018-02-26 11:02:12
    包括三个简单的项目以及mybatis用于自动生成bean、dao、mapping所需的文件,项目分别为: 1、ssm的简单搭建。 2、oauth2.0的客户端。 3、oauth2.0的服务端。
  • 阮一峰大佬对Oauth2.0的解释 二. 认证授权流程中的4个角色 用户:资源的拥有着 客户端:要访问/获取用户资源的服务 认证服务器:对用户与客户端认证授权的服务器 资源服务器:保存用户资源的服务器 三. 四种授权...
  • 微博Oauth2.0 协议,用java 实现单点登录获取用户信息。
  • 首先Sercurity Oauth2.0 单点登录有四种模式,授权码模式,密码模式,Implicit,Client Credentials。 这里首先推荐这位作者写的https://blog.csdn.net/kefengwang/article/details/81213025这篇文章。通俗易懂很...
  • oauth2.0授权界面,大致流程图: 前提准备: 在新浪开放平台申请appkey和appsecret:http://open.weibo.com/. 熟悉oauth2.0协议,相关知识:http://www.ruanyifeng.com/blog/2014/05/oauth_2_0.html OAuth2的...
  • 点击上方☝码猿技术专栏轻松关注,设为星标!及时获取有趣有料的技术单点登录是多域名企业站点流行的登录方式。本文以现实生活场景辅助理解,力争彻底理清 OAuth2.0 实现单点登录的原理流程...
  • 单点登录(Single Sign On),简称sso,一种统一和授权的机制,用户登录一次,即可访问所有相互信任的系统。 二. 优点 提高用户效率:用户不用频繁的操作登录,也不用记住不同的登录账号。 提高开发人员效率:开发...
  • 点击上方☝码猿技术专栏轻松关注,设为星标!及时获取有趣有料的技术大家好,我是不才陈某~单点登录是多域名企业站点流行的登录方式。本文以现实生活场景辅助理解,力争彻底理清 OAuth2.0 ...
  • 单点登录(Single sign on),英文名称缩写SSO,SSO的意思就是在多系统的环境中,登录单方系统,就可以在不用再次登录的情况下访问相关受信任的系统。也就是说只要登录一次单体系统就可以
  • OAuth2.0授权与单点登录的实现

    千次阅读 2019-03-04 17:08:42
    OAuth2.0授权与单点登录(SSO)的区别 在前两篇文章中我介绍了OAuth2.0协议的基本概念(https://www.zifangsky.cn/1309.html)以及OAuth2.0授权服务端从设计到实现(https://www.zifangsky.cn/1313.html)。这篇...
  • oauth2 单点登录 的简单解决方案 提供给需要的同学参考
  • 继承WebSecurityConfigurerAdapter,添加@EnableOAuth2Sso注解开启单点登录。 @EnableOAuth2Sso public class SecurityConfig extends WebSecurityConfigurerAdapter { } 只需要将所有需要认证的请求开启认证即可。...
  • //1:
  • 这篇文章,我们主要来系统的串起来讲一下,从宏观的层面来讲述一下单点登录,并且来实现一个demo。 首先,我们来借助一个真实的案例来切入: 相信大家都登录过码云吧:(https://gitee.com/) 在登录选项里我们选择...
  • 基于Oauth2.0单点登录—初识Security(一) 基于Oauth2.0单点登录Oauth2.0(二) 基于Oauth2.0单点登录单点登录(三) 基于Oauth2.0单点登录—搭建认证服务器(四) 基于Oauth2.0单点登录—搭建资源服务器...
  • Spring Security OAuth2.0实现单点登录SSO

    千次阅读 2018-04-27 14:25:26
    基于Spring Security OAuth2.0实现单点登录SSO 完整的代码下载链接 https://github.com/haoxiaoyong1014/spring-security-sso 简单的单点登录Spring Security OAuth2 1.概述 在本教程中,我们将讨论如何使用...
  • 作者:王克锋kefeng.wang/2018/04/06/oauth2-sso单点登录是多域名企业站点流行的登录方式。本文以现实生活场景辅助理解,力争彻底理清 OAuth2.0 实现单点登...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 7,858
精华内容 3,143
关键字:

oauth2.0单点登录