日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 综合教程 >内容正文

综合教程

企业微信三方开发(三):网页授权登录

發布時間:2023/12/19 综合教程 29 生活家
生活随笔 收集整理的這篇文章主要介紹了 企业微信三方开发(三):网页授权登录 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

初識微信開發

企業微信三方開發:注冊企業微信服務商

企業微信三方開發(一):回調驗證及重要參數獲取

企業微信三方開發(二):獲取access_token

企業微信三方開發(三):網頁授權登錄

企業微信三方開發(四):發送消息

企業微信三方開發(五):掃碼登錄

目錄

前言一
技術棧及工具
一、OAuth2到底是什么?

1.1、首先要對授權登錄有個正確的概念
1.2、OAuth2.0的授權碼模式

二、網頁授權

2.1、新建uni-app項目
2.2、 構建網頁授權鏈接

三、獲取用戶信息及敏感信息
總結

前言一

企業微信登錄分兩種:網頁授權登錄和掃碼授權登錄。
區別除了字面意思一個需要掃碼一個不需要掃碼外。還一個重要應用上的區別就是網頁授權登錄必須在微信客戶端完成。
此文是關于如何實現網頁授權登錄的。

登錄的整體邏輯分三段,從用戶點擊登錄按鈕開始:

點擊登錄按鈕,訪問OAuth2網頁授權鏈接獲取微信授權code【前端處理】
通過授權code換取用戶成員票據user_ticket在內的用戶信息【后端處理】
通過user_ticket獲取用戶敏感信息【后端處理】

這里OAuth2網頁授權鏈接獲取授權code在前端完成。我們前端使用uni-app框架,其好處是搭建方便、支持跨端、語言為現在很熱門的vue。

微信企業三方開發訪問授權鏈接不支持本地調試,官方意見是自己搭建線上調試平臺,然后通過企業微信訪問調試。這里我就只好用我自己線上的服務器和域名進行開發調試。

技術棧及工具

前端開發框架:uni-app
前端開發工具:HBulider
后端開發框架:spring-boot
后端開發工具: idea

一、OAuth2到底是什么?

在做授權登錄時,無論是微信還企業微信,包括許多其它廠的登錄。我們都會碰到一個概念——OAuth

通常也寫作OAuth2.0,其中2.0是他的版本號

1.1、首先要對授權登錄有個正確的概念

通常說到登錄,就涉及兩方:用戶和應用

比如我在使用微信,那么我就是用戶,微信app就是應用。
登錄邏輯也很簡單:我只需要注冊用戶名及密碼到微信服務器,即可用用戶名和密碼登錄

而授權登錄則涉及三方:用戶,認證服務器 ,應用

比如我想使用CSDN,需要注冊登錄。如果我直接選擇用我的微信賬號登錄,這就是一個授權登錄過程。其中用戶就是我,認證服務器就是微信的服務器,應用則是CSDN

其中微信的授權登錄就是采用的OAuth 2.0授權碼模式

1.2、OAuth2.0的授權碼模式

OAuth是一套授權模式的統稱,其中用的最多的就是授權碼模式。

上圖就是OAuth2.0授權碼模式的流程,我們再結合微信授權登錄CSDN的情形講解一下:

首先我點擊CSDN的微信登錄按鈕,CSDN服務器會構造OAuth2鏈接(具體鏈接參看微信文檔,參數包括CSDN的身份ID,以及重定向URI,這個URI也就是CSDN登錄成功的頁面),進入到微信的授權頁
我在微信的授權頁點擊同意授權,微信會跳轉到重定向URI,也就是CSDN登錄成功頁并附上授權碼
進入登錄成功頁時,CSDN服務器會拿著授權碼以及調用憑證AccessToken(由微信指定接口獲取)向微信服務器獲取我的基本信息。整個授權過程完成。

可以看到OAuth2.0很明顯的優點,CSDN完全不用知道更不需要存儲我的微信賬號和密碼,就能判斷我的微信就是我的微信,即我就是我!

二、網頁授權

明白了OAuth2.0,下面構建OAuth2.0鏈接以及其中的參數也就不需要多講。

2.1、新建uni-app項目

因為正好在用uni-app做小程序,所以這里就選擇了這個框架,具體創建方式直接查看官方教程,這里我們已經創建了一個叫easyou-agency的項目。

