<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-thymeleafartifactId>
dependency>
<dependency>
<groupId>org.apache.httpcomponentsgroupId>
<artifactId>httpclientartifactId>
<version>4.5.6version>
dependency>
<dependency>
<groupId>com.alibabagroupId>
<artifactId>fastjsonartifactId>
<version>1.2.51version>
dependency>
<dependency>
<groupId>me.zhyd.oauthgroupId>
<artifactId>JustAuthartifactId>
dependency>
<dependency>
<groupId>com.xkcoding.httpgroupId>
<artifactId>simple-httpartifactId>
dependency>
package com.ruoyi.web.controller.login;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.utils.uuid.IdUtils;
import com.ruoyi.framework.web.service.SysLoginService;
import me.zhyd.oauth.config.AuthConfig;
import me.zhyd.oauth.request.AuthGiteeRequest;
import me.zhyd.oauth.request.AuthRequest;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class GiteeLogin {
@Autowired
private SysLoginService loginService;
@GetMapping("/PreLoginByGitee")
public AjaxResult PreLoginByGitee() {
AjaxResult ajax = AjaxResult.success();
AuthRequest authRequest = new AuthGiteeRequest(AuthConfig.builder()
.clientId("自己gitee申请的")
.clientSecret("3自己gitee申请的 ")
.redirectUri("http://localhost/callback")
.build());
String uuid = IdUtils.fastUUID();
String authorizeUrl = authRequest.authorize(uuid);
//存储
ajax.put("authorizeUrl", authorizeUrl);
ajax.put("uuid", uuid);
return ajax;
}
@PostMapping("/loginByGitee")
public AjaxResult loginByGitee(@RequestBody LoginByOtherSourceBody loginByOtherSourceBody) {
AjaxResult ajax = AjaxResult.success();
String token = loginService
.loginByOtherSource(loginByOtherSourceBody.getCode(), loginByOtherSourceBody.getSource(), loginByOtherSourceBody.getUuid());
ajax.put(Constants.TOKEN, token);
return ajax;
}
}
public String loginByOtherSource(String code, String source, String uuid) {
//先到数据库查询这个人曾经有没有登录过,没有就注册
// 创建授权request
AuthRequest authRequest = new AuthGiteeRequest(AuthConfig.builder()
.clientId("自己gitee申请的")
.clientSecret("自己gitee申请的")
.redirectUri("http://localhost/callback")
.build());
AuthResponse<AuthUser> login = authRequest.login(AuthCallback.builder().state(uuid).code(code).build());
System.out.println(login);
//先查询数据库有没有该用户
AuthUser authUser = login.getData();
SysUser sysUser = new SysUser();
sysUser.setUserName(authUser.getUsername());
sysUser.setSource(authUser.getSource());
List<SysUser> sysUsers = userService.selectUserListNoDataScope(sysUser);
if (sysUsers.size() > 1) {
throw new ServiceException("第三方登录异常,账号重叠");
} else if (sysUsers.size() == 0) {
//相当于注册
sysUser.setNickName(authUser.getNickname());
sysUser.setAvatar(authUser.getAvatar());
sysUser.setEmail(authUser.getEmail());
sysUser.setRemark(authUser.getRemark());
userService.registerUserAndGetUserId(sysUser);
AsyncManager.me().execute(AsyncFactory.recordLogininfor(sysUser.getUserName(), Constants.REGISTER,
MessageUtils.message("user.register.success")));
} else {
sysUser = sysUsers.get(0);
}
AsyncManager.me().execute(AsyncFactory.recordLogininfor(sysUser.getUserName(), Constants.LOGIN_SUCCESS, MessageUtils.message("user.login.success")));
//注册成功或者是已经存在的用户
LoginUser loginUser =
new LoginUser(sysUser.getUserId(), sysUser.getDeptId(), sysUser, permissionService.getMenuPermission(sysUser));
recordLoginInfo(loginUser.getUserId());
// 生成token
return tokenService.createToken(loginUser);
}
source表示登录平台,如微信登录,支付宝登录,因为要确定用户的唯一性。username在不同的平台可能会重复,但是username+source就不会重复了。
AuthUser authUser = login.getData();
userService.selectUserListNoDataScope(sysUser);
@Override
public List<SysUser> selectUserListNoDataScope(SysUser user) {
return userMapper.selectUserList(user);
}
package com.ruoyi.web.controller.login;
public class LoginByOtherSourceBody {
private String code;
private String source;
private String uuid;
}
安全配置放行了若干接口
.antMatchers("/login", "/register", "/captchaImage", "/loginByGitee", "/PreLoginByGitee").anonymous()
export function PreLoginByGitee() {
return request({
url: '/PreLoginByGitee',
headers: {
isToken: false
},
method: 'get',
})
}
export function loginByGitee(code, uuid) {
const data = {
code,
source: "Gitee",
uuid
}
return request({
url: '/loginByGitee',
headers: {
isToken: false
},
method: 'post',
data: data
})
}
获取Gitee头像展示
import {login, logout, getInfo, loginByGitee} from '@/api/login'
// Gitee登录
LoginByGitee({commit}, body) {
return new Promise((resolve, reject) => {
loginByGitee(body.code, body.uuid).then(res => {
setToken(res.token)
commit('SET_TOKEN', res.token)
resolve()
}).catch(error => {
reject(error)
})
})
},
//获取Gitee头像展示
let avatar = "";
if (user.avatar == "" || user.avatar == null) {
avatar = require("@/assets/images/profile.jpg")
} else if (user.avatar.startsWith("http")) {
avatar = user.avatar
} else {
avatar = process.env.VUE_APP_BASE_API + user.avatar;
}
前端白名单放行
const whiteList = ['/login', '/auth-redirect', '/bind', '/register' ,'/callback']
<router-link class="link-type" :to="'/register'">立即注册router-link>
div>
<div style="width: 32px;height: 32px;margin-top: 5px;cursor: pointer;" title="利用Gitee登录" @click="giteeLogin">
<img style="height: 100%;width: 100%;" src="../assets/logo/gitee.png">
div>
methods点击事件
giteeLogin() {
PreLoginByGitee().then(res => {
Cookies.set("user-uuid", res.uuid)
window.location = res.authorizeUrl
})
},
<template>
<div v-loading="loading" style="height: 100%;width: 100%;">
正在加载中...
div>
template>
<script>
import Cookies from "js-cookie";
export default {
name: "loginByGitee",
data() {
return {
loading: true
}
},
mounted() {
this.loading = true;
console.log("uuid", Cookies.get("user-uuid"))
const formBody = {
uuid: Cookies.get("user-uuid"),
code: this.$route.query.code
}
this.$store.dispatch("LoginByGitee", formBody).then(() => {
this.$router.push({path: this.redirect || "/"}).catch(() => {
});
}).catch(() => {
this.loading = false;
});
}
}
script>
<style scoped>
style>
export function PreLoginByGitee() {
return request({
url: '/PreLoginByGitee',
headers: {
isToken: false
},
method: 'get',
})
}
export function loginByGitee(code, uuid) {
const data = {
code,
source: "Gitee",
uuid
}
return request({
url: '/loginByGitee',
headers: {
isToken: false
},
method: 'post',
data: data
})
}