前端权限控制代码
使用场景:
前端页面根据权限码,对页面模块、组件的显示控制。支持场景:
- 在js代码里,进行同步、异步权限判断、拦截登操作;
- 在templete里通过v-if指令,控制组件、元素的显示;
API说明:
// 从服务端获取权限数据
getAuthData: () => void;
// 【同步】检查是否具备权限函数
checkHasAuth: (auth: AuthKey, data?: AuthRecords) => boolean;
// 【异步】检查是否具备权限函数(会等待权限数据,适合在js同步代码里做权限判断、拦截)
asyncCheckHasAuth: (auth: AuthKey, data?: AuthRecords) => Promise<boolean>;
// 【computed函数计算】是否具备权限
computedHasAuth: ComputedRef<(auth: AuthKey, data?: AuthRecords) => boolean>;
// 设置权限数据
setAuthData: (authData: AuthRecords) => void;
// 清除权限数据
clearAuthData: () => void;
完整代码:
import { watch, ref, type Ref, type ComputedRef } from "vue";
type AuthRecords = string[] | undefined;
type AuthKey = string | string[];
interface Auth {
// 从服务端获取权限数据
getAuthData: () => void;
// 【同步】检查是否具备权限函数
checkHasAuth: (auth: AuthKey, data?: AuthRecords) => boolean;
// 【异步】检查是否具备权限函数(会等待权限数据,适合在js同步代码里做权限判断、拦截)
asyncCheckHasAuth: (auth: AuthKey, data?: AuthRecords) => Promise<boolean>;
// 【computed函数计算】是否具备权限
computedHasAuth: ComputedRef<(auth: AuthKey, data?: AuthRecords) => boolean>;
// 设置权限数据
setAuthData: (authData: AuthRecords) => void;
// 清除权限数据
clearAuthData: () => void;
}
function useAuth() {
// 权限记录表
const authData: Ref<AuthRecords> = ref<AuthRecords>();
/**
* 获取权限数据
*/
async function getAuthData() {
// reset data
setAuthData(undefined);
// TODO
// const data = await ****
// authData.value = data;
}
/**
* 同步检查是否具备权限函数
* @param auth
* @returns boolean
*/
function checkHasAuth(auth: AuthKey, data?: AuthRecords) {
const authdata = data || authData.value;
// 权限数据未赋值时,都视为没有权限
if (authdata === undefined || authData === null) return false;
if (typeof auth === 'string') return authdata?.includes(auth)
if (Array.isArray(auth)){
for(const key of auth) {
if (!authdata?.includes(key)) return false;
}
}
return true;
}
/**
* 异步检查是否具备权限函数(会等待权限数据,适合在js同步代码里做权限判断、拦截)
* @param auth
* @returns boolean
*/
function asyncCheckHasAuth(auth: AuthKey, data?: AuthRecords): Promise<boolean> {
if (authData.value) {
return Promise.resolve(checkHasAuth(auth, data));
}
return new Promise((reslove) => {
const stopWatch = watch(authData, (value: any) => {
if (value){
reslove(checkHasAuth(auth, data))
stopWatch();
}
}, {
immediate: true,
deep: true
})
})
}
/**
* 计算是否具备权限
* @param auth
* @returns
*/
const computedHasAuth = computed(() => (auth: AuthKey) => checkHasAuth(auth, authData.value));
/**
* 设置同步权限数据
* @param authData
*/
function setAuthData(data: AuthRecords) {
authData.value = data;
}
/**
* 清除权限数据
*/
function clearAuthData(){
authData.value = []
}
return {
checkHasAuth,
asyncCheckHasAuth,
computedHasAuth,
setAuthData,
clearAuthData,
getAuthData
}
}
案例:
在js里同步、异步判断:
....
// 同步判断
const hasAuth = checkHasAuth('string');
....
....
// 异步判断
const hasAuth = await asyncCheckHasAuth('string');
....
多种权限组合判断:
....
const hasAuth = checkHasAuth(['abc', 'bcd']);
....
在templete里:
<templete>
....
<div v-if="computedHasAuth('string')">
........
</div>
....
</templete>