feat: implement gas and delivery admin systems
This commit is contained in:
19
frontend/delivery_admin/src/utils/auth.ts
Normal file
19
frontend/delivery_admin/src/utils/auth.ts
Normal file
@@ -0,0 +1,19 @@
|
||||
const TOKEN_KEY = 'token';
|
||||
|
||||
const isLogin = () => {
|
||||
return !!localStorage.getItem(TOKEN_KEY);
|
||||
};
|
||||
|
||||
const getToken = () => {
|
||||
return localStorage.getItem(TOKEN_KEY);
|
||||
};
|
||||
|
||||
const setToken = (token: string) => {
|
||||
localStorage.setItem(TOKEN_KEY, token);
|
||||
};
|
||||
|
||||
const clearToken = () => {
|
||||
localStorage.removeItem(TOKEN_KEY);
|
||||
};
|
||||
|
||||
export { clearToken, getToken, isLogin, setToken };
|
||||
3
frontend/delivery_admin/src/utils/env.ts
Normal file
3
frontend/delivery_admin/src/utils/env.ts
Normal file
@@ -0,0 +1,3 @@
|
||||
const debug = import.meta.env.MODE !== 'production';
|
||||
|
||||
export default debug;
|
||||
19
frontend/delivery_admin/src/utils/error-report.ts
Normal file
19
frontend/delivery_admin/src/utils/error-report.ts
Normal file
@@ -0,0 +1,19 @@
|
||||
import axios from 'axios';
|
||||
import type { App, ComponentPublicInstance } from 'vue';
|
||||
|
||||
export default function setupErrorReport(app: App, baseUrl: string) {
|
||||
if (!baseUrl) {
|
||||
return;
|
||||
}
|
||||
app.config.errorHandler = (
|
||||
err: unknown,
|
||||
instance: ComponentPublicInstance | null,
|
||||
info: string,
|
||||
) => {
|
||||
axios.post(`${baseUrl}/report-error`, {
|
||||
err,
|
||||
instance,
|
||||
info,
|
||||
});
|
||||
};
|
||||
}
|
||||
27
frontend/delivery_admin/src/utils/event.ts
Normal file
27
frontend/delivery_admin/src/utils/event.ts
Normal file
@@ -0,0 +1,27 @@
|
||||
export function addEventListen(
|
||||
target: Window | HTMLElement,
|
||||
event: string,
|
||||
handler: EventListenerOrEventListenerObject,
|
||||
capture = false,
|
||||
) {
|
||||
if (
|
||||
target.addEventListener &&
|
||||
typeof target.addEventListener === 'function'
|
||||
) {
|
||||
target.addEventListener(event, handler, capture);
|
||||
}
|
||||
}
|
||||
|
||||
export function removeEventListen(
|
||||
target: Window | HTMLElement,
|
||||
event: string,
|
||||
handler: EventListenerOrEventListenerObject,
|
||||
capture = false,
|
||||
) {
|
||||
if (
|
||||
target.removeEventListener &&
|
||||
typeof target.removeEventListener === 'function'
|
||||
) {
|
||||
target.removeEventListener(event, handler, capture);
|
||||
}
|
||||
}
|
||||
23
frontend/delivery_admin/src/utils/index.ts
Normal file
23
frontend/delivery_admin/src/utils/index.ts
Normal file
@@ -0,0 +1,23 @@
|
||||
type TargetContext = '_self' | '_parent' | '_blank' | '_top';
|
||||
|
||||
export const openWindow = (
|
||||
url: string,
|
||||
opts?: { target?: TargetContext; [key: string]: any },
|
||||
) => {
|
||||
const { target = '_blank', ...others } = opts || {};
|
||||
window.open(
|
||||
url,
|
||||
target,
|
||||
Object.entries(others)
|
||||
.reduce((preValue: string[], curValue) => {
|
||||
const [key, value] = curValue;
|
||||
return [...preValue, `${key}=${value}`];
|
||||
}, [])
|
||||
.join(','),
|
||||
);
|
||||
};
|
||||
|
||||
export const regexUrl =
|
||||
/^(?!mailto:)(?:(?:http|https|ftp):\/\/)(?:\S+(?::\S*)?@)?(?:(?:(?:[1-9]\d?|1\d\d|2[01]\d|22[0-3])(?:\.(?:1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.(?:[0-9]\d?|1\d\d|2[0-4]\d|25[0-4]))|(?:(?:[a-z\u00a1-\uffff0-9]+-?)*[a-z\u00a1-\uffff0-9]+)(?:\.(?:[a-z\u00a1-\uffff0-9]+-?)*[a-z\u00a1-\uffff0-9]+)*(?:\.(?:[a-z\u00a1-\uffff]{2,})))|localhost)(?::\d{2,5})?(?:(\/|\?|#)[^\s]*)?$/i;
|
||||
|
||||
export default null;
|
||||
53
frontend/delivery_admin/src/utils/is.ts
Normal file
53
frontend/delivery_admin/src/utils/is.ts
Normal file
@@ -0,0 +1,53 @@
|
||||
const opt = Object.prototype.toString;
|
||||
|
||||
export function isArray(obj: any): obj is any[] {
|
||||
return opt.call(obj) === '[object Array]';
|
||||
}
|
||||
|
||||
export function isObject(obj: any): obj is { [key: string]: any } {
|
||||
return opt.call(obj) === '[object Object]';
|
||||
}
|
||||
|
||||
export function isString(obj: any): obj is string {
|
||||
return opt.call(obj) === '[object String]';
|
||||
}
|
||||
|
||||
export function isNumber(obj: any): obj is number {
|
||||
return opt.call(obj) === '[object Number]' && !Number.isNaN(obj);
|
||||
}
|
||||
|
||||
export function isRegExp(obj: any) {
|
||||
return opt.call(obj) === '[object RegExp]';
|
||||
}
|
||||
|
||||
export function isFile(obj: any): obj is File {
|
||||
return opt.call(obj) === '[object File]';
|
||||
}
|
||||
|
||||
export function isBlob(obj: any): obj is Blob {
|
||||
return opt.call(obj) === '[object Blob]';
|
||||
}
|
||||
|
||||
export function isUndefined(obj: any): obj is undefined {
|
||||
return obj === undefined;
|
||||
}
|
||||
|
||||
export function isNull(obj: any): obj is null {
|
||||
return obj === null;
|
||||
}
|
||||
|
||||
export function isFunction(obj: any): obj is (...args: any[]) => any {
|
||||
return typeof obj === 'function';
|
||||
}
|
||||
|
||||
export function isEmptyObject(obj: any): boolean {
|
||||
return isObject(obj) && Object.keys(obj).length === 0;
|
||||
}
|
||||
|
||||
export function isExist(obj: any): boolean {
|
||||
return obj || obj === 0;
|
||||
}
|
||||
|
||||
export function isWindow(el: any): el is Window {
|
||||
return el === window;
|
||||
}
|
||||
8
frontend/delivery_admin/src/utils/parse-url-query.ts
Normal file
8
frontend/delivery_admin/src/utils/parse-url-query.ts
Normal file
@@ -0,0 +1,8 @@
|
||||
export function parseUrlQuery(url: string): Record<string, string> {
|
||||
const { searchParams } = new URL(url, 'http://localhost');
|
||||
const query: Record<string, string> = {};
|
||||
searchParams.forEach((value, key) => {
|
||||
query[key] = value;
|
||||
});
|
||||
return query;
|
||||
}
|
||||
31
frontend/delivery_admin/src/utils/route-listener.ts
Normal file
31
frontend/delivery_admin/src/utils/route-listener.ts
Normal file
@@ -0,0 +1,31 @@
|
||||
/**
|
||||
* Listening to routes alone would waste rendering performance.
|
||||
* Use the publish-subscribe model for distribution management.
|
||||
*/
|
||||
import mitt, { type Handler } from 'mitt';
|
||||
import type { RouteLocationNormalized } from 'vue-router';
|
||||
|
||||
const emitter = mitt();
|
||||
|
||||
const key = Symbol('ROUTE_CHANGE');
|
||||
|
||||
let latestRoute: RouteLocationNormalized;
|
||||
|
||||
export function setRouteEmitter(to: RouteLocationNormalized) {
|
||||
emitter.emit(key, to);
|
||||
latestRoute = to;
|
||||
}
|
||||
|
||||
export function listenerRouteChange(
|
||||
handler: (route: RouteLocationNormalized) => void,
|
||||
immediate = true,
|
||||
) {
|
||||
emitter.on(key, handler as Handler);
|
||||
if (immediate && latestRoute) {
|
||||
handler(latestRoute);
|
||||
}
|
||||
}
|
||||
|
||||
export function removeRouteListener() {
|
||||
emitter.off(key);
|
||||
}
|
||||
Reference in New Issue
Block a user