refactor: 登录超时逻辑

master
dap 6 months ago
parent 7535bd6096
commit 29dd4ce7f7

@ -1,3 +1,9 @@
import { $t } from '@vben/locales';
import { message } from 'ant-design-vue';
import { useAuthStore } from '#/store';
import { requestClient } from './request'; import { requestClient } from './request';
/** /**
@ -26,3 +32,35 @@ export function commonExport(url: string, data: Record<string, any>) {
responseType: 'blob', responseType: 'blob',
}); });
} }
/**
* 401 ?
*/
export class UnauthorizedException extends Error {}
/**
*
* api 401
*/
let isLogoutProcessing = false;
/**
*
* @throws UnauthorizedException
*/
export function handleUnauthorizedLogout() {
const timeoutMsg = $t('http.loginTimeout');
// 已经在登出过程中 不再执行
if (isLogoutProcessing) {
throw new UnauthorizedException(timeoutMsg);
}
isLogoutProcessing = true;
const userStore = useAuthStore();
userStore.logout().finally(() => {
message.error(timeoutMsg);
isLogoutProcessing = false;
});
// 不再执行下面逻辑
throw new UnauthorizedException(timeoutMsg);
}

@ -4,6 +4,7 @@
import type { HttpResponse } from '@vben/request'; import type { HttpResponse } from '@vben/request';
import { BUSINESS_SUCCESS_CODE, UNAUTHORIZED_CODE } from '@vben/constants';
import { useAppConfig } from '@vben/hooks'; import { useAppConfig } from '@vben/hooks';
import { $t } from '@vben/locales'; import { $t } from '@vben/locales';
import { preferences } from '@vben/preferences'; import { preferences } from '@vben/preferences';
@ -28,22 +29,13 @@ import {
} from '#/utils/encryption/crypto'; } from '#/utils/encryption/crypto';
import * as encryptUtil from '#/utils/encryption/jsencrypt'; import * as encryptUtil from '#/utils/encryption/jsencrypt';
import { handleUnauthorizedLogout } from './helper';
const { apiURL, clientId, enableEncrypt } = useAppConfig( const { apiURL, clientId, enableEncrypt } = useAppConfig(
import.meta.env, import.meta.env,
import.meta.env.PROD, import.meta.env.PROD,
); );
/**
*
* api 401
*/
let isLogoutProcessing = false;
/**
* 401 ?
*/
export class UnauthorizedException extends Error {}
function createRequestClient(baseURL: string) { function createRequestClient(baseURL: string) {
const client = new RequestClient({ const client = new RequestClient({
// 后端地址 // 后端地址
@ -173,21 +165,38 @@ function createRequestClient(baseURL: string) {
// 不进行任何处理,直接返回 // 不进行任何处理,直接返回
// 用于页面代码可能需要直接获取codedatamessage这些信息时开启 // 用于页面代码可能需要直接获取codedatamessage这些信息时开启
if (!isTransformResponse) { if (!isTransformResponse) {
/** // json数据的判断
* json if (response.headers['content-type']?.includes?.('application/json')) {
* typeblobcontent-typeapplication/json /**
*/ * /401
if ( *
response.config.responseType === 'blob' && */
response.headers['content-type']?.includes?.('application/json') const resp = response.data as unknown as HttpResponse;
) { // 抛出异常 不再执行
// 这时候的data为blob类型 if (
const blob = response.data as unknown as Blob; typeof resp === 'object' &&
// 拿到字符串转json对象 Reflect.has(resp, 'code') &&
response.data = JSON.parse(await blob.text()); resp.code === UNAUTHORIZED_CODE
// 然后按正常逻辑执行下面的代码(判断业务状态码) ) {
handleUnauthorizedLogout();
}
/**
* json
* typeblobcontent-typeapplication/json
*/
if (response.config.responseType === 'blob') {
// 这时候的data为blob类型
const blob = response.data as unknown as Blob;
// 拿到字符串转json对象
response.data = JSON.parse(await blob.text());
// 然后按正常逻辑执行下面的代码(判断业务状态码)
} else {
// 其他类型数据 直接返回
return response.data;
}
} else { } else {
// 其他情况 直接返回 // 非json数据 直接返回 不做校验
return response.data; return response.data;
} }
} }
@ -200,8 +209,10 @@ function createRequestClient(baseURL: string) {
// 后端并没有采用严格的{code, msg, data}模式 // 后端并没有采用严格的{code, msg, data}模式
const { code, data, msg, ...other } = axiosResponseData; const { code, data, msg, ...other } = axiosResponseData;
// 业务状态码为200则请求成功 // 业务状态码为200 则请求成功
const hasSuccess = Reflect.has(axiosResponseData, 'code') && code === 200; const hasSuccess =
Reflect.has(axiosResponseData, 'code') &&
code === BUSINESS_SUCCESS_CODE;
if (hasSuccess) { if (hasSuccess) {
let successMsg = msg; let successMsg = msg;
@ -230,20 +241,10 @@ function createRequestClient(baseURL: string) {
// 如果不希望中断当前请求请return数据否则直接抛出异常即可 // 如果不希望中断当前请求请return数据否则直接抛出异常即可
let timeoutMsg = ''; let timeoutMsg = '';
switch (code) { switch (code) {
case 401: { // 登录超时
// 已经在登出过程中 不再执行 case UNAUTHORIZED_CODE: {
if (isLogoutProcessing) { handleUnauthorizedLogout();
throw new UnauthorizedException(timeoutMsg); break;
}
isLogoutProcessing = true;
const _msg = $t('http.loginTimeout');
const userStore = useAuthStore();
userStore.logout().finally(() => {
message.error(_msg);
isLogoutProcessing = false;
});
// 不再执行下面逻辑
throw new UnauthorizedException(_msg);
} }
default: { default: {
if (msg) { if (msg) {

@ -1,4 +1,4 @@
import { UnauthorizedException } from '#/api/request'; import { UnauthorizedException } from '#/api/helper';
import { dictDataInfo } from '#/api/system/dict/dict-data'; import { dictDataInfo } from '#/api/system/dict/dict-data';
import { useDictStore } from '#/store/dict'; import { useDictStore } from '#/store/dict';

@ -26,3 +26,13 @@ export const SUPPORT_LANGUAGES: LanguageOption[] = [
* ID * ID
*/ */
export const DEFAULT_TENANT_ID = '000000'; export const DEFAULT_TENANT_ID = '000000';
/**
*
*/
export const BUSINESS_SUCCESS_CODE = 200;
/**
* ()
*/
export const UNAUTHORIZED_CODE = 401;

Loading…
Cancel
Save