這里前端用什么框架不重要,關鍵是需要發送http請求

2.2、 構建網頁授權鏈接

接口文檔


注意參數scope,主要用于設置手動授權還是靜默授權。 區別就是授權時需不需要點擊授權按鈕。

如果選擇手動授權,需給應用配置權限

接下來繼續寫代碼,先新建兩個頁面,index和login

login頁面需要訪問構建的URL:

<template>
	<view>
		<view>
			 <form @submit="doLogin">
				<button plain="true" class="loginBtn" lang="zh_CN" form-type="submit">登錄</button>
			 </form>
		</view>
	</view>
</template>

<script>

	export default {
		data() {
			return {
				usercode: '',
				password: '',
				passwordHidden: true
			}
		},
		onLoad:function(){

		},
		methods: {
			doLogin() {
				let _this = this
				localStorage.setItem("hasLogin",true)
				// 這里放自己的域名
				let redirect_uri = encodeURI("www.xxxx.com")
				let authorUrl = 'https://open.weixin.qq.com/connect/oauth2/authorize?appid=ww8273b1801b97c577&redirect_uri='+redirect_uri+'&response_type=code&scope=snsapi_userinfo&state=STATE#wechat_redirect'
				window.location.href = authorUrl
			}
		}
	}
</script>

<style>
	.loginBtn{
		color: #337bd4!important;
		border:1rpx solid #337bd4!important;
		font-size: 30rpx;
		border-radius: 50rpx;
	}
</style>

redirect_uri 用的是我線上的域名,也就是我安裝好的應用的主頁url。在應用詳情里配置:

index頁是打開應用時缺省進入的頁面,需要做三件事:

通過storage判斷是否是登錄狀態,不是回到login頁
再判斷url參數是否帶code
如果帶code說明是網頁授權過來的,將code發給后臺換取成員票據user_ticket和用戶信息

index頁如下:

<template>
	<view class="content">
		<image class="logo" src="/static/logo.png"></image>
		<view class="text-area">
			<text class="title">{{title}}</text>
		</view>
	</view>
</template>

<script>
	export default {
		data() {
			return {
				title: this.$route.query.code
			}
		},
		onLoad() {
			if(localStorage.getItem("hasLogin")=='false'){
				uni.redirectTo({
				    url: '../login/login'
				});
			}
			
			if(this.$route.query.code){
				// 從靜模授權進入首頁				
				localStorage.setItem("auth_code",this.$route.query.code)
				
				this.getuserinfo3rd()
			} 

		},
		methods: {
		    // 獲取敏感信息
			getuserinfo3rd:function(){
				uni.request({
				   url: 'http://tantan.vaiwan.com/login/getuserinfo3rd.do?code='+this.$route.query.code,
				   method:'POST',
				   success: function (res) {
						console.log("res:"+res);
				   }
				})
			}
		}
	}
</script>

<style>
	.content {
		display: flex;
		flex-direction: column;
		align-items: center;
		justify-content: center;
	}

	.logo {
		height: 200rpx;
		width: 200rpx;
		margin-top: 200rpx;
		margin-left: auto;
		margin-right: auto;
		margin-bottom: 50rpx;
	}

	.text-area {
		display: flex;
		justify-content: center;
	}

	.title {
		font-size: 36rpx;
		color: #8f8f94;
	}
</style>

自此前端部分就完成了,生成發行版本并上傳至自己服務器,并配置好域名指向index。

企業微信能夠成功訪問index,由于storage的登錄狀態為false,所以跳轉到login頁面

企業微信網頁應用有前端調試插件,安裝方法查看官方教程

點擊登錄按鍵:

成功跳轉到首頁

請求鏈接攜帶code,說明構建網頁授權鏈接成功!

如果是手動授權,則會先跳轉到授權頁:

此時就要手動點即授權按鈕授權

三、獲取用戶信息及敏感信息

在1.2中我們在index頁中有個getuserinfo3rd函數向后臺發送ajax請求,參數攜帶了網頁授權成功的code。此時我們就要響應并通過code獲取用戶票據user_ticket,再通過user_ticket獲取用戶敏感信息。

新建一個LoginController:

package com.tan.cwp.controller;

import com.tan.cwp.util.HttpHelper;
import com.tan.cwp.util.PropertiesUtil;
import org.json.JSONException;
import org.json.JSONObject;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;


