微信公眾號網頁授權獲取用戶信息
本文內容部分出處: https://developers.weixin.qq.com/doc/offiaccount/OA_Web_Apps/Wechat_webpage_authorization.html
近期做過微信公眾號這塊的對接及業務,梳理下其中的點,有需要的小伙伴可以參考下。
用戶在微信客戶端中訪問第三方網頁,公眾號可以通過微信網頁授權機制,來獲取用戶基本信息,進而實現業務邏輯。
關於網頁授權回調域名的說明
1、在微信公眾號請求用戶網頁授權之前,開發者需要先到公眾平台的“設置 - 公眾號設置 - 功能設置 - 網頁授權”的配置選項中,修改授權回調域名。請注意,這里填寫的是域名(是一個字符串),而不是URL,因此請勿加 http:// 等協議頭。
2、授權回調域名配置規范為全域名,比如需要網頁授權的域名為:www.qq.com,配置以后此域名下面的頁面http://www.qq.com/music.html 、 http://www.qq.com/login.html 都可以進行OAuth2.0鑒權。但http://pay.qq.com 、 http://music.qq.com 、 http://qq.com無法進行OAuth2.0鑒權。
3、如果公眾號登錄授權給了第三方開發者來進行管理,則不必做任何設置,由第三方代替公眾號實現網頁授權即可。
關於網頁授權的兩種scope的區別說明
1、以snsapi_base為scope發起的網頁授權,是用來獲取進入頁面的用戶的openid的,並且是靜默授權並自動跳轉到回調頁面的。用戶感知的就是直接進入了回調頁面(配置在自定義菜單中的一長串地址中redirect_uri 對應的回調方法)
2、以snsapi_userinfo為scope發起的網頁授權,是用來獲取用戶的基本信息的。但這種授權需要用戶手動同意,並且由於用戶同意過,所以無須關注,就可在授權后獲取該用戶的基本信息,下圖為手動授權的參考:scope等於snsapi_userinfo時的授權頁面。
3、用戶管理類接口中的“獲取用戶基本信息接口”,是在用戶和公眾號產生消息交互或關注后事件推送后,才能根據用戶OpenID來獲取用戶基本信息。這個接口,包括其他微信接口,都是需要該用戶(即openid)關注了公眾號后,才能調用成功的。
關於UnionID機制
1、請注意,網頁授權獲取用戶基本信息也遵循UnionID機制。即如果開發者有在多個公眾號,或在公眾號、移動應用之間統一用戶帳號的需求,需要前往微信開放平台(open.weixin.qq.com)綁定公眾號后,才可利用UnionID機制來滿足上述需求。
2、UnionID機制的作用說明:如果開發者擁有多個移動應用、網站應用和公眾帳號,可通過獲取用戶基本信息中的unionid來區分用戶的唯一性,因為同一用戶,對同一個微信開放平台下的不同應用(移動應用、網站應用和公眾帳號),unionid是相同的。
關於網頁授權access_token和普通access_token的區別
1、微信網頁授權是通過OAuth2.0機制實現的,在用戶授權給公眾號后,公眾號可以獲取到一個網頁授權特有的接口調用憑證(網頁授權access_token),通過網頁授權access_token可以進行授權后接口調用,如獲取用戶基本信息;
2、其他微信接口,需要通過基礎支持中的 “獲取access_token” 接口來獲取到的普通access_token調用。
下面介紹下獲取用戶的步驟流程:
1、引導用戶進入授權頁面同意授權,獲取code
2、通過code換取網頁授權access_token(與基礎支持中的access_token不同)
3、如果需要,開發者可以刷新網頁授權access_token,避免過期
4、通過網頁授權access_token和openid獲取用戶基本信息(支持UnionID機制)
第一步、用戶同意授權,獲取code:
https://open.weixin.qq.com/connect/oauth2/authorize?appid=APPID&redirect_uri=REDIRECT_URI&response_type=code&scope=SCOPE&state=STATE#wechat_redirect
地址中不能出現空格或者轉義字符等。
其次在發起授權請求時,微信會對授權鏈接做正則強匹配校驗,如果鏈接的參數順序不對,授權頁面將無法正常訪問。
參考鏈接(請在微信客戶端中打開此鏈接體驗): (注意:該長串地址實際就是配置在微信公眾號后台自定義菜單里面的地址)
scope為snsapi_base:
https://open.weixin.qq.com/connect/oauth2/authorize?appid=wx520c15f417810387&redirect_uri=https%3A%2F%2Fchong.qq.com%2Fphp%2Findex.php%3Fd%3D%26c%3DwxAdapter%26m%3DmobileDeal%26showwxpaytitle%3D1%26vb2ctag%3D4_2030_5_1194_60&response_type=code&scope=snsapi_base&state=123#wechat_redirect
scope為snsapi_userinfo:
https://open.weixin.qq.com/connect/oauth2/authorize?appid=wxf0e81c3bee622d60&redirect_uri=http%3A%2F%2Fnba.bluewebgame.com%2Foauth_response.php&response_type=code&scope=snsapi_userinfo&state=STATE#wechat_redirect
參數說明

