20 changed files with 300 additions and 185 deletions
@ -1,3 +1,7 @@ |
|||||
import AppLocalPicker from './src/AppLocalPicker.vue'; |
import AppLocalPicker from './src/AppLocalPicker.vue'; |
||||
|
import AppFooterToolbar from './src/AppFooterToolbar.vue'; |
||||
|
import { withInstall } from '../util'; |
||||
|
|
||||
export { AppLocalPicker }; |
export { AppLocalPicker, AppFooterToolbar }; |
||||
|
|
||||
|
export default withInstall(AppLocalPicker, AppFooterToolbar); |
||||
|
|||||
@ -1,8 +1,7 @@ |
|||||
import type { App } from 'vue'; |
|
||||
import Authority from './src/index.vue'; |
import Authority from './src/index.vue'; |
||||
|
|
||||
export default (app: App): void => { |
import { withInstall } from '../util'; |
||||
app.component(Authority.name, Authority); |
|
||||
}; |
export default withInstall(Authority); |
||||
|
|
||||
export { Authority }; |
export { Authority }; |
||||
|
|||||
@ -1 +0,0 @@ |
|||||
export { default as AppFooter } from './src/index.vue'; |
|
||||
@ -1,10 +0,0 @@ |
|||||
// System default cache time, in seconds
|
|
||||
export const DEFAULT_CACHE_TIME = 60 * 60 * 24 * 7; |
|
||||
|
|
||||
/** |
|
||||
* @description: |
|
||||
*/ |
|
||||
export const storageCipher = { |
|
||||
key: '_12345678901234@', |
|
||||
iv: '@12345678901234_', |
|
||||
}; |
|
||||
@ -0,0 +1,13 @@ |
|||||
|
import { isDevMode } from '/@/utils/env'; |
||||
|
|
||||
|
// System default cache time, in seconds
|
||||
|
export const DEFAULT_CACHE_TIME = 60 * 60 * 24 * 7; |
||||
|
|
||||
|
// aes encryption key
|
||||
|
export const cacheCipher = { |
||||
|
key: '_12345678901234@', |
||||
|
iv: '@12345678901234_', |
||||
|
}; |
||||
|
|
||||
|
// Whether the system cache is encrypted using aes
|
||||
|
export const enableStorageEncryption = !isDevMode(); |
||||
@ -0,0 +1,78 @@ |
|||||
|
import { DEFAULT_CACHE_TIME } from '../../settings/encryptionSetting'; |
||||
|
import { getStorageShortName } from '/@/utils/helper/envHelper'; |
||||
|
import { cacheCipher } from '/@/settings/encryptionSetting'; |
||||
|
import Encryption from '/@/utils/encryption/aesEncryption'; |
||||
|
|
||||
|
export default class WebCookie { |
||||
|
private encryption: Encryption; |
||||
|
private hasEncrypt: boolean; |
||||
|
|
||||
|
constructor(hasEncrypt = true, key = cacheCipher.key, iv = cacheCipher.iv) { |
||||
|
const encryption = new Encryption({ key, iv }); |
||||
|
this.encryption = encryption; |
||||
|
this.hasEncrypt = hasEncrypt; |
||||
|
} |
||||
|
|
||||
|
private getKey(key: string) { |
||||
|
return `${getStorageShortName()}${key}`.toUpperCase(); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Add cookie |
||||
|
* @param name cookie key |
||||
|
* @param value cookie value |
||||
|
* @param expire |
||||
|
* If the expiration time is not set, the default management browser will automatically delete |
||||
|
* e.g: |
||||
|
* cookieData.set('name','value',) |
||||
|
*/ |
||||
|
setCookie(key: string, value: any, expire: number | null = DEFAULT_CACHE_TIME) { |
||||
|
value = this.hasEncrypt ? this.encryption.encryptByAES(JSON.stringify(value)) : value; |
||||
|
document.cookie = this.getKey(key) + '=' + value + '; Max-Age=' + expire; |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Get the cook value according to the key |
||||
|
* @param key cookie key |
||||
|
*/ |
||||
|
getCookie(key: string) { |
||||
|
const arr = document.cookie.split('; '); |
||||
|
for (let i = 0; i < arr.length; i++) { |
||||
|
const arr2 = arr[i].split('='); |
||||
|
if (arr2[0] === this.getKey(key)) { |
||||
|
let message: any = null; |
||||
|
const str = arr2[1]; |
||||
|
if (this.hasEncrypt && str) { |
||||
|
message = this.encryption.decryptByAES(str); |
||||
|
try { |
||||
|
return JSON.parse(message); |
||||
|
} catch (e) { |
||||
|
return str; |
||||
|
} |
||||
|
} |
||||
|
return str; |
||||
|
} |
||||
|
} |
||||
|
return ''; |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Delete cookie based on cookie key |
||||
|
* @param key cookie key |
||||
|
*/ |
||||
|
removeCookie(key: string) { |
||||
|
this.setCookie(key, 1, -1); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* clear cookie |
||||
|
*/ |
||||
|
clearCookie(): void { |
||||
|
const keys = document.cookie.match(/[^ =;]+(?==)/g); |
||||
|
if (keys) { |
||||
|
for (let i = keys.length; i--; ) { |
||||
|
document.cookie = keys[i] + '=0;expires=' + new Date(0).toUTCString(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -1,17 +1,20 @@ |
|||||
import { getStorageShortName } from '/@/utils/helper/envHelper'; |
import { getStorageShortName } from '/@/utils/helper/envHelper'; |
||||
import { createStorage as create } from './Storage'; |
import { createStorage as create } from './storageCache'; |
||||
|
import { enableStorageEncryption } from '/@/settings/encryptionSetting'; |
||||
// debug模式下不加密
|
|
||||
|
|
||||
const createOptions = (storage = sessionStorage) => { |
const createOptions = (storage = sessionStorage) => { |
||||
return { |
return { |
||||
|
// No encryption in debug mode
|
||||
|
hasEncrypt: enableStorageEncryption, |
||||
storage, |
storage, |
||||
prefixKey: getStorageShortName(), |
prefixKey: getStorageShortName(), |
||||
}; |
}; |
||||
}; |
}; |
||||
|
|
||||
export const WebStorage = create(createOptions()); |
export const WebStorage = create(createOptions()); |
||||
|
|
||||
export const createStorage = (storage: Storage = sessionStorage) => { |
export const createStorage = (storage: Storage = sessionStorage) => { |
||||
return create(createOptions(storage))!; |
return create(createOptions(storage))!; |
||||
}; |
}; |
||||
|
|
||||
export default WebStorage; |
export default WebStorage; |
||||
@ -0,0 +1,108 @@ |
|||||
|
import { DEFAULT_CACHE_TIME } from '/@/settings/encryptionSetting'; |
||||
|
import { cacheCipher } from '/@/settings/encryptionSetting'; |
||||
|
import Encryption, { EncryptionParams } from '/@/utils/encryption/aesEncryption'; |
||||
|
|
||||
|
export interface CreateStorageParams extends EncryptionParams { |
||||
|
storage: Storage; |
||||
|
|
||||
|
hasEncrypt: boolean; |
||||
|
} |
||||
|
export const createStorage = ({ |
||||
|
prefixKey = '', |
||||
|
storage = sessionStorage, |
||||
|
key = cacheCipher.key, |
||||
|
iv = cacheCipher.iv, |
||||
|
hasEncrypt = true, |
||||
|
} = {}) => { |
||||
|
if (hasEncrypt && [key.length, iv.length].some((item) => item !== 16)) { |
||||
|
throw new Error('When hasEncrypt is true, the key or iv must be 16 bits!'); |
||||
|
} |
||||
|
|
||||
|
const encryption = new Encryption({ key, iv }); |
||||
|
|
||||
|
/** |
||||
|
*Cache class |
||||
|
*Construction parameters can be passed into sessionStorage, localStorage, |
||||
|
* @class Cache |
||||
|
* @example |
||||
|
*/ |
||||
|
const WebStorage = class WebStorage { |
||||
|
private storage: Storage; |
||||
|
private prefixKey?: string; |
||||
|
private encryption: Encryption; |
||||
|
private hasEncrypt: boolean; |
||||
|
/** |
||||
|
* |
||||
|
* @param {*} storage |
||||
|
*/ |
||||
|
constructor() { |
||||
|
this.storage = storage; |
||||
|
this.prefixKey = prefixKey; |
||||
|
this.encryption = encryption; |
||||
|
this.hasEncrypt = hasEncrypt; |
||||
|
} |
||||
|
|
||||
|
private getKey(key: string) { |
||||
|
return `${this.prefixKey}${key}`.toUpperCase(); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* |
||||
|
* Set cache |
||||
|
* @param {string} key |
||||
|
* @param {*} value |
||||
|
* @expire Expiration time in seconds |
||||
|
* @memberof Cache |
||||
|
*/ |
||||
|
set(key: string, value: any, expire: number | null = DEFAULT_CACHE_TIME) { |
||||
|
const stringData = JSON.stringify({ |
||||
|
value, |
||||
|
expire: expire !== null ? new Date().getTime() + expire * 1000 : null, |
||||
|
}); |
||||
|
const stringifyValue = this.hasEncrypt |
||||
|
? this.encryption.encryptByAES(stringData) |
||||
|
: stringData; |
||||
|
this.storage.setItem(this.getKey(key), stringifyValue); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
*Read cache |
||||
|
* @param {string} key |
||||
|
* @memberof Cache |
||||
|
*/ |
||||
|
get(key: string, def: any = null): any { |
||||
|
const item = this.storage.getItem(this.getKey(key)); |
||||
|
if (item) { |
||||
|
try { |
||||
|
const decItem = this.hasEncrypt ? this.encryption.decryptByAES(item) : item; |
||||
|
const data = JSON.parse(decItem); |
||||
|
const { value, expire } = data; |
||||
|
if (expire === null || expire >= new Date().getTime()) { |
||||
|
return value; |
||||
|
} |
||||
|
this.remove(this.getKey(key)); |
||||
|
} catch (e) { |
||||
|
return def; |
||||
|
} |
||||
|
} |
||||
|
return def; |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Delete cache based on key |
||||
|
* @param {string} key |
||||
|
* @memberof Cache |
||||
|
*/ |
||||
|
remove(key: string) { |
||||
|
this.storage.removeItem(this.getKey(key)); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Delete all caches of this instance |
||||
|
*/ |
||||
|
clear(): void { |
||||
|
this.storage.clear(); |
||||
|
} |
||||
|
}; |
||||
|
return new WebStorage(); |
||||
|
}; |
||||
@ -0,0 +1,35 @@ |
|||||
|
import CryptoES from 'crypto-es'; |
||||
|
export interface EncryptionParams { |
||||
|
key: string; |
||||
|
iv: string; |
||||
|
} |
||||
|
export class Encryption { |
||||
|
private key; |
||||
|
|
||||
|
private iv; |
||||
|
|
||||
|
constructor(opt: EncryptionParams) { |
||||
|
const { key, iv } = opt; |
||||
|
this.key = CryptoES.enc.Utf8.parse(key); |
||||
|
this.iv = CryptoES.enc.Utf8.parse(iv); |
||||
|
} |
||||
|
|
||||
|
get getOpt(): CryptoES.lib.CipherCfg { |
||||
|
return { |
||||
|
mode: CryptoES.mode.CBC as any, |
||||
|
padding: CryptoES.pad.Pkcs7, |
||||
|
iv: this.iv, |
||||
|
}; |
||||
|
} |
||||
|
|
||||
|
encryptByAES(str: string) { |
||||
|
const encrypted = CryptoES.AES.encrypt(str, this.key, this.getOpt); |
||||
|
return encrypted.toString(); |
||||
|
} |
||||
|
|
||||
|
decryptByAES(str: string) { |
||||
|
const decrypted = CryptoES.AES.decrypt(str, this.key, this.getOpt); |
||||
|
return decrypted.toString(CryptoES.enc.Utf8); |
||||
|
} |
||||
|
} |
||||
|
export default Encryption; |
||||
@ -1,138 +0,0 @@ |
|||||
import { DEFAULT_CACHE_TIME } from '/@/settings/cipherSetting'; |
|
||||
|
|
||||
// import { EncryptionParams } from '/@/utils/cipher/aesEncryption';
|
|
||||
export interface CreateStorageParams { |
|
||||
storage: Storage; |
|
||||
hasEncrypt: boolean; |
|
||||
} |
|
||||
export const createStorage = ({ prefixKey = '', storage = sessionStorage } = {}) => { |
|
||||
/** |
|
||||
*缓存类 |
|
||||
*构造参数可以传入 sessionStorage,localStorage, |
|
||||
* @class Cache |
|
||||
* @example |
|
||||
*/ |
|
||||
const WebStorage = class WebStorage { |
|
||||
private storage: Storage; |
|
||||
private prefixKey?: string; |
|
||||
|
|
||||
/** |
|
||||
* |
|
||||
* @param {*} storage |
|
||||
*/ |
|
||||
constructor() { |
|
||||
this.storage = storage; |
|
||||
this.prefixKey = prefixKey; |
|
||||
} |
|
||||
|
|
||||
private getKey(key: string) { |
|
||||
return `${this.prefixKey}${key}`.toUpperCase(); |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* |
|
||||
* 设置缓存 |
|
||||
* @param {string} key 缓存键 |
|
||||
* @param {*} value 缓存值 |
|
||||
* @expire 过期时间 单位秒 |
|
||||
* @memberof Cache |
|
||||
*/ |
|
||||
set(key: string, value: any, expire: number | null = DEFAULT_CACHE_TIME) { |
|
||||
const stringData = JSON.stringify({ |
|
||||
value, |
|
||||
expire: expire !== null ? new Date().getTime() + expire * 1000 : null, |
|
||||
}); |
|
||||
this.storage.setItem(this.getKey(key), stringData); |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* |
|
||||
*读取缓存 |
|
||||
* @param {string} key 缓存键 |
|
||||
* @returns 缓存值 |
|
||||
* @memberof Cache |
|
||||
*/ |
|
||||
get(key: string, def: any = null): any { |
|
||||
const item = this.storage.getItem(this.getKey(key)); |
|
||||
if (item) { |
|
||||
try { |
|
||||
const data = JSON.parse(item); |
|
||||
const { value, expire } = data; |
|
||||
if (expire === null || expire >= new Date().getTime()) { |
|
||||
return value; |
|
||||
} |
|
||||
this.remove(this.getKey(key)); |
|
||||
} catch (e) { |
|
||||
return def; |
|
||||
} |
|
||||
} |
|
||||
return def; |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* |
|
||||
*删除缓存 |
|
||||
* @param {string} key 缓存键 |
|
||||
* @memberof Cache |
|
||||
*/ |
|
||||
remove(key: string) { |
|
||||
this.storage.removeItem(this.getKey(key)); |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* |
|
||||
*删除该实例所有缓存 |
|
||||
* @memberof Cache |
|
||||
*/ |
|
||||
clear(): void { |
|
||||
this.storage.clear(); |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* 添加cookie |
|
||||
* @param name cookie名字 |
|
||||
* @param value cookie内容 |
|
||||
* @param expire |
|
||||
* 如果过期时间未设置,默认管理浏览器自动删除 |
|
||||
* 例子: |
|
||||
* cookieData.set('name','value',) |
|
||||
*/ |
|
||||
setCookie(name: string, value: any, expire: number | null = DEFAULT_CACHE_TIME) { |
|
||||
document.cookie = this.getKey(name) + '=' + value + '; Max-Age=' + expire; |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* 根据名字获取cooki值 |
|
||||
* @param name cookie名 |
|
||||
* @returns {*} cookie值 |
|
||||
*/ |
|
||||
getCookie(name: string) { |
|
||||
const arr = document.cookie.split('; '); |
|
||||
for (let i = 0; i < arr.length; i++) { |
|
||||
const arr2 = arr[i].split('='); |
|
||||
if (arr2[0] === this.getKey(name)) { |
|
||||
return arr2[1]; |
|
||||
} |
|
||||
} |
|
||||
return ''; |
|
||||
} |
|
||||
|
|
||||
/** |
|
||||
* 根据cookie名字删除cookie |
|
||||
* @param name cookie名字 |
|
||||
*/ |
|
||||
removeCookie(key: string) { |
|
||||
this.setCookie(key, 1, -1); |
|
||||
} |
|
||||
|
|
||||
clearCookie(): void { |
|
||||
const keys = document.cookie.match(/[^ =;]+(?==)/g); |
|
||||
if (keys) { |
|
||||
for (let i = keys.length; i--; ) { |
|
||||
document.cookie = keys[i] + '=0;expires=' + new Date(0).toUTCString(); |
|
||||
} |
|
||||
} |
|
||||
} |
|
||||
}; |
|
||||
return new WebStorage(); |
|
||||
}; |
|
||||
Loading…
Reference in new issue