@RestController
@RequestMapping("/login")
public class LoginController {
    /**
     * 獲取訪問用戶userid
     *
     * 請求地址:https://qyapi.weixin.qq.com/cgi-bin/service/getuserinfo3rd?suite_access_token=SUITE_ACCESS_TOKEN&code=CODE
     * 請求方式: GET
     * @parm1 SUITE_ACCESS_TOKEN
     * @parm2 oauth2授權成功返回的code
     */
    @RequestMapping(value = "getuserinfo3rd.do" ,method = RequestMethod.POST)
    public static void getUserInfo3rd(HttpServletRequest request,HttpServletResponse response) throws IOException, JSONException {

        String code = request.getParameter("code");

        String suite_access_token = PropertiesUtil.getProperty("suite_access_token");

        String url = "https://qyapi.weixin.qq.com/cgi-bin/service/getuserinfo3rd?suite_access_token="+suite_access_token+"&code="+code;

        JSONObject jsonObj = HttpHelper.doGet(url);

        JSONObject result = getUserDetail3rd((String) jsonObj.get("user_ticket"));

        // 將信息發送至前臺
        PrintWriter out = response.getWriter();
        out.print(result);
        out.close();
    }

    /**
     * 獲取訪問用戶敏感信息
     *
     * 請求地址:https://qyapi.weixin.qq.com/cgi-bin/service/getuserdetail3rd?suite_access_token=SUITE_ACCESS_TOKEN
     * 請求方式: POST
     * @parm1 SUITE_ACCESS_TOKEN
     * @parm2 getUserInfo3rd獲得的user_ticket
     */
    public static JSONObject getUserDetail3rd(String user_ticket) throws JSONException, IOException {
        String suite_access_token = PropertiesUtil.getProperty("suite_access_token");
        String url = "https://qyapi.weixin.qq.com/cgi-bin/service/getuserdetail3rd?suite_access_token="+suite_access_token;

        JSONObject jsonParms = new JSONObject();
        jsonParms.put("user_ticket", user_ticket);
        JSONObject jsonObj = HttpHelper.doPost(url,jsonParms);

        return jsonObj;
    }
}

通過兩個函數先后獲取用戶普通信息和敏感信息。

保存并重新運行

回到企業微信點擊登錄按鈕發現報錯了:

一個標標準準的跨域錯誤

這里的調用域名是我線上的域名www.xxxx.com,被調用域名是我本地的 http://tantan.vaiwan.com,所以跨域了。解決跨域通常有兩種思路:

從調用方出發:通過http服務器(nginx或apache)將被調用域名反向代理到同一個域名
從被調用方出發:通過過濾器增加請求頭,允許指定域名可以跨域

我們選擇第二種方法新增過濾器。

新增filter包,加個叫CrosFilter的過濾器:

package com.tan.cwp.filter;

import javax.servlet.*;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

public class CrosFilter implements javax.servlet.Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {

    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {

        HttpServletResponse res = (HttpServletResponse)servletResponse;

        // 允許所有域名跨域
        res.addHeader("Access-Control-Allow-Origin","*");
        res.addHeader("Access-Control-Allow-Methods","GET,POST,PUT,DELETE,OPTIONS");
        res.addHeader("Access-Control-Allow-Headers","Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

        filterChain.doFilter(servletRequest,servletResponse);
    }

    @Override
    public void destroy() {

    }
}

在 CwpApplication 中將過濾器配上:

package com.tan.cwp;
import com.tan.cwp.filter.CrosFilter;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;

@SpringBootApplication
public class CwpApplication {

    public static void main(String[] args) {
        SpringApplication.run(CwpApplication.class, args);
    }

    @Bean
    public FilterRegistrationBean registerFilter() {
        FilterRegistrationBean bean = new FilterRegistrationBean();

        // 過濾所有訪問
        bean.addUrlPatterns("/*");
        bean.setFilter(new CrosFilter());
        return bean;
    }
}

重啟項目,企業微信點擊登錄:

成功獲取到用戶普通信息和敏感信息!

總結

在獲取用戶信息中,有個open_userid返回值。這個是用戶在應用內的唯一標識,需存入數據庫用作用戶登錄的憑證。

總結

以上是生活随笔為你收集整理的企业微信三方开发(三):网页授权登录的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。