用戶同意授權后
頁面將跳轉至 redirect_uri/?code=CODE&state=STATE。 這個時候可以在回調的方法里面獲取到微信傳過來的code,
說明:每次授權微信帶過來的code 是不一樣的,五分鍾會過期。
//回調的方法中直接進行獲取 String code = request.getParameter("code");
第二步、通過code 獲取access_token
獲取code后,請求以下鏈接獲取access_token: https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code
實現代碼,有不足之處請見諒!
/*app_accesstoken_path 的值就是 *https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code
*log.error(),可以看到日志輸出結果,方便排查問題
*該方法沒有關閉請求連接,需要注意下 */ public static String getAccessToken(String app_accesstoken_path){ String access_token = ""; try { // 構造httprequest設置 HttpClient client = new DefaultHttpClient(); HttpGet request = new HttpGet(app_accesstoken_path); //添加請求頭 request.addHeader("User-Agent", "Mozilla/5.0"); HttpResponse response = client.execute(request); BufferedReader rd = new BufferedReader( new InputStreamReader(response.getEntity().getContent())); StringBuffer result = new StringBuffer(); String line = ""; while ((line = rd.readLine()) != null) { result.append(line); } LOG.error("resultxx:"+result); Map<String, String> access_tokenMap = (Map<String,String>)JSON.parse(result.toString()); LOG.error("access_tokenMapxx:"+access_tokenMap.toString()); access_token = access_tokenMap.get("access_token"); LOG.error("access_tokenxx:"+access_token); } catch (Exception e) { LOG.error("發送GET請求出現異常!" + e); e.printStackTrace(); } return access_token; }
access_token 的有效期是 2 小時,獲取后可以存在數據庫中或緩存中,快過期的時候可以重新獲取access_token的值,也可以通過access_token值去刷新獲取新的access_token,避免過期導致獲取不到用戶信息。
第三步、通過access_token 獲取新的 acess_token
可以使用refresh_token進行刷新,refresh_token有效期為30天,當refresh_token失效之后,需要用戶重新授權。
請求以下鏈接獲取access_token:
https://api.weixin.qq.com/sns/oauth2/refresh_token?appid=APPID&grant_type=refresh_token&refresh_token=REFRESH_TOKEN
第四步:拉取用戶信息(需scope為 snsapi_userinfo)
請求一下鏈接獲取用戶信息(單個用戶)
http:GET(請使用https協議) https://api.weixin.qq.com/sns/userinfo?access_token=ACCESS_TOKEN&openid=OPENID&lang=zh_CN
實現代碼,有不足之處請見諒!
/*
*該方法返回的是用戶信息,要獲取到具體的值可以自行獲取需要的值
*/
public static String doPost(String url) throws Exception{ String resp = null; CloseableHttpResponse response = null; try { CloseableHttpClient httpclient = HttpClients.createDefault(); HttpPost httpPost = new HttpPost(url); httpPost.setHeader("Content-type", "application/x-www-form-urlencoded;charset=utf-8"); httpPost.setHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/33.0.1750.146 Safari/537.36"); response = httpclient.execute(httpPost); org.apache.http.HttpEntity entity = response.getEntity(); resp = EntityUtils.toString(entity, "utf-8"); }catch (Exception e) { e.printStackTrace(); }finally { try { response.close(); } catch (Exception e) { e.printStackTrace(); } } return resp;
請求返回的錯誤碼詳情點擊此鏈接:全局錯誤碼 。
以上就是網頁授權獲取用戶信息的步驟了!