1,簡介OAuth
http://www.ruanyifeng.com/blog/2019/04/oauth_design.html OAuth 是什么?
http://www.ruanyifeng.com/blog/2019/04/oauth-grant-types.html OAuth的四種授權方式
一般用於聯合登陸,比如第三方系統,可以用微信快速等速,不需要輸入輸入用戶名,密碼,只需一個access token,在沒有過期之前,你就有訪問的權限了。
2,https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421140842 微信公眾技術平台文檔里有:
1 第一步:用戶同意授權,獲取code
2 第二步:通過code換取網頁授權access_token
3 第三步:刷新access_token(如果需要)
4 第四步:拉取用戶信息(需scope為 snsapi_userinfo)
5 附:檢驗授權憑證(access_token)是否有效
3,簡單的小例子:
package com.zfb.api.controller; import javax.servlet.http.HttpServletRequest; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; import com.alibaba.fastjson.JSONObject; import com.zfb.base.Response; import com.zfb.utils.HttpClientUtils; import com.zfb.utils.WeiXinUtils; @Controller public class OauthController extends Response { @Autowired private WeiXinUtils weiXinUtils; private String errorPage = "errorPage"; // 生成授權鏈接 @RequestMapping("/authorizedUrl") public String authorizedUrl() { return "redirect:" + weiXinUtils.getAuthorizedUrl(); } // 微信授權回調地址 @RequestMapping("/callback") public String callback(String code, HttpServletRequest request) { // 1.使用Code 獲取 access_token String accessTokenUrl = weiXinUtils.getAccessTokenUrl(code); JSONObject resultAccessToken = HttpClientUtils.httpGet(accessTokenUrl); boolean containsKey = resultAccessToken.containsKey("errcode"); if (containsKey) { request.setAttribute("errorMsg", "系統錯誤!"); return errorPage; } // 2.使用access_token獲取用戶信息 String accessToken = resultAccessToken.getString("access_token"); String openid = resultAccessToken.getString("openid"); // 3.拉取用戶信息(需scope為 snsapi_userinfo) String userInfoUrl = weiXinUtils.getUserInfo(accessToken, openid); JSONObject userInfoResult = HttpClientUtils.httpGet(userInfoUrl); System.out.println("userInfoResult:" + userInfoResult); request.setAttribute("nickname", userInfoResult.getString("nickname")); request.setAttribute("city", userInfoResult.getString("city")); request.setAttribute("headimgurl", userInfoResult.getString("headimgurl")); return "info"; } }
封裝了一些鏈接,微信提供
@Component public class WeiXinUtils { @Value("${appid}") private String appId; @Value("${secret}") private String secret; @Value("${redirecturi}") private String redirectUri; @Value("${authorizedUrl}") private String authorizedUrl; @Value("${access_token}") private String accessToken; @Value("${userinfo}") private String userinfo; //生成授權鏈接權 public String getAuthorizedUrl() { return authorizedUrl.replace("APPID", appId).replace("REDIRECT_URI", URLEncoder.encode(redirectUri)); } // 生成accessToken public String getAccessTokenUrl(String code) { return accessToken.replace("APPID", appId).replace("SECRET", secret).replace("CODE", code); } // 獲取用戶信息 public String getUserInfo(String accessToken, String openId) { return userinfo.replace("ACCESS_TOKEN", accessToken).replace("OPENID", openId); } }
WeiXinUtils 從配置文件讀取鏈接:
appid: wx5c43fde3c9733d9e secret: b8b217126c33a5fb7074927d5e72a81a redirectUri: http://127.0.0.1:8080/callback ### 生成微信授權 authorizedUrl: https://open.weixin.qq.com/connect/oauth2/authorize?appid=APPID&redirect_uri=REDIRECT_URI&response_type=code&scope=snsapi_userinfo&state=STATE#wechat_redirect ###獲取code后,請求以下鏈接獲取access_token access_token: https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code ###拉取用戶信息(需scope為 snsapi_userinfo) userinfo: https://api.weixin.qq.com/sns/userinfo?access_token=ACCESS_TOKEN&openid=OPENID&lang=zh_CN