feat: Oauth update
This commit is contained in:
@@ -1 +1,32 @@
|
|||||||
|
/** @format */
|
||||||
|
|
||||||
|
import web from "@/utils/axios/web.ts";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取所有Minio信息
|
||||||
|
*/
|
||||||
|
export const getAllMinioInfo = () => {
|
||||||
|
return web.request({
|
||||||
|
url: "/oss/minio/getAllMinioInfo",
|
||||||
|
method: "get",
|
||||||
|
});
|
||||||
|
};
|
||||||
|
/**
|
||||||
|
* 第三方登录
|
||||||
|
* @param type
|
||||||
|
*/
|
||||||
|
export const oauthLogin = (type: string) => {
|
||||||
|
return web.request({
|
||||||
|
url: "/oauth/render/" + type,
|
||||||
|
method: "get",
|
||||||
|
});
|
||||||
|
};
|
||||||
|
/**
|
||||||
|
* 获取用户信息
|
||||||
|
*/
|
||||||
|
export const geOauthtUserInfo = () => {
|
||||||
|
return web.request({
|
||||||
|
url: "/oauth/userInfo/",
|
||||||
|
method: "get",
|
||||||
|
});
|
||||||
|
};
|
||||||
|
50
src/components/LoadingPage/index.less
Normal file
50
src/components/LoadingPage/index.less
Normal file
@@ -0,0 +1,50 @@
|
|||||||
|
.splash-body {
|
||||||
|
align-items: center;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
height: 100vh;
|
||||||
|
overflow: hidden;
|
||||||
|
background-image: url("@/assets/images/background.png");
|
||||||
|
}
|
||||||
|
.gegga {
|
||||||
|
width: 0;
|
||||||
|
}
|
||||||
|
.snurra {
|
||||||
|
filter: url(#gegga);
|
||||||
|
}
|
||||||
|
.stopp1 {
|
||||||
|
stop-color: #f700a8;
|
||||||
|
}
|
||||||
|
.stopp2 {
|
||||||
|
stop-color: #ff8000;
|
||||||
|
}
|
||||||
|
.halvan {
|
||||||
|
animation: Snurra1 10s infinite linear;
|
||||||
|
stroke-dasharray: 180 800;
|
||||||
|
fill: none;
|
||||||
|
stroke: url(#gradient);
|
||||||
|
stroke-width: 23;
|
||||||
|
stroke-linecap: round;
|
||||||
|
}
|
||||||
|
.strecken {
|
||||||
|
animation: Snurra1 3s infinite linear;
|
||||||
|
stroke-dasharray: 26 54;
|
||||||
|
fill: none;
|
||||||
|
stroke: url(#gradient);
|
||||||
|
stroke-width: 23;
|
||||||
|
stroke-linecap: round;
|
||||||
|
}
|
||||||
|
.skugga {
|
||||||
|
filter: blur(5px);
|
||||||
|
opacity: 0.3;
|
||||||
|
position: absolute;
|
||||||
|
transform: translate(3px, 3px);
|
||||||
|
}
|
||||||
|
@keyframes Snurra1 {
|
||||||
|
0% {
|
||||||
|
stroke-dashoffset: 0;
|
||||||
|
}
|
||||||
|
100% {
|
||||||
|
stroke-dashoffset: -403px;
|
||||||
|
}
|
||||||
|
}
|
73
src/components/LoadingPage/index.tsx
Normal file
73
src/components/LoadingPage/index.tsx
Normal file
@@ -0,0 +1,73 @@
|
|||||||
|
/** @format */
|
||||||
|
|
||||||
|
import React, { useEffect } from "react";
|
||||||
|
import "./index.less";
|
||||||
|
import { geOauthtUserInfo } from "@/api/user";
|
||||||
|
import localforage from "localforage";
|
||||||
|
|
||||||
|
const LoadingPage: React.FC = () => {
|
||||||
|
async function getUserInfo() {
|
||||||
|
const res: any = await geOauthtUserInfo();
|
||||||
|
localforage.setItem("token", res.data.token).then();
|
||||||
|
localforage.setItem("userId", res.data.userId).then();
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
document.body.classList.add("loading-body");
|
||||||
|
getUserInfo().then(() => {
|
||||||
|
if (
|
||||||
|
localforage.getItem("token").then() !== null &&
|
||||||
|
localforage.getItem("userId").then() !== null
|
||||||
|
) {
|
||||||
|
window.location.href = "/main";
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return () => {
|
||||||
|
document.body.classList.remove("loading-body");
|
||||||
|
};
|
||||||
|
}, []);
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<svg className="gegga">
|
||||||
|
<defs>
|
||||||
|
<filter id="gegga">
|
||||||
|
<feGaussianBlur
|
||||||
|
in="SourceGraphic"
|
||||||
|
stdDeviation="7"
|
||||||
|
result="blur"></feGaussianBlur>
|
||||||
|
<feColorMatrix
|
||||||
|
in="blur"
|
||||||
|
mode="matrix"
|
||||||
|
values="1 0 0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 20 -10"
|
||||||
|
result="inreGegga"></feColorMatrix>
|
||||||
|
<feComposite
|
||||||
|
in="SourceGraphic"
|
||||||
|
in2="inreGegga"
|
||||||
|
operator="atop"></feComposite>
|
||||||
|
</filter>
|
||||||
|
</defs>
|
||||||
|
</svg>
|
||||||
|
<svg className="snurra" width="200" height="200" viewBox="0 0 200 200">
|
||||||
|
<defs>
|
||||||
|
<linearGradient id="linjärGradient">
|
||||||
|
<stop className="stopp1" offset="0"></stop>
|
||||||
|
<stop className="stopp2" offset="1"></stop>
|
||||||
|
</linearGradient>
|
||||||
|
<linearGradient
|
||||||
|
y2="160"
|
||||||
|
x2="160"
|
||||||
|
y1="40"
|
||||||
|
x1="40"
|
||||||
|
gradientUnits="userSpaceOnUse"
|
||||||
|
id="gradient"
|
||||||
|
xlinkHref="#linjärGradient"></linearGradient>
|
||||||
|
</defs>
|
||||||
|
<path
|
||||||
|
className="halvan"
|
||||||
|
d="m 164,100 c 0,-35.346224 -28.65378,-64 -64,-64 -35.346224,0 -64,28.653776 -64,64 0,35.34622 28.653776,64 64,64 35.34622,0 64,-26.21502 64,-64 0,-37.784981 -26.92058,-64 -64,-64 -37.079421,0 -65.267479,26.922736 -64,64 1.267479,37.07726 26.703171,65.05317 64,64 37.29683,-1.05317 64,-64 64,-64"></path>
|
||||||
|
<circle className="strecken" cx="100" cy="100" r="64"></circle>
|
||||||
|
</svg>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
export default React.memo(LoadingPage);
|
@@ -7,8 +7,8 @@ import Login from "./modules/login/index.ts";
|
|||||||
import Register from "./modules/register/index.ts";
|
import Register from "./modules/register/index.ts";
|
||||||
import home from "./modules/home/index.ts";
|
import home from "./modules/home/index.ts";
|
||||||
import Main from "./modules/main/index.ts";
|
import Main from "./modules/main/index.ts";
|
||||||
|
|
||||||
import ComponentLoading from "@/components/ComponentLoading";
|
import ComponentLoading from "@/components/ComponentLoading";
|
||||||
|
import Loading from "./modules/loading";
|
||||||
|
|
||||||
const routes: RouteObject[] = [
|
const routes: RouteObject[] = [
|
||||||
{
|
{
|
||||||
@@ -23,10 +23,6 @@ const routes: RouteObject[] = [
|
|||||||
path: "/register",
|
path: "/register",
|
||||||
Component: (props) => ComponentLoading(Register, props),
|
Component: (props) => ComponentLoading(Register, props),
|
||||||
},
|
},
|
||||||
// {
|
|
||||||
// path: '/home',
|
|
||||||
// Component: home,
|
|
||||||
// },
|
|
||||||
{
|
{
|
||||||
path: "/login",
|
path: "/login",
|
||||||
Component: (props) => ComponentLoading(Login, props),
|
Component: (props) => ComponentLoading(Login, props),
|
||||||
@@ -35,6 +31,10 @@ const routes: RouteObject[] = [
|
|||||||
path: "/main",
|
path: "/main",
|
||||||
Component: (props) => ComponentLoading(Main, props),
|
Component: (props) => ComponentLoading(Main, props),
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
path: "/loading",
|
||||||
|
Component: (props) => ComponentLoading(Loading, props),
|
||||||
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
export default routes;
|
export default routes;
|
||||||
|
11
src/router/modules/loading/index.ts
Normal file
11
src/router/modules/loading/index.ts
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
/** @format */
|
||||||
|
|
||||||
|
import { lazy } from "react";
|
||||||
|
|
||||||
|
const loading = lazy(
|
||||||
|
() =>
|
||||||
|
new Promise((resolve: any) => {
|
||||||
|
setTimeout(() => resolve(import("@/components/LoadingPage")), 0);
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
export default loading;
|
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
import axios, { AxiosInstance, AxiosRequestConfig } from "axios";
|
import axios, { AxiosInstance, AxiosRequestConfig } from "axios";
|
||||||
import { message } from "antd";
|
import { message } from "antd";
|
||||||
|
import { DecryptData, EncryptData } from "@/utils/encrypt/encrypt.ts";
|
||||||
|
|
||||||
class Request {
|
class Request {
|
||||||
private instance: AxiosInstance | undefined;
|
private instance: AxiosInstance | undefined;
|
||||||
@@ -11,6 +12,9 @@ class Request {
|
|||||||
// 全局请求拦截
|
// 全局请求拦截
|
||||||
this.instance.interceptors.request.use(
|
this.instance.interceptors.request.use(
|
||||||
(config) => {
|
(config) => {
|
||||||
|
if (config.method == "post") {
|
||||||
|
config.data = EncryptData(JSON.stringify(config.data));
|
||||||
|
}
|
||||||
return config;
|
return config;
|
||||||
},
|
},
|
||||||
(error) => {
|
(error) => {
|
||||||
@@ -20,12 +24,16 @@ class Request {
|
|||||||
|
|
||||||
// 全局响应拦截
|
// 全局响应拦截
|
||||||
this.instance.interceptors.response.use(
|
this.instance.interceptors.response.use(
|
||||||
(res) => {
|
(response) => {
|
||||||
// if (res.data.code && res.data.code !== 200) {
|
// 后端返回字符串表示需要解密操作
|
||||||
// message.error(res.data.message).then()
|
if (typeof response.data == "string") {
|
||||||
// return Promise.reject(res.data)
|
response.data = DecryptData(response.data);
|
||||||
// }
|
if (!response.data.code && response.data.code !== 200) {
|
||||||
return res.data;
|
message.error(response.data.message).then();
|
||||||
|
return Promise.reject(response.data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return response.data;
|
||||||
},
|
},
|
||||||
(error) => {
|
(error) => {
|
||||||
const { response } = error;
|
const { response } = error;
|
||||||
|
@@ -1,173 +1,29 @@
|
|||||||
/** @format */
|
/** @format */
|
||||||
|
|
||||||
import JSEncrypt from "jsencrypt";
|
|
||||||
import CryptoJS from "crypto-js";
|
import CryptoJS from "crypto-js";
|
||||||
|
|
||||||
|
const key = CryptoJS.enc.Hex.parse("d86d7bab3d6ac01ad9dc6a897652f2d2");
|
||||||
|
// const iv = CryptoJS.enc.Latin1.parse("d86d7bab3d6ac01ad9dc6a897652f2d2");
|
||||||
|
|
||||||
// 加密
|
// 加密
|
||||||
export function rsaEncrypt(Str: string, afterPublicKey: string) {
|
function EncryptData(data: any) {
|
||||||
const encryptor = new JSEncrypt();
|
const srcs = CryptoJS.enc.Utf8.parse(data);
|
||||||
encryptor.setPublicKey(afterPublicKey); // 设置公钥
|
|
||||||
return encryptor.encrypt(Str); // 对数据进行加密
|
|
||||||
}
|
|
||||||
|
|
||||||
// 解密
|
|
||||||
export function rsaDecrypt(Str: string, frontPrivateKey: string) {
|
|
||||||
const encryptor = new JSEncrypt();
|
|
||||||
encryptor.setPrivateKey(frontPrivateKey); // 设置私钥
|
|
||||||
return encryptor.decrypt(Str); // 对数据进行解密
|
|
||||||
}
|
|
||||||
|
|
||||||
export function aesEncrypt(aeskey: string, Str: string) {
|
|
||||||
// 设置一个默认值,如果第二个参数为空采用默认值,不为空则采用新设置的密钥
|
|
||||||
const key = CryptoJS.enc.Utf8.parse(aeskey);
|
|
||||||
const srcs = CryptoJS.enc.Utf8.parse(Str);
|
|
||||||
const encrypted = CryptoJS.AES.encrypt(srcs, key, {
|
const encrypted = CryptoJS.AES.encrypt(srcs, key, {
|
||||||
// 切记 需要和后端算法模式一致
|
|
||||||
mode: CryptoJS.mode.ECB,
|
mode: CryptoJS.mode.ECB,
|
||||||
padding: CryptoJS.pad.Pkcs7,
|
padding: CryptoJS.pad.Pkcs7,
|
||||||
});
|
});
|
||||||
|
|
||||||
return encrypted.toString();
|
return encrypted.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
export function aesDecrypt(aeskey: string, Str: string) {
|
// 解密
|
||||||
const key = CryptoJS.enc.Utf8.parse(aeskey);
|
function DecryptData(data: any) {
|
||||||
const decrypt = CryptoJS.AES.decrypt(Str, key, {
|
// const stime = new Date().getTime();
|
||||||
// 切记 需要和后端算法模式一致
|
const decrypt = CryptoJS.AES.decrypt(data, key, {
|
||||||
mode: CryptoJS.mode.ECB,
|
mode: CryptoJS.mode.ECB,
|
||||||
padding: CryptoJS.pad.Pkcs7,
|
padding: CryptoJS.pad.Pkcs7,
|
||||||
});
|
});
|
||||||
return CryptoJS.enc.Utf8.stringify(decrypt).toString();
|
const result = JSON.parse(CryptoJS.enc.Utf8.stringify(decrypt).toString());
|
||||||
}
|
// const etime = new Date().getTime();
|
||||||
|
// console.log("DecryptData Time:" + (etime - stime));
|
||||||
/**
|
return result;
|
||||||
* 获取16位随机码AES
|
|
||||||
* @returns {string}
|
|
||||||
*/
|
|
||||||
export function get16RandomNum() {
|
|
||||||
const chars = [
|
|
||||||
"0",
|
|
||||||
"1",
|
|
||||||
"2",
|
|
||||||
"3",
|
|
||||||
"4",
|
|
||||||
"5",
|
|
||||||
"6",
|
|
||||||
"7",
|
|
||||||
"8",
|
|
||||||
"9",
|
|
||||||
"A",
|
|
||||||
"B",
|
|
||||||
"C",
|
|
||||||
"D",
|
|
||||||
"E",
|
|
||||||
"F",
|
|
||||||
"G",
|
|
||||||
"H",
|
|
||||||
"I",
|
|
||||||
"J",
|
|
||||||
"K",
|
|
||||||
"L",
|
|
||||||
"M",
|
|
||||||
"N",
|
|
||||||
"O",
|
|
||||||
"P",
|
|
||||||
"Q",
|
|
||||||
"R",
|
|
||||||
"S",
|
|
||||||
"T",
|
|
||||||
"U",
|
|
||||||
"V",
|
|
||||||
"W",
|
|
||||||
"X",
|
|
||||||
"Y",
|
|
||||||
"Z",
|
|
||||||
"a",
|
|
||||||
"b",
|
|
||||||
"c",
|
|
||||||
"d",
|
|
||||||
"e",
|
|
||||||
"f",
|
|
||||||
"g",
|
|
||||||
"h",
|
|
||||||
"i",
|
|
||||||
"j",
|
|
||||||
"k",
|
|
||||||
"l",
|
|
||||||
"m",
|
|
||||||
"n",
|
|
||||||
"o",
|
|
||||||
"p",
|
|
||||||
"q",
|
|
||||||
"r",
|
|
||||||
"s",
|
|
||||||
"t",
|
|
||||||
"u",
|
|
||||||
"v",
|
|
||||||
"w",
|
|
||||||
"x",
|
|
||||||
"y",
|
|
||||||
"z",
|
|
||||||
];
|
|
||||||
let nums = "";
|
|
||||||
//这个地方切记要选择16位,因为美国对密钥长度有限制,选择32位的话加解密会报错,需要根据jdk版本去修改相关jar包,有点恼火,选择16位就不用处理。
|
|
||||||
for (let i = 0; i < 16; i++) {
|
|
||||||
const id = parseInt(String(Math.random() * 61));
|
|
||||||
nums += chars[id];
|
|
||||||
}
|
|
||||||
return nums;
|
|
||||||
}
|
|
||||||
|
|
||||||
//获取rsa密钥对
|
|
||||||
export function getRsaKeys() {
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
window.crypto.subtle
|
|
||||||
.generateKey(
|
|
||||||
{
|
|
||||||
name: "RSA-OAEP",
|
|
||||||
modulusLength: 2048, //can be 1024, 2048, or 4096
|
|
||||||
publicExponent: new Uint8Array([0x01, 0x00, 0x01]),
|
|
||||||
hash: { name: "SHA-512" }, //can be "SHA-1", "SHA-256", "SHA-384", or "SHA-512"
|
|
||||||
},
|
|
||||||
true, //whether the key is extractable (i.e. can be used in exportKey)
|
|
||||||
["encrypt", "decrypt"], //must be ["encrypt", "decrypt"] or ["wrapKey", "unwrapKey"]
|
|
||||||
)
|
|
||||||
.then(function (key) {
|
|
||||||
window.crypto.subtle
|
|
||||||
.exportKey("pkcs8", key.privateKey)
|
|
||||||
.then(function (keydata1) {
|
|
||||||
window.crypto.subtle
|
|
||||||
.exportKey("spki", key.publicKey)
|
|
||||||
.then(function (keydata2) {
|
|
||||||
const privateKey = RSA2text(keydata1, 1);
|
|
||||||
|
|
||||||
const publicKey = RSA2text(keydata2);
|
|
||||||
|
|
||||||
resolve({ privateKey, publicKey });
|
|
||||||
})
|
|
||||||
.catch(function (err) {
|
|
||||||
reject(err);
|
|
||||||
});
|
|
||||||
})
|
|
||||||
.catch(function (err) {
|
|
||||||
reject(err);
|
|
||||||
});
|
|
||||||
})
|
|
||||||
.catch(function (err) {
|
|
||||||
reject(err);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
function RSA2text(buffer: any, _isPrivate: number = 0) {
|
|
||||||
let binary = "";
|
|
||||||
const bytes = new Uint8Array(buffer);
|
|
||||||
const len = bytes.byteLength;
|
|
||||||
for (let i = 0; i < len; i++) {
|
|
||||||
binary += String.fromCharCode(bytes[i]);
|
|
||||||
}
|
|
||||||
const base64 = window.btoa(binary);
|
|
||||||
const text = base64.replace(/[^\x00-\xff]/g, "$&\x01").replace(/.{64}\x01?/g, "$&\n");
|
|
||||||
|
|
||||||
return text;
|
|
||||||
}
|
}
|
||||||
|
export { EncryptData, DecryptData };
|
||||||
|
@@ -1,7 +1,7 @@
|
|||||||
/** @format */
|
/** @format */
|
||||||
|
|
||||||
import { useNavigate } from "react-router-dom";
|
import { useNavigate } from "react-router-dom";
|
||||||
// import "./index.less";
|
import "./index.less";
|
||||||
import { useEffect } from "react";
|
import { useEffect } from "react";
|
||||||
|
|
||||||
export default () => {
|
export default () => {
|
||||||
@@ -17,155 +17,153 @@ export default () => {
|
|||||||
}, []);
|
}, []);
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<body translate="no">
|
<div className="container container-star">
|
||||||
<div className="container container-star">
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-1"></div>
|
||||||
<div className="star-1"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
<div className="star-2"></div>
|
||||||
<div className="star-2"></div>
|
</div>
|
||||||
|
<div className="container container-bird">
|
||||||
|
<div className="bird bird-anim">
|
||||||
|
<div className="bird-container">
|
||||||
|
<div className="wing wing-left">
|
||||||
|
<div className="wing-left-top"></div>
|
||||||
|
</div>
|
||||||
|
<div className="wing wing-right">
|
||||||
|
<div className="wing-right-top"></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="container container-bird">
|
<div className="bird bird-anim">
|
||||||
<div className="bird bird-anim">
|
<div className="bird-container">
|
||||||
<div className="bird-container">
|
<div className="wing wing-left">
|
||||||
<div className="wing wing-left">
|
<div className="wing-left-top"></div>
|
||||||
<div className="wing-left-top"></div>
|
</div>
|
||||||
</div>
|
<div className="wing wing-right">
|
||||||
<div className="wing wing-right">
|
<div className="wing-right-top"></div>
|
||||||
<div className="wing-right-top"></div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="bird bird-anim">
|
</div>
|
||||||
<div className="bird-container">
|
<div className="bird bird-anim">
|
||||||
<div className="wing wing-left">
|
<div className="bird-container">
|
||||||
<div className="wing-left-top"></div>
|
<div className="wing wing-left">
|
||||||
</div>
|
<div className="wing-left-top"></div>
|
||||||
<div className="wing wing-right">
|
</div>
|
||||||
<div className="wing-right-top"></div>
|
<div className="wing wing-right">
|
||||||
</div>
|
<div className="wing-right-top"></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="bird bird-anim">
|
</div>
|
||||||
<div className="bird-container">
|
<div className="bird bird-anim">
|
||||||
<div className="wing wing-left">
|
<div className="bird-container">
|
||||||
<div className="wing-left-top"></div>
|
<div className="wing wing-left">
|
||||||
</div>
|
<div className="wing-left-top"></div>
|
||||||
<div className="wing wing-right">
|
</div>
|
||||||
<div className="wing-right-top"></div>
|
<div className="wing wing-right">
|
||||||
</div>
|
<div className="wing-right-top"></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="bird bird-anim">
|
</div>
|
||||||
<div className="bird-container">
|
<div className="bird bird-anim">
|
||||||
<div className="wing wing-left">
|
<div className="bird-container">
|
||||||
<div className="wing-left-top"></div>
|
<div className="wing wing-left">
|
||||||
</div>
|
<div className="wing-left-top"></div>
|
||||||
<div className="wing wing-right">
|
</div>
|
||||||
<div className="wing-right-top"></div>
|
<div className="wing wing-right">
|
||||||
</div>
|
<div className="wing-right-top"></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="bird bird-anim">
|
</div>
|
||||||
<div className="bird-container">
|
<div className="bird bird-anim">
|
||||||
<div className="wing wing-left">
|
<div className="bird-container">
|
||||||
<div className="wing-left-top"></div>
|
<div className="wing wing-left">
|
||||||
</div>
|
<div className="wing-left-top"></div>
|
||||||
<div className="wing wing-right">
|
</div>
|
||||||
<div className="wing-right-top"></div>
|
<div className="wing wing-right">
|
||||||
</div>
|
<div className="wing-right-top"></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="bird bird-anim">
|
</div>
|
||||||
<div className="bird-container">
|
<div className="container-title">
|
||||||
<div className="wing wing-left">
|
<div className="title">
|
||||||
<div className="wing-left-top"></div>
|
<div className="number">4</div>
|
||||||
</div>
|
<div className="moon">
|
||||||
<div className="wing wing-right">
|
<div className="face">
|
||||||
<div className="wing-right-top"></div>
|
<div className="mouth"></div>
|
||||||
</div>
|
<div className="eyes">
|
||||||
</div>
|
<div className="eye-left"></div>
|
||||||
</div>
|
<div className="eye-right"></div>
|
||||||
<div className="container-title">
|
|
||||||
<div className="title">
|
|
||||||
<div className="number">4</div>
|
|
||||||
<div className="moon">
|
|
||||||
<div className="face">
|
|
||||||
<div className="mouth"></div>
|
|
||||||
<div className="eyes">
|
|
||||||
<div className="eye-left"></div>
|
|
||||||
<div className="eye-right"></div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="number">4</div>
|
|
||||||
</div>
|
</div>
|
||||||
<div className="subtitle">Oops. Looks like you took a wrong turn.</div>
|
<div className="number">4</div>
|
||||||
<button
|
|
||||||
style={{
|
|
||||||
marginTop: "1.5em",
|
|
||||||
}}
|
|
||||||
onClick={goBack}>
|
|
||||||
Go back
|
|
||||||
</button>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div className="subtitle">Oops. Looks like you took a wrong turn.</div>
|
||||||
|
<button
|
||||||
|
style={{
|
||||||
|
marginTop: "1.5em",
|
||||||
|
}}
|
||||||
|
onClick={goBack}>
|
||||||
|
Go back
|
||||||
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</div>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@@ -1,10 +1,8 @@
|
|||||||
/** @format */
|
/** @format */
|
||||||
import { useEffect } from "react";
|
|
||||||
|
|
||||||
import MainContainer from "@/components/Home/main-container/MainContainer.tsx";
|
import MainContainer from "@/components/Home/main-container/MainContainer.tsx";
|
||||||
|
|
||||||
export default () => {
|
export default () => {
|
||||||
useEffect(() => {}, []);
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<MainContainer />
|
<MainContainer />
|
||||||
|
@@ -20,6 +20,7 @@ import { observer } from "mobx-react";
|
|||||||
import FooterComponent from "@/components/Footer";
|
import FooterComponent from "@/components/Footer";
|
||||||
import RotateCaptcha, { CaptchaInstance } from "react-rotate-captcha";
|
import RotateCaptcha, { CaptchaInstance } from "react-rotate-captcha";
|
||||||
import { get, load, verify } from "@/api/captcha/index.ts";
|
import { get, load, verify } from "@/api/captcha/index.ts";
|
||||||
|
import { oauthLogin } from "@/api/user";
|
||||||
// import useStore from '@/utils/store/useStore.tsx'
|
// import useStore from '@/utils/store/useStore.tsx'
|
||||||
type LoginType = "account" | "phone";
|
type LoginType = "account" | "phone";
|
||||||
|
|
||||||
@@ -53,6 +54,12 @@ export default observer(() => {
|
|||||||
key: "phone",
|
key: "phone",
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
|
async function oAuthLogin(type: string) {
|
||||||
|
const res: any = await oauthLogin(type);
|
||||||
|
window.location.href = res.data;
|
||||||
|
}
|
||||||
|
|
||||||
const [loginType, setLoginType] = useState<LoginType>("account");
|
const [loginType, setLoginType] = useState<LoginType>("account");
|
||||||
|
|
||||||
const onSubmit = async (formData: object) => {
|
const onSubmit = async (formData: object) => {
|
||||||
@@ -359,6 +366,9 @@ export default observer(() => {
|
|||||||
borderRadius: "50%",
|
borderRadius: "50%",
|
||||||
}}>
|
}}>
|
||||||
<GitlabOutlined
|
<GitlabOutlined
|
||||||
|
onClick={() => {
|
||||||
|
oAuthLogin("GITEE").then();
|
||||||
|
}}
|
||||||
style={{ ...iconStyles, color: "#FF6A10" }}
|
style={{ ...iconStyles, color: "#FF6A10" }}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
Reference in New Issue
Block a user