You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

README.md 19 kB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554
  1. # spring-boot-demo-social
  2. > 此 demo 主要演示 Spring Boot 项目如何使用 **[史上最全的第三方登录工具 - JustAuth](https://github.com/zhangyd-c/JustAuth)** 实现第三方登录。
  3. >
  4. > 如果技术选型是 `JFinal` 的,请查看此 [**`demo`**](https://github.com/xkcoding/jfinal-justauth-demo)
  5. >
  6. > https://github.com/xkcoding/jfinal-justauth-demo
  7. >
  8. > 如果技术选型是 `ActFramework` 的,请查看此 [**`demo`**](https://github.com/xkcoding/act-justauth-demo)
  9. >
  10. > https://github.com/xkcoding/act-justauth-demo
  11. >
  12. > JustAuth,如你所见,它仅仅是一个**第三方授权登录**的**工具类库**,它可以让我们脱离繁琐的第三方登录SDK,让登录变得**So easy!**
  13. >
  14. > 1. **全**:已集成十多家第三方平台(国内外常用的基本都已包含),后续依然还有扩展计划!
  15. > 2. **简**:API就是奔着最简单去设计的(见后面[`快速开始`](https://github.com/zhangyd-c/JustAuth#%E5%BF%AB%E9%80%9F%E5%BC%80%E5%A7%8B)),尽量让您用起来没有障碍感!
  16. >
  17. > PS: 本人十分幸运的参与到了这个SDK的开发,主要开发了**QQ登录、微信登录、小米登录、微软登录、谷歌登录**这 **`5`** 个第三方登录,以及一些BUG的修复工作。再次感谢 [@母狼](https://github.com/zhangyd-c) 开源这个又好用又全面的第三方登录SDK。
  18. ## 1. 环境准备
  19. ### 1.1. 公网服务器准备
  20. 首先准备一台有公网IP的服务器,可以选用阿里云或者腾讯云,如果选用的是阿里云的,可以使用我的[优惠链接](https://chuangke.aliyun.com/invite?userCode=r8z5amhr)购买。
  21. ### 1.2. 内网穿透frp搭建
  22. > frp 安装程序:https://github.com/fatedier/frp/releases
  23. #### 1.2.1. frp服务端搭建
  24. 服务端搭建在上一步准备的公网服务器上,因为服务器是centos7 x64的系统,因此,这里下载安装包版本为linux_amd64的 [frp_0.27.0_linux_amd64.tar.gz](https://github.com/fatedier/frp/releases/download/v0.27.0/frp_0.27.0_linux_amd64.tar.gz) 。
  25. 1. 下载安装包
  26. ```shell
  27. $ wget https://github.com/fatedier/frp/releases/download/v0.27.0/frp_0.27.0_linux_amd64.tar.gz
  28. ```
  29. 2. 解压安装包
  30. ```shell
  31. $ tar -zxvf frp_0.27.0_linux_amd64.tar.gz
  32. ```
  33. 3. 修改配置文件
  34. ```shell
  35. $ cd frp_0.27.0_linux_amd64
  36. $ vim frps.ini
  37. [common]
  38. bind_port = 7100
  39. vhost_http_port = 7200
  40. ```
  41. 4. 启动frp服务端
  42. ```shell
  43. $ ./frps -c frps.ini
  44. 2019/06/15 16:42:02 [I] [service.go:139] frps tcp listen on 0.0.0.0:7100
  45. 2019/06/15 16:42:02 [I] [service.go:181] http service listen on 0.0.0.0:7200
  46. 2019/06/15 16:42:02 [I] [root.go:204] Start frps success
  47. ```
  48. #### 1.2.2. frp客户端搭建
  49. 客户端搭建在本地的Mac上,因此下载安装包版本为darwin_amd64的 [frp_0.27.0_darwin_amd64.tar.gz](https://github.com/fatedier/frp/releases/download/v0.27.0/frp_0.27.0_darwin_amd64.tar.gz) 。
  50. 1. 下载安装包
  51. ```shell
  52. $ wget https://github.com/fatedier/frp/releases/download/v0.27.0/frp_0.27.0_darwin_amd64.tar.gz
  53. ```
  54. 2. 解压安装包
  55. ```shell
  56. $ tar -zxvf frp_0.27.0_darwin_amd64.tar.gz
  57. ```
  58. 3. 修改配置文件,配置服务端ip端口及监听的域名信息
  59. ```shell
  60. $ cd frp_0.27.0_darwin_amd64
  61. $ vim frpc.ini
  62. [common]
  63. server_addr = 120.92.169.103
  64. server_port = 7100
  65. [web]
  66. type = http
  67. local_port = 8080
  68. custom_domains = oauth.xkcoding.com
  69. ```
  70. 4. 启动frp客户端
  71. ```shell
  72. $ ./frpc -c frpc.ini
  73. 2019/06/15 16:48:52 [I] [service.go:221] login to server success, get run id [8bb83bae5c58afe6], server udp port [0]
  74. 2019/06/15 16:48:52 [I] [proxy_manager.go:137] [8bb83bae5c58afe6] proxy added: [web]
  75. 2019/06/15 16:48:52 [I] [control.go:144] [web] start proxy success
  76. ```
  77. ### 1.3. 配置域名解析
  78. 前往阿里云DNS解析,将域名解析到我们的公网服务器上,比如我的就是将 `oauth.xkcoding.com -> 120.92.169.103`
  79. ![image-20190615165843639](assets/image-20190615165843639.png)
  80. ### 1.4. nginx代理
  81. nginx 的搭建就不在此赘述了,只说配置
  82. ```nginx
  83. server {
  84. listen 80;
  85. server_name oauth.xkcoding.com;
  86. location / {
  87. proxy_pass http://127.0.0.1:7200;
  88. proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  89. proxy_set_header Host $http_host;
  90. proxy_set_header X-Forwarded-Proto $scheme;
  91. proxy_set_header X-Real-IP $remote_addr;
  92. proxy_buffering off;
  93. sendfile off;
  94. proxy_max_temp_file_size 0;
  95. client_max_body_size 10m;
  96. client_body_buffer_size 128k;
  97. proxy_connect_timeout 90;
  98. proxy_send_timeout 90;
  99. proxy_read_timeout 90;
  100. proxy_temp_file_write_size 64k;
  101. proxy_http_version 1.1;
  102. proxy_request_buffering off;
  103. }
  104. }
  105. ```
  106. 测试配置文件是否有问题
  107. ```shell
  108. $ nginx -t
  109. nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
  110. nginx: configuration file /etc/nginx/nginx.conf test is successful
  111. ```
  112. 重新加载配置文件,使其生效
  113. ```shell
  114. $ nginx -s reload
  115. ```
  116. > 现在当我们在浏览器输入 `oauth.xkcoding.com` 的时候,网络流量其实会经历以下几个步骤:
  117. >
  118. > 1. 通过之前配的DNS域名解析会访问到我们的公网服务器 `120.92.169.103` 的 80 端口
  119. > 2. 再经过 nginx,代理到本地的 7200 端口
  120. > 3. 再经过 frp 穿透到我们的 Mac 电脑的 8080 端口
  121. > 4. 此时 8080 就是我们的应用程序端口
  122. ### 1.5. 第三方平台申请
  123. #### 1.5.1. QQ互联平台申请
  124. 1. 前往 https://connect.qq.com/
  125. 2. 申请开发者
  126. 3. 应用管理 -> 添加网站应用,等待审核通过即可
  127. ![image-20190617144655429](assets/image-20190617144655429.png)
  128. #### 1.5.2. GitHub平台申请
  129. 1. 前往 https://github.com/settings/developers
  130. 2. 点击 `New OAuth App` 按钮创建应用
  131. ![image-20190617145839851](assets/image-20190617145839851.png)
  132. #### 1.5.3 微信开放平台申请
  133. 这里微信开放平台需要用企业的,个人没有资质,所以我在某宝租了一个月的资质,需要的可以 [戳我租赁](https://item.taobao.com/item.htm?spm=2013.1.w4023-5034755838.13.747a61a7ccfHwS&id=554942413474)
  134. > 声明:本人与该店铺无利益相关,纯属个人觉得好用做分享
  135. >
  136. > 该店铺有两种方式:
  137. >
  138. > 1. 店铺支持帮你过企业资质,这里就用你自己的开放平台号就好了
  139. > 2. 临时使用可以问店家租一个月进行开发,这里租了之后,店家会把 AppID 和 AppSecret 的信息发给你,你提供回调域就好了
  140. 因此这里我就贴出一张授权回调的地址作参考。
  141. ![image-20190617153552218](assets/image-20190617153552218.png)
  142. #### 1.5.4. 谷歌开放平台申请
  143. 1. 前往 https://console.developers.google.com/projectcreate 创建项目
  144. 2. 前往 https://console.developers.google.com/apis/credentials ,在第一步创建的项目下,添加应用
  145. ![image-20190617151119584](assets/image-20190617151119584.png)
  146. ![image-20190617150903039](assets/image-20190617150903039.png)
  147. #### 1.5.5. 微软开放平台申请
  148. 1. 前往 https://portal.azure.com/#blade/Microsoft_AAD_RegisteredApps/ApplicationsListBlade 注册应用
  149. 2. 在注册应用的时候就需要填写回调地址,当然后期也可以重新修改
  150. ![image-20190617152529449](assets/image-20190617152529449.png)
  151. 3. client id 在这里
  152. ![image-20190617152805581](assets/image-20190617152805581.png)
  153. 4. client secret 需要自己在这里生成
  154. ![image-20190617152711938](assets/image-20190617152711938.png)
  155. #### 1.5.6. 小米开放平台申请
  156. 1. 申请小米开发者,审核通过
  157. 2. 前往 https://dev.mi.com/passport/oauth2/applist 添加oauth应用,选择 `创建网页应用`
  158. 3. 填写基本信息之后,进入应用信息页面填写 `回调地址`
  159. ![image-20190617151502414](assets/image-20190617151502414.png)
  160. 4. 应用审核通过之后,可以在应用信息页面的 `应用详情` 查看到 AppKey 和 AppSecret,吐槽下,小米应用的审核速度特别慢,需要耐心等待。。。。
  161. ![image-20190617151624603](assets/image-20190617151624603.png)
  162. ## 2. 主要代码
  163. ### 2.1. pom.xml
  164. ```xml
  165. <?xml version="1.0" encoding="UTF-8"?>
  166. <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  167. xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  168. <modelVersion>4.0.0</modelVersion>
  169. <artifactId>spring-boot-demo-social</artifactId>
  170. <version>1.0.0-SNAPSHOT</version>
  171. <packaging>jar</packaging>
  172. <name>spring-boot-demo-social</name>
  173. <description>Demo project for Spring Boot</description>
  174. <parent>
  175. <groupId>com.xkcoding</groupId>
  176. <artifactId>spring-boot-demo</artifactId>
  177. <version>1.0.0-SNAPSHOT</version>
  178. </parent>
  179. <properties>
  180. <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  181. <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
  182. <java.version>1.8</java.version>
  183. <spring.social.version>1.1.6.RELEASE</spring.social.version>
  184. </properties>
  185. <dependencies>
  186. <dependency>
  187. <groupId>org.springframework.boot</groupId>
  188. <artifactId>spring-boot-starter-web</artifactId>
  189. </dependency>
  190. <dependency>
  191. <groupId>org.springframework.boot</groupId>
  192. <artifactId>spring-boot-starter-test</artifactId>
  193. <scope>test</scope>
  194. </dependency>
  195. <!-- oauth工具类 -->
  196. <dependency>
  197. <groupId>me.zhyd.oauth</groupId>
  198. <artifactId>JustAuth</artifactId>
  199. <version>1.9.5</version>
  200. </dependency>
  201. <dependency>
  202. <groupId>org.projectlombok</groupId>
  203. <artifactId>lombok</artifactId>
  204. <optional>true</optional>
  205. </dependency>
  206. <dependency>
  207. <groupId>com.google.guava</groupId>
  208. <artifactId>guava</artifactId>
  209. </dependency>
  210. <dependency>
  211. <groupId>cn.hutool</groupId>
  212. <artifactId>hutool-all</artifactId>
  213. </dependency>
  214. </dependencies>
  215. <build>
  216. <finalName>spring-boot-demo-social</finalName>
  217. <plugins>
  218. <plugin>
  219. <groupId>org.springframework.boot</groupId>
  220. <artifactId>spring-boot-maven-plugin</artifactId>
  221. </plugin>
  222. </plugins>
  223. </build>
  224. </project>
  225. ```
  226. ### 2.2. application.yml
  227. ```yaml
  228. server:
  229. port: 8080
  230. servlet:
  231. context-path: /demo
  232. oauth:
  233. qq:
  234. client-id: 1015*****
  235. client-secret: 1f7d08df55766**************
  236. redirect-uri: http://oauth.xkcoding.com/demo/oauth/qq/callback
  237. github:
  238. client-id: 2d25a70**************
  239. client-secret: 5a2919b5fe911567343**************
  240. redirect-uri: http://oauth.xkcoding.com/demo/oauth/github/callback
  241. wechat:
  242. client-id: wxdcb31**************
  243. client-secret: b4e9dc6841ef7d**************
  244. redirect-uri: http://oauth.xkcoding.com/demo/oauth/wechat/callback
  245. google:
  246. client-id: 716518501517-6dbdkapivhia806vqcjjh9nttj3**************
  247. client-secret: 9IBornd7w1A**************
  248. redirect-uri: http://oauth.xkcoding.com/demo/oauth/google/callback
  249. microsoft:
  250. client-id: 7bdce818-2c8e-4b**************
  251. client-secret: Iu0zZ43RQydo_FkD**************
  252. redirect-uri: https://oauth.xkcoding.com/demo/oauth/microsoft/callback
  253. mi:
  254. client-id: 2882303**************
  255. client-secret: nFeTt89Yn**************
  256. redirect-uri: http://oauth.xkcoding.com/demo/oauth/mi/callback
  257. ```
  258. ### 2.3. OAuthProperties.java
  259. ```java
  260. /**
  261. * <p>
  262. * 第三方登录配置
  263. * </p>
  264. *
  265. * @package: com.xkcoding.oauth.config.props
  266. * @description: 第三方登录配置
  267. * @author: yangkai.shen
  268. * @date: Created in 2019-05-17 15:33
  269. * @copyright: Copyright (c) 2019
  270. * @version: V1.0
  271. * @modified: yangkai.shen
  272. */
  273. @Data
  274. @Component
  275. @ConfigurationProperties(prefix = "oauth")
  276. public class OAuthProperties {
  277. /**
  278. * QQ 配置
  279. */
  280. private AuthConfig qq;
  281. /**
  282. * github 配置
  283. */
  284. private AuthConfig github;
  285. /**
  286. * 微信 配置
  287. */
  288. private AuthConfig wechat;
  289. /**
  290. * Google 配置
  291. */
  292. private AuthConfig google;
  293. /**
  294. * Microsoft 配置
  295. */
  296. private AuthConfig microsoft;
  297. /**
  298. * Mi 配置
  299. */
  300. private AuthConfig mi;
  301. }
  302. ```
  303. ### 2.4. OauthController.java
  304. ```java
  305. package com.xkcoding.social.controller;
  306. import cn.hutool.core.lang.Dict;
  307. import cn.hutool.json.JSONUtil;
  308. import com.xkcoding.social.props.OAuthProperties;
  309. import lombok.RequiredArgsConstructor;
  310. import lombok.extern.slf4j.Slf4j;
  311. import me.zhyd.oauth.config.AuthConfig;
  312. import me.zhyd.oauth.config.AuthSource;
  313. import me.zhyd.oauth.model.AuthCallback;
  314. import me.zhyd.oauth.model.AuthResponse;
  315. import me.zhyd.oauth.request.*;
  316. import me.zhyd.oauth.utils.AuthStateUtils;
  317. import org.springframework.beans.factory.annotation.Autowired;
  318. import org.springframework.web.bind.annotation.GetMapping;
  319. import org.springframework.web.bind.annotation.PathVariable;
  320. import org.springframework.web.bind.annotation.RequestMapping;
  321. import org.springframework.web.bind.annotation.RestController;
  322. import javax.servlet.http.HttpServletResponse;
  323. import java.io.IOException;
  324. /**
  325. * <p>
  326. * 第三方登录 Controller
  327. * </p>
  328. *
  329. * @package: com.xkcoding.oauth.controller
  330. * @description: 第三方登录 Controller
  331. * @author: yangkai.shen
  332. * @date: Created in 2019-05-17 10:07
  333. * @copyright: Copyright (c) 2019
  334. * @version: V1.0
  335. * @modified: yangkai.shen
  336. */
  337. @Slf4j
  338. @RestController
  339. @RequestMapping("/oauth")
  340. @RequiredArgsConstructor(onConstructor_ = @Autowired)
  341. public class OauthController {
  342. private final OAuthProperties properties;
  343. /**
  344. * 登录类型
  345. */
  346. @GetMapping
  347. public Dict loginType() {
  348. return Dict.create().set("QQ登录", "http://oauth.xkcoding.com/demo/oauth/login/qq").set("GitHub登录", "http://oauth.xkcoding.com/demo/oauth/login/github").set("微信登录", "http://oauth.xkcoding.com/demo/oauth/login/wechat").set("Google登录", "http://oauth.xkcoding.com/demo/oauth/login/google").set("Microsoft 登录", "http://oauth.xkcoding.com/demo/oauth/login/microsoft").set("小米登录", "http://oauth.xkcoding.com/demo/oauth/login/mi");
  349. }
  350. /**
  351. * 登录
  352. *
  353. * @param oauthType 第三方登录类型
  354. * @param response response
  355. * @throws IOException
  356. */
  357. @RequestMapping("/login/{oauthType}")
  358. public void renderAuth(@PathVariable String oauthType, HttpServletResponse response) throws IOException {
  359. AuthRequest authRequest = getAuthRequest(oauthType);
  360. response.sendRedirect(authRequest.authorize(AuthStateUtils.createState()));
  361. }
  362. /**
  363. * 登录成功后的回调
  364. *
  365. * @param oauthType 第三方登录类型
  366. * @param callback 携带返回的信息
  367. * @return 登录成功后的信息
  368. */
  369. @RequestMapping("/{oauthType}/callback")
  370. public AuthResponse login(@PathVariable String oauthType, AuthCallback callback) {
  371. AuthRequest authRequest = getAuthRequest(oauthType);
  372. AuthResponse response = authRequest.login(callback);
  373. log.info("【response】= {}", JSONUtil.toJsonStr(response));
  374. return response;
  375. }
  376. private AuthRequest getAuthRequest(String oauthType) {
  377. AuthSource authSource = AuthSource.valueOf(oauthType.toUpperCase());
  378. switch (authSource) {
  379. case QQ:
  380. return getQqAuthRequest();
  381. case GITHUB:
  382. return getGithubAuthRequest();
  383. case WECHAT:
  384. return getWechatAuthRequest();
  385. case GOOGLE:
  386. return getGoogleAuthRequest();
  387. case MICROSOFT:
  388. return getMicrosoftAuthRequest();
  389. case MI:
  390. return getMiAuthRequest();
  391. default:
  392. throw new RuntimeException("暂不支持的第三方登录");
  393. }
  394. }
  395. private AuthRequest getQqAuthRequest() {
  396. AuthConfig authConfig = properties.getQq();
  397. return new AuthQqRequest(authConfig);
  398. }
  399. private AuthRequest getGithubAuthRequest() {
  400. AuthConfig authConfig = properties.getGithub();
  401. return new AuthGithubRequest(authConfig);
  402. }
  403. private AuthRequest getWechatAuthRequest() {
  404. AuthConfig authConfig = properties.getWechat();
  405. return new AuthWeChatRequest(authConfig);
  406. }
  407. private AuthRequest getGoogleAuthRequest() {
  408. AuthConfig authConfig = properties.getGoogle();
  409. return new AuthGoogleRequest(authConfig);
  410. }
  411. private AuthRequest getMicrosoftAuthRequest() {
  412. AuthConfig authConfig = properties.getMicrosoft();
  413. return new AuthMicrosoftRequest(authConfig);
  414. }
  415. private AuthRequest getMiAuthRequest() {
  416. AuthConfig authConfig = properties.getMi();
  417. return new AuthMiRequest(authConfig);
  418. }
  419. }
  420. ```
  421. ## 3. 运行方式
  422. 打开浏览器,输入 http://oauth.xkcoding.com/demo/oauth ,点击各个登录方式自行测试。
  423. > `Google 登录,有可能因为祖国的强大导致测试失败,自行解决~` :kissing_smiling_eyes:
  424. ![image-20190617154343815](assets/image-20190617154343815.png)
  425. ## 参考
  426. 1. JustAuth 项目地址:https://github.com/zhangyd-c/JustAuth
  427. 2. frp内网穿透项目地址:https://github.com/fatedier/frp
  428. 3. frp内网穿透官方中文文档:https://github.com/fatedier/frp/blob/master/README_zh.md
  429. 4. Frp实现内网穿透:https://zhuanlan.zhihu.com/p/45445979
  430. 5. QQ互联文档:http://wiki.connect.qq.com/%E5%87%86%E5%A4%87%E5%B7%A5%E4%BD%9C_oauth2-0
  431. 6. 微信开放平台文档:https://open.weixin.qq.com/cgi-bin/showdocument?action=dir_list&t=resource/res_list&verify=1&id=open1419316505&token=&lang=zh_CN
  432. 7. GitHub第三方登录文档:https://developer.github.com/apps/building-oauth-apps/
  433. 8. 谷歌Oauth2文档:https://developers.google.com/identity/protocols/OpenIDConnect
  434. 9. 微软Oauth2文档:https://docs.microsoft.com/zh-cn/graph/auth-v2-user
  435. 10. 小米开放平台账号服务文档:https://dev.mi.com/console/doc/detail?pId=707

一个用来深度学习并实战 spring boot 的项目,目前总共包含 66 个集成demo,已经完成 55 个。

Contributors (1)