@fairys/mocker-cli 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +36 -0
- package/bin/fairys-mocker +22 -0
- package/esm/base.d.ts +28 -0
- package/esm/base.js +80 -0
- package/esm/ci.d.ts +2 -0
- package/esm/ci.js +49 -0
- package/esm/connect.d.ts +15 -0
- package/esm/connect.js +38 -0
- package/esm/controller/base.d.ts +2 -0
- package/esm/controller/base.js +3 -0
- package/esm/controller/index.d.ts +3 -0
- package/esm/controller/index.js +3 -0
- package/esm/controller/mock.router.d.ts +21 -0
- package/esm/controller/mock.router.js +497 -0
- package/esm/controller/proxy.router.d.ts +18 -0
- package/esm/controller/proxy.router.js +503 -0
- package/esm/index.d.ts +5 -0
- package/esm/index.js +5 -0
- package/esm/main.d.ts +15 -0
- package/esm/main.js +38 -0
- package/esm/plugins/rsbuild.d.ts +2 -0
- package/esm/plugins/rsbuild.js +12 -0
- package/esm/router/base.d.ts +12 -0
- package/esm/router/base.js +23 -0
- package/esm/router/index.d.ts +3 -0
- package/esm/router/index.js +3 -0
- package/esm/router/mock.d.ts +7 -0
- package/esm/router/mock.js +32 -0
- package/esm/router/proxy.d.ts +14 -0
- package/esm/router/proxy.js +67 -0
- package/esm/utils/decorator.d.ts +18 -0
- package/esm/utils/decorator.js +55 -0
- package/esm/utils/index.d.ts +2 -0
- package/esm/utils/index.js +2 -0
- package/esm/utils/mcok.proxy.d.ts +36 -0
- package/esm/utils/mcok.proxy.js +141 -0
- package/esm/utils/utils.d.ts +20 -0
- package/esm/utils/utils.js +31 -0
- package/package.json +52 -0
- package/public/_fairys_mocker/favicon.png +0 -0
- package/public/_fairys_mocker/index.html +1 -0
- package/public/_fairys_mocker/static/css/index.2ba69ff5.css +1 -0
- package/public/_fairys_mocker/static/js/514.950758f1.js +2 -0
- package/public/_fairys_mocker/static/js/514.950758f1.js.LICENSE.txt +5 -0
- package/public/_fairys_mocker/static/js/index.f70ed1dc.js +1 -0
- package/public/_fairys_mocker/static/js/lib-react.2748fa4b.js +2 -0
- package/public/_fairys_mocker/static/js/lib-react.2748fa4b.js.LICENSE.txt +49 -0
- package/src/base.ts +125 -0
- package/src/ci.ts +61 -0
- package/src/connect.ts +62 -0
- package/src/controller/base.ts +4 -0
- package/src/controller/index.ts +3 -0
- package/src/controller/mock.router.ts +175 -0
- package/src/controller/proxy.router.ts +182 -0
- package/src/index.ts +5 -0
- package/src/main.ts +59 -0
- package/src/plugins/rsbuild.ts +14 -0
- package/src/router/base.ts +36 -0
- package/src/router/index.ts +3 -0
- package/src/router/mock.ts +38 -0
- package/src/router/proxy.ts +89 -0
- package/src/utils/decorator.ts +90 -0
- package/src/utils/index.ts +2 -0
- package/src/utils/mcok.proxy.ts +162 -0
- package/src/utils/utils.ts +46 -0
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import express from 'express';
|
|
2
|
+
import { ProxyItem } from "@fairys/create-mock-data";
|
|
3
|
+
import { BaseRouter } from "./base.js";
|
|
4
|
+
import { RequestHandler } from "http-proxy-middleware";
|
|
5
|
+
/**代理 路由器实例*/
|
|
6
|
+
export declare class ProxyRouter extends BaseRouter<ProxyItem> {
|
|
7
|
+
/**代理 路由器实例*/
|
|
8
|
+
router: express.Router | null;
|
|
9
|
+
wsProxyList: RequestHandler[];
|
|
10
|
+
/**加载代理路由*/
|
|
11
|
+
load: (proxyList: ProxyItem[]) => void;
|
|
12
|
+
/**销毁路由器实例*/
|
|
13
|
+
destroy: (msg?: string) => void;
|
|
14
|
+
}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import express from "express";
|
|
2
|
+
import { BaseRouter } from "./base.js";
|
|
3
|
+
import { createProxyMiddleware } from "http-proxy-middleware";
|
|
4
|
+
import chalk from "chalk";
|
|
5
|
+
import { fairysMockerBase } from "../base.js";
|
|
6
|
+
class ProxyRouter extends BaseRouter {
|
|
7
|
+
router = null;
|
|
8
|
+
wsProxyList = [];
|
|
9
|
+
load = (proxyList)=>{
|
|
10
|
+
const _that = this;
|
|
11
|
+
this.destroy();
|
|
12
|
+
const router = this.router = express.Router();
|
|
13
|
+
this.isEnabled = true;
|
|
14
|
+
for(let index = 0; index < proxyList.length; index++){
|
|
15
|
+
const proxyItem = proxyList[index];
|
|
16
|
+
let protocol = 'http';
|
|
17
|
+
let _target = proxyItem.target;
|
|
18
|
+
let _path = new RegExp(proxyItem.path);
|
|
19
|
+
if (/^(http:|https:|ws:|wss:)/.test(proxyItem.target)) {
|
|
20
|
+
const [_protocol] = proxyItem.target.split(":");
|
|
21
|
+
protocol = _protocol;
|
|
22
|
+
}
|
|
23
|
+
if ('ws' !== protocol && 'wss' !== protocol && proxyItem.ws) {
|
|
24
|
+
protocol = 'ws';
|
|
25
|
+
const [_protocol, ...rest] = proxyItem.target.split(":");
|
|
26
|
+
_target = [
|
|
27
|
+
protocol,
|
|
28
|
+
...rest
|
|
29
|
+
].join(":");
|
|
30
|
+
}
|
|
31
|
+
console.log(chalk.hex('#AF52DE')(chalk.bold(` 🍇 proxy代理启动:\t${chalk.yellow(protocol)}\t${proxyItem.path} ===> ${_target}\t`)));
|
|
32
|
+
if (!proxyItem.path.startsWith('^')) _path = new RegExp('^' + proxyItem.path);
|
|
33
|
+
if (proxyItem.ws) {
|
|
34
|
+
const wsProxy = createProxyMiddleware({
|
|
35
|
+
target: proxyItem.target,
|
|
36
|
+
pathRewrite: proxyItem.pathRewrite,
|
|
37
|
+
ws: proxyItem.ws,
|
|
38
|
+
changeOrigin: true
|
|
39
|
+
});
|
|
40
|
+
_that.wsProxyList.push(wsProxy);
|
|
41
|
+
router.all(_path, wsProxy);
|
|
42
|
+
if (fairysMockerBase.server) fairysMockerBase.server?.on('upgrade', wsProxy.upgrade);
|
|
43
|
+
} else router.all(_path, createProxyMiddleware({
|
|
44
|
+
target: proxyItem.target,
|
|
45
|
+
pathRewrite: proxyItem.pathRewrite,
|
|
46
|
+
ws: proxyItem.ws,
|
|
47
|
+
changeOrigin: true
|
|
48
|
+
}));
|
|
49
|
+
}
|
|
50
|
+
console.log('');
|
|
51
|
+
this.useRouter();
|
|
52
|
+
};
|
|
53
|
+
destroy = (msg)=>{
|
|
54
|
+
if (this.router) {
|
|
55
|
+
this.router.stack = [];
|
|
56
|
+
this.isEnabled = false;
|
|
57
|
+
}
|
|
58
|
+
const wsProxyList = this.wsProxyList;
|
|
59
|
+
if (Array.isArray(wsProxyList) && wsProxyList.length && fairysMockerBase.server) for(let index = 0; index < wsProxyList.length; index++){
|
|
60
|
+
const wsProxy = wsProxyList[index];
|
|
61
|
+
fairysMockerBase.server.off('upgrade', wsProxy.upgrade);
|
|
62
|
+
}
|
|
63
|
+
if (msg) console.log(chalk.red(msg));
|
|
64
|
+
console.log('');
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
export { ProxyRouter };
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
export type ClassStruct<TInstanceType extends unknown = unknown> = new (...args: any[]) => TInstanceType;
|
|
2
|
+
export interface RouteItemType {
|
|
3
|
+
method: 'get' | 'delete' | 'post' | 'put' | 'patch' | 'head' | 'options';
|
|
4
|
+
path: string;
|
|
5
|
+
funName?: string | symbol;
|
|
6
|
+
}
|
|
7
|
+
export interface ControllerItemType {
|
|
8
|
+
prefix?: string;
|
|
9
|
+
}
|
|
10
|
+
/**控制器参数*/
|
|
11
|
+
export declare const controllerMap: WeakMap<object, ControllerItemType>;
|
|
12
|
+
/**路由方法参数*/
|
|
13
|
+
export declare const routesMap: WeakMap<object, RouteItemType>;
|
|
14
|
+
export declare function Controller(prefix: string): (target: any, context: ClassDecoratorContext) => void;
|
|
15
|
+
export declare function Post(path: string): (target: any, context: ClassMethodDecoratorContext) => void;
|
|
16
|
+
export declare function Get(path: string): (target: any, context: ClassMethodDecoratorContext) => void;
|
|
17
|
+
export declare function MethodPath(path: string, method?: RouteItemType['method']): (target: any, context: ClassMethodDecoratorContext) => void;
|
|
18
|
+
export declare function registerRoutes(instance: unknown): void;
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import { fairysMockerBase } from "../base.js";
|
|
2
|
+
const controllerMap = new WeakMap();
|
|
3
|
+
const routesMap = new WeakMap();
|
|
4
|
+
function Controller(prefix) {
|
|
5
|
+
return (target, context)=>{
|
|
6
|
+
controllerMap.set(target, {
|
|
7
|
+
prefix
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
}
|
|
11
|
+
function Post(path) {
|
|
12
|
+
return (target, context)=>{
|
|
13
|
+
if ('method' === context.kind) routesMap.set(target, {
|
|
14
|
+
method: 'post',
|
|
15
|
+
path,
|
|
16
|
+
funName: context.name
|
|
17
|
+
});
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
function Get(path) {
|
|
21
|
+
return (target, context)=>{
|
|
22
|
+
if ('method' === context.kind) routesMap.set(target, {
|
|
23
|
+
method: 'get',
|
|
24
|
+
path,
|
|
25
|
+
funName: context.name
|
|
26
|
+
});
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
function MethodPath(path, method = 'post') {
|
|
30
|
+
return (target, context)=>{
|
|
31
|
+
if ('method' === context.kind) routesMap.set(target, {
|
|
32
|
+
method: method.toLowerCase(),
|
|
33
|
+
path,
|
|
34
|
+
funName: context.name
|
|
35
|
+
});
|
|
36
|
+
};
|
|
37
|
+
}
|
|
38
|
+
function registerRoutes(instance) {
|
|
39
|
+
const fairysRouter = fairysMockerBase.fairysMockerRouter;
|
|
40
|
+
if (!fairysRouter) return void console.log('请先初始化内置路由');
|
|
41
|
+
const proto = Object.getPrototypeOf(instance);
|
|
42
|
+
const controllerAPIRootPath = controllerMap.get(proto.constructor);
|
|
43
|
+
const controllerMethods = Object.getOwnPropertyNames(proto).filter((i)=>"constructor" !== i);
|
|
44
|
+
for(let index = 0; index < controllerMethods.length; index++){
|
|
45
|
+
const controllerMethod = controllerMethods[index];
|
|
46
|
+
const _requestHandle = proto[controllerMethod];
|
|
47
|
+
const boundRequestHandle = _requestHandle.bind(instance);
|
|
48
|
+
const routeItem = routesMap.get(_requestHandle);
|
|
49
|
+
if (routeItem) {
|
|
50
|
+
const fullPath = (controllerAPIRootPath?.prefix || '') + routeItem.path;
|
|
51
|
+
fairysRouter[routeItem.method](fullPath, (req, res)=>boundRequestHandle(req, res));
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
export { Controller, Get, MethodPath, Post, controllerMap, registerRoutes, routesMap };
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { ProxyList, DefineMockList } from "@fairys/create-mock-data";
|
|
2
|
+
export declare const getProxyFile: (rootDir?: string, dir?: string, fileName?: string) => {
|
|
3
|
+
proxyList: any;
|
|
4
|
+
rootDir: string;
|
|
5
|
+
dir: string;
|
|
6
|
+
fileName: string;
|
|
7
|
+
cache: string;
|
|
8
|
+
} | undefined;
|
|
9
|
+
export declare const createProxyFile: (proxyList: ProxyList, rootDir?: string, dir?: string, fileName?: string) => {
|
|
10
|
+
proxyConfig: Record<string, Omit<import("@fairys/create-mock-data").ProxyItem, "path">>;
|
|
11
|
+
rootDir: string;
|
|
12
|
+
dir: string;
|
|
13
|
+
fileName: string;
|
|
14
|
+
cache: string;
|
|
15
|
+
};
|
|
16
|
+
export declare const getMcokFile: (rootDir?: string, dir?: string, fileName?: string) => {
|
|
17
|
+
mockList: any;
|
|
18
|
+
rootDir: string;
|
|
19
|
+
dir: string;
|
|
20
|
+
fileName: string;
|
|
21
|
+
cache: string;
|
|
22
|
+
} | undefined;
|
|
23
|
+
export declare const createMockFile: (mockList: DefineMockList, rootDir?: string, dir?: string, fileName?: string) => {
|
|
24
|
+
mockConfig: {
|
|
25
|
+
body: any;
|
|
26
|
+
delay: number;
|
|
27
|
+
method: "GET" | "POST" | "PUT" | "DELETE" | "PATCH" | "HEAD" | "OPTIONS";
|
|
28
|
+
status: string;
|
|
29
|
+
url: string;
|
|
30
|
+
listCount: number;
|
|
31
|
+
}[];
|
|
32
|
+
rootDir: string;
|
|
33
|
+
dir: string;
|
|
34
|
+
fileName: string;
|
|
35
|
+
cache: string;
|
|
36
|
+
};
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
import node_path from "node:path";
|
|
2
|
+
import node_fs from "node:fs";
|
|
3
|
+
import { utils } from "./utils.js";
|
|
4
|
+
import { createMockData, createProxyData } from "@fairys/create-mock-data";
|
|
5
|
+
const getProxyFile = (rootDir, dir, fileName)=>{
|
|
6
|
+
const _rootDir = rootDir?.trim() || utils.rootDir;
|
|
7
|
+
const _dir = dir?.trim() || utils.dir;
|
|
8
|
+
const _fileName = fileName?.trim() || utils.proxyFile;
|
|
9
|
+
const proxyDir = node_path.join(_rootDir, _dir);
|
|
10
|
+
const cacheFilePath = node_path.join(proxyDir, _fileName + '.cache.json');
|
|
11
|
+
if (node_fs.existsSync(cacheFilePath)) {
|
|
12
|
+
const cacheFileContent = node_fs.readFileSync(cacheFilePath, 'utf-8');
|
|
13
|
+
const cacheData = JSON.parse(cacheFileContent);
|
|
14
|
+
const proxyList = cacheData.proxyList || [];
|
|
15
|
+
return {
|
|
16
|
+
proxyList,
|
|
17
|
+
rootDir: _rootDir,
|
|
18
|
+
dir: _dir,
|
|
19
|
+
fileName: _fileName,
|
|
20
|
+
cache: _fileName + '.cache.json'
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
};
|
|
24
|
+
const createProxyFile = (proxyList, rootDir, dir, fileName)=>{
|
|
25
|
+
const _rootDir = rootDir?.trim() || utils.rootDir;
|
|
26
|
+
const _dir = dir?.trim() || utils.dir;
|
|
27
|
+
const _fileName = fileName?.trim() || utils.proxyFile;
|
|
28
|
+
const proxyDir = node_path.join(_rootDir, _dir);
|
|
29
|
+
if (!node_fs.existsSync(proxyDir)) node_fs.mkdirSync(proxyDir, {
|
|
30
|
+
recursive: true
|
|
31
|
+
});
|
|
32
|
+
const proxyConfig = createProxyData(proxyList);
|
|
33
|
+
const proxyFilePath = node_path.join(proxyDir, `${_fileName}.ts`);
|
|
34
|
+
const proxyFileContent = `// 代理配置文件
|
|
35
|
+
// 自动生成于 ${new Date().toISOString()}
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* 代理配置参数
|
|
39
|
+
*/
|
|
40
|
+
export type ProxyItem = Record<string,{
|
|
41
|
+
/**转发地址*/
|
|
42
|
+
target: string,
|
|
43
|
+
/**路径重写*/
|
|
44
|
+
pathRewrite?: Record<string, string>,
|
|
45
|
+
/**是否开启ws*/
|
|
46
|
+
ws?: boolean
|
|
47
|
+
}>
|
|
48
|
+
|
|
49
|
+
export const proxyConfig: ProxyItem = ${JSON.stringify(proxyConfig, null, 2)};
|
|
50
|
+
export default proxyConfig;
|
|
51
|
+
`;
|
|
52
|
+
node_fs.writeFileSync(proxyFilePath, proxyFileContent);
|
|
53
|
+
const cacheFilePath = node_path.join(proxyDir, _fileName + '.cache.json');
|
|
54
|
+
const cacheFileContent = JSON.stringify({
|
|
55
|
+
proxyList,
|
|
56
|
+
rootDir: _rootDir,
|
|
57
|
+
dir: _dir,
|
|
58
|
+
fileName: _fileName,
|
|
59
|
+
cache: _fileName + '.cache.json'
|
|
60
|
+
}, null, 2);
|
|
61
|
+
node_fs.writeFileSync(cacheFilePath, cacheFileContent);
|
|
62
|
+
return {
|
|
63
|
+
proxyConfig,
|
|
64
|
+
rootDir: _rootDir,
|
|
65
|
+
dir: _dir,
|
|
66
|
+
fileName: _fileName,
|
|
67
|
+
cache: _fileName + '.cache.json'
|
|
68
|
+
};
|
|
69
|
+
};
|
|
70
|
+
const getMcokFile = (rootDir, dir, fileName)=>{
|
|
71
|
+
const _rootDir = rootDir?.trim() || utils.rootDir;
|
|
72
|
+
const _dir = dir?.trim() || utils.dir;
|
|
73
|
+
const _fileName = fileName?.trim() || utils.file;
|
|
74
|
+
const mockDir = node_path.join(_rootDir, _dir);
|
|
75
|
+
const cacheFilePath = node_path.join(mockDir, _fileName + '.cache.json');
|
|
76
|
+
if (node_fs.existsSync(cacheFilePath)) {
|
|
77
|
+
const cacheFileContent = node_fs.readFileSync(cacheFilePath, 'utf-8');
|
|
78
|
+
const cacheData = JSON.parse(cacheFileContent);
|
|
79
|
+
const mockList = cacheData.mockList || [];
|
|
80
|
+
return {
|
|
81
|
+
mockList,
|
|
82
|
+
rootDir: _rootDir,
|
|
83
|
+
dir: _dir,
|
|
84
|
+
fileName: _fileName,
|
|
85
|
+
cache: _fileName + '.cache.json'
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
};
|
|
89
|
+
const createMockFile = (mockList, rootDir, dir, fileName)=>{
|
|
90
|
+
const _rootDir = rootDir?.trim() || utils.rootDir;
|
|
91
|
+
const _dir = dir?.trim() || utils.dir;
|
|
92
|
+
const _fileName = fileName?.trim() || utils.file;
|
|
93
|
+
const mockDir = node_path.join(_rootDir, _dir);
|
|
94
|
+
if (!node_fs.existsSync(mockDir)) node_fs.mkdirSync(mockDir, {
|
|
95
|
+
recursive: true
|
|
96
|
+
});
|
|
97
|
+
const mockConfig = createMockData(mockList);
|
|
98
|
+
const mockFilePath = node_path.join(mockDir, `${_fileName}.ts`);
|
|
99
|
+
const mockFileContent = `// Mock 配置文件
|
|
100
|
+
// 自动生成于 ${new Date().toISOString()}
|
|
101
|
+
|
|
102
|
+
export interface MockerItem {
|
|
103
|
+
/**该接口允许的 请求方法,默认同时支持 GET 和 POST*/
|
|
104
|
+
method: 'GET' | 'POST' | 'PUT' | 'DELETE' | 'PATCH' | 'HEAD' | 'OPTIONS';
|
|
105
|
+
/**状态码*/
|
|
106
|
+
status: string;
|
|
107
|
+
//配置响应延迟时间, 如果传入的是一个数组,则代表延迟时间的范围
|
|
108
|
+
delay: number | [number, number];
|
|
109
|
+
/**响应体(可以自定义返回格式)*/
|
|
110
|
+
body: any;
|
|
111
|
+
/**接口地址*/
|
|
112
|
+
url: string;
|
|
113
|
+
/**列表数据条数(仅 list 格式有效)*/
|
|
114
|
+
listCount?: number;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
/**mock配置 列表*/
|
|
118
|
+
export type DefineMockList = MockerItem[];
|
|
119
|
+
|
|
120
|
+
export const mockList: DefineMockList = ${JSON.stringify(mockConfig, null, 2)};
|
|
121
|
+
export default mockList;
|
|
122
|
+
`;
|
|
123
|
+
node_fs.writeFileSync(mockFilePath, mockFileContent);
|
|
124
|
+
const cacheFilePath = node_path.join(mockDir, _fileName + '.cache.json');
|
|
125
|
+
const cacheFileContent = JSON.stringify({
|
|
126
|
+
mockList,
|
|
127
|
+
rootDir: _rootDir,
|
|
128
|
+
dir: _dir,
|
|
129
|
+
fileName: _fileName,
|
|
130
|
+
cache: _fileName + '.cache.json'
|
|
131
|
+
}, null, 2);
|
|
132
|
+
node_fs.writeFileSync(cacheFilePath, cacheFileContent);
|
|
133
|
+
return {
|
|
134
|
+
mockConfig,
|
|
135
|
+
rootDir: _rootDir,
|
|
136
|
+
dir: _dir,
|
|
137
|
+
fileName: _fileName,
|
|
138
|
+
cache: _fileName + '.cache.json'
|
|
139
|
+
};
|
|
140
|
+
};
|
|
141
|
+
export { createMockFile, createProxyFile, getMcokFile, getProxyFile };
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
declare class Utils {
|
|
2
|
+
/**根目录*/
|
|
3
|
+
rootDir: string;
|
|
4
|
+
/**目录名*/
|
|
5
|
+
dir: string;
|
|
6
|
+
/**文件名*/
|
|
7
|
+
file: string;
|
|
8
|
+
/**代理文件名*/
|
|
9
|
+
proxyFile: string;
|
|
10
|
+
/**设置根目录*/
|
|
11
|
+
setRootDir: (value?: string) => void;
|
|
12
|
+
/**设置目录名*/
|
|
13
|
+
setDir: (value?: string) => void;
|
|
14
|
+
/**设置文件名*/
|
|
15
|
+
setFile: (value?: string) => void;
|
|
16
|
+
/**设置代理文件名*/
|
|
17
|
+
setProxyFile: (value?: string) => void;
|
|
18
|
+
}
|
|
19
|
+
export declare const utils: Utils;
|
|
20
|
+
export {};
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import chalk from "chalk";
|
|
2
|
+
import node_fs from "node:fs";
|
|
3
|
+
import node_path from "node:path";
|
|
4
|
+
class Utils {
|
|
5
|
+
rootDir = process.cwd();
|
|
6
|
+
dir = 'mock';
|
|
7
|
+
file = 'index.mock';
|
|
8
|
+
proxyFile = 'proxy';
|
|
9
|
+
setRootDir = (value)=>{
|
|
10
|
+
if (value && node_fs.existsSync(value)) this.rootDir = value;
|
|
11
|
+
else {
|
|
12
|
+
if (value) {
|
|
13
|
+
console.log('');
|
|
14
|
+
console.log(chalk.red(`设置的根目录不存在:${value}`));
|
|
15
|
+
console.log('');
|
|
16
|
+
}
|
|
17
|
+
this.rootDir = process.env.FAIRYS_MOCKER_ROOT_DIR || node_path.join(process.cwd());
|
|
18
|
+
}
|
|
19
|
+
};
|
|
20
|
+
setDir = (value)=>{
|
|
21
|
+
this.dir = value || process.env.FAIRYS_MOCKER_DIR || 'mock';
|
|
22
|
+
};
|
|
23
|
+
setFile = (value)=>{
|
|
24
|
+
this.file = value || process.env.FAIRYS_MOCKER_FILE || 'index.mock';
|
|
25
|
+
};
|
|
26
|
+
setProxyFile = (value)=>{
|
|
27
|
+
this.proxyFile = value || process.env.FAIRYS_MOCKER_PROXY_FILE || 'proxy';
|
|
28
|
+
};
|
|
29
|
+
}
|
|
30
|
+
const utils = new Utils();
|
|
31
|
+
export { utils };
|
package/package.json
ADDED
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@fairys/mocker-cli",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"description": "Fairys Mocker CLI for mock data generation",
|
|
5
|
+
"author": "SunLxy <1011771396@qq.com>",
|
|
6
|
+
"homepage": "https://github.com/autumn-fairy-tales/fairys-mocker",
|
|
7
|
+
"main": "esm/index.js",
|
|
8
|
+
"types": "esm/index.d.ts",
|
|
9
|
+
"module": "esm/index.js",
|
|
10
|
+
"license": "ISC",
|
|
11
|
+
"type": "module",
|
|
12
|
+
"publishConfig": {
|
|
13
|
+
"access": "public"
|
|
14
|
+
},
|
|
15
|
+
"repository": {
|
|
16
|
+
"type": "git",
|
|
17
|
+
"url": "git+https://github.com/autumn-fairy-tales/fairys-mocker.git",
|
|
18
|
+
"directory": "packages/mocker-cli"
|
|
19
|
+
},
|
|
20
|
+
"scripts": {
|
|
21
|
+
"start": "node --trace-deprecation bin/fairys-mocker",
|
|
22
|
+
"build": "carefrees-rslib build --node --esm",
|
|
23
|
+
"watch": "carefrees-rslib build --watch --node --esm"
|
|
24
|
+
},
|
|
25
|
+
"bin": {
|
|
26
|
+
"fairys-mocker": "bin/fairys-mocker"
|
|
27
|
+
},
|
|
28
|
+
"dependencies": {
|
|
29
|
+
"@fairys/create-mock-data": "^0.0.1",
|
|
30
|
+
"body-parser": "2.2.2",
|
|
31
|
+
"chalk": "^5.6.2",
|
|
32
|
+
"connect": "^3.7.0",
|
|
33
|
+
"cors": "^2.8.5",
|
|
34
|
+
"detect-port": "^2.1.0",
|
|
35
|
+
"express": "^5.2.1",
|
|
36
|
+
"finalhandler": "^2.1.1",
|
|
37
|
+
"http-proxy-middleware": "^3.0.5",
|
|
38
|
+
"yargs-parser": "^22.0.0"
|
|
39
|
+
},
|
|
40
|
+
"devDependencies": {
|
|
41
|
+
"@types/cors": "^2.8.19",
|
|
42
|
+
"@types/express": "^5.0.6",
|
|
43
|
+
"@types/finalhandler": "^1.2.4",
|
|
44
|
+
"@types/yargs-parser": "^21.0.3"
|
|
45
|
+
},
|
|
46
|
+
"files": [
|
|
47
|
+
"bin",
|
|
48
|
+
"public",
|
|
49
|
+
"esm",
|
|
50
|
+
"src"
|
|
51
|
+
]
|
|
52
|
+
}
|
|
Binary file
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<!DOCTYPE html><html><head><link rel="icon" href="/_fairys_mocker/favicon.png"><title>Fairys Mocker</title><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><script defer src="/_fairys_mocker/static/js/lib-react.2748fa4b.js"></script><script defer src="/_fairys_mocker/static/js/514.950758f1.js"></script><script defer src="/_fairys_mocker/static/js/index.f70ed1dc.js"></script><link href="/_fairys_mocker/static/css/index.2ba69ff5.css" rel="stylesheet"></head><body><div id="root"></div></body></html>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
@media (prefers-color-scheme:dark){.w-tc-editor{--color-fg-default:#c9d1d9;--color-canvas-subtle:#161b22;--color-prettylights-syntax-comment:#8b949e;--color-prettylights-syntax-entity-tag:#7ee787;--color-prettylights-syntax-entity:#d2a8ff;--color-prettylights-syntax-sublimelinter-gutter-mark:#484f58;--color-prettylights-syntax-constant:#79c0ff;--color-prettylights-syntax-string:#a5d6ff;--color-prettylights-syntax-keyword:#ff7b72;--color-prettylights-syntax-markup-bold:#c9d1d9}}@media (prefers-color-scheme:light){.w-tc-editor{--color-fg-default:#24292f;--color-canvas-subtle:#f6f8fa;--color-prettylights-syntax-comment:#6e7781;--color-prettylights-syntax-entity-tag:#116329;--color-prettylights-syntax-entity:#8250df;--color-prettylights-syntax-sublimelinter-gutter-mark:#8c959f;--color-prettylights-syntax-constant:#0550ae;--color-prettylights-syntax-string:#0a3069;--color-prettylights-syntax-keyword:#cf222e;--color-prettylights-syntax-markup-bold:#24292f}}.w-tc-editor[data-color-mode*=dark],[data-color-mode*=dark] .w-tc-editor,[data-color-mode*=dark] .w-tc-editor-var,body[data-color-mode*=dark]{--color-fg-default:#c9d1d9;--color-canvas-subtle:#161b22;--color-prettylights-syntax-comment:#8b949e;--color-prettylights-syntax-entity-tag:#7ee787;--color-prettylights-syntax-entity:#d2a8ff;--color-prettylights-syntax-sublimelinter-gutter-mark:#484f58;--color-prettylights-syntax-constant:#79c0ff;--color-prettylights-syntax-string:#a5d6ff;--color-prettylights-syntax-keyword:#ff7b72;--color-prettylights-syntax-markup-bold:#c9d1d9}.w-tc-editor[data-color-mode*=light],[data-color-mode*=light] .w-tc-editor,[data-color-mode*=light] .w-tc-editor-var,body[data-color-mode*=light]{--color-fg-default:#24292f;--color-canvas-subtle:#f6f8fa;--color-prettylights-syntax-comment:#6e7781;--color-prettylights-syntax-entity-tag:#116329;--color-prettylights-syntax-entity:#8250df;--color-prettylights-syntax-sublimelinter-gutter-mark:#8c959f;--color-prettylights-syntax-constant:#0550ae;--color-prettylights-syntax-string:#0a3069;--color-prettylights-syntax-keyword:#cf222e;--color-prettylights-syntax-markup-bold:#24292f}.w-tc-editor{background-color:var(--color-canvas-subtle);color:var(--color-fg-default);font-family:inherit;font-size:12px}.w-tc-editor-text,.w-tc-editor-preview{min-height:16px}.w-tc-editor-preview pre{white-space:inherit;font-family:inherit;font-size:inherit;margin:0;padding:0}.w-tc-editor-preview pre code{font-family:inherit}.w-tc-editor code[class*=language-] .token.cdata,.w-tc-editor pre[class*=language-] .token.cdata,.w-tc-editor code[class*=language-] .token.comment,.w-tc-editor pre[class*=language-] .token.comment,.w-tc-editor code[class*=language-] .token.doctype,.w-tc-editor pre[class*=language-] .token.doctype,.w-tc-editor code[class*=language-] .token.prolog,.w-tc-editor pre[class*=language-] .token.prolog{color:var(--color-prettylights-syntax-comment)}.w-tc-editor code[class*=language-] .token.punctuation,.w-tc-editor pre[class*=language-] .token.punctuation{color:var(--color-prettylights-syntax-sublimelinter-gutter-mark)}.w-tc-editor code[class*=language-] .namespace,.w-tc-editor pre[class*=language-] .namespace{opacity:.7}.w-tc-editor code[class*=language-] .token.boolean,.w-tc-editor pre[class*=language-] .token.boolean,.w-tc-editor code[class*=language-] .token.constant,.w-tc-editor pre[class*=language-] .token.constant,.w-tc-editor code[class*=language-] .token.deleted,.w-tc-editor pre[class*=language-] .token.deleted,.w-tc-editor code[class*=language-] .token.number,.w-tc-editor pre[class*=language-] .token.number,.w-tc-editor code[class*=language-] .token.symbol,.w-tc-editor pre[class*=language-] .token.symbol{color:var(--color-prettylights-syntax-entity-tag)}.w-tc-editor code[class*=language-] .token.builtin,.w-tc-editor pre[class*=language-] .token.builtin,.w-tc-editor code[class*=language-] .token.char,.w-tc-editor pre[class*=language-] .token.char,.w-tc-editor code[class*=language-] .token.inserted,.w-tc-editor pre[class*=language-] .token.inserted,.w-tc-editor code[class*=language-] .token.selector,.w-tc-editor pre[class*=language-] .token.selector,.w-tc-editor code[class*=language-] .token.string,.w-tc-editor pre[class*=language-] .token.string,.w-tc-editor code[class*=language-] .style .token.string,.w-tc-editor pre[class*=language-] .style .token.string,.w-tc-editor code[class*=language-] .token.entity,.w-tc-editor pre[class*=language-] .token.entity,.w-tc-editor code[class*=language-] .token.property,.w-tc-editor pre[class*=language-] .token.property,.w-tc-editor code[class*=language-] .token.operator,.w-tc-editor pre[class*=language-] .token.operator,.w-tc-editor code[class*=language-] .token.url,.w-tc-editor pre[class*=language-] .token.url{color:var(--color-prettylights-syntax-constant)}.w-tc-editor code[class*=language-] .token.atrule,.w-tc-editor pre[class*=language-] .token.atrule,.w-tc-editor code[class*=language-] .token.property-access .token.method,.w-tc-editor pre[class*=language-] .token.property-access .token.method,.w-tc-editor code[class*=language-] .token.keyword,.w-tc-editor pre[class*=language-] .token.keyword{color:var(--color-prettylights-syntax-keyword)}.w-tc-editor code[class*=language-] .token.function,.w-tc-editor pre[class*=language-] .token.function{color:var(--color-prettylights-syntax-string)}.w-tc-editor code[class*=language-] .token.important,.w-tc-editor pre[class*=language-] .token.important,.w-tc-editor code[class*=language-] .token.regex,.w-tc-editor pre[class*=language-] .token.regex,.w-tc-editor code[class*=language-] .token.variable,.w-tc-editor pre[class*=language-] .token.variable{color:var(--color-prettylights-syntax-string-regexp)}.w-tc-editor code[class*=language-] .token.bold,.w-tc-editor pre[class*=language-] .token.bold,.w-tc-editor code[class*=language-] .token.important,.w-tc-editor pre[class*=language-] .token.important{color:var(--color-prettylights-syntax-markup-bold)}.w-tc-editor code[class*=language-] .token.tag,.w-tc-editor pre[class*=language-] .token.tag{color:var(--color-prettylights-syntax-entity-tag)}.w-tc-editor code[class*=language-] .token.attr-value,.w-tc-editor pre[class*=language-] .token.attr-value,.w-tc-editor code[class*=language-] .token.attr-name,.w-tc-editor pre[class*=language-] .token.attr-name{color:var(--color-prettylights-syntax-constant)}.w-tc-editor code[class*=language-] .token.selector .class,.w-tc-editor pre[class*=language-] .token.selector .class,.w-tc-editor code[class*=language-] .token.class-name,.w-tc-editor pre[class*=language-] .token.class-name{color:var(--color-prettylights-syntax-entity)}@layer properties{@supports (((-webkit-hyphens:none)) and (not (margin-trim:inline))) or ((-moz-orient:inline) and (not (color:rgb(from red r g b)))){*,:before,:after{--tw-translate-x:0;--tw-translate-y:0;--tw-translate-z:0;--tw-space-y-reverse:0;--tw-space-x-reverse:0;--tw-border-style:solid;--tw-font-weight:initial;--tw-shadow:0 0 #0000;--tw-shadow-color:initial;--tw-shadow-alpha:100%;--tw-inset-shadow:0 0 #0000;--tw-inset-shadow-color:initial;--tw-inset-shadow-alpha:100%;--tw-ring-color:initial;--tw-ring-shadow:0 0 #0000;--tw-inset-ring-color:initial;--tw-inset-ring-shadow:0 0 #0000;--tw-ring-inset:initial;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-offset-shadow:0 0 #0000;--tw-backdrop-blur:initial;--tw-backdrop-brightness:initial;--tw-backdrop-contrast:initial;--tw-backdrop-grayscale:initial;--tw-backdrop-hue-rotate:initial;--tw-backdrop-invert:initial;--tw-backdrop-opacity:initial;--tw-backdrop-saturate:initial;--tw-backdrop-sepia:initial;--tw-duration:initial;--tw-ease:initial}::backdrop{--tw-translate-x:0;--tw-translate-y:0;--tw-translate-z:0;--tw-space-y-reverse:0;--tw-space-x-reverse:0;--tw-border-style:solid;--tw-font-weight:initial;--tw-shadow:0 0 #0000;--tw-shadow-color:initial;--tw-shadow-alpha:100%;--tw-inset-shadow:0 0 #0000;--tw-inset-shadow-color:initial;--tw-inset-shadow-alpha:100%;--tw-ring-color:initial;--tw-ring-shadow:0 0 #0000;--tw-inset-ring-color:initial;--tw-inset-ring-shadow:0 0 #0000;--tw-ring-inset:initial;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-offset-shadow:0 0 #0000;--tw-backdrop-blur:initial;--tw-backdrop-brightness:initial;--tw-backdrop-contrast:initial;--tw-backdrop-grayscale:initial;--tw-backdrop-hue-rotate:initial;--tw-backdrop-invert:initial;--tw-backdrop-opacity:initial;--tw-backdrop-saturate:initial;--tw-backdrop-sepia:initial;--tw-duration:initial;--tw-ease:initial}}}@layer theme{:root,:host{--font-sans:ui-sans-serif,system-ui,sans-serif,"Apple Color Emoji","Segoe UI Emoji","Segoe UI Symbol","Noto Color Emoji";--font-mono:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,"Liberation Mono","Courier New",monospace;--color-red-500:#fb2c36;--color-red-600:#e40014;--color-orange-500:#fe6e00;--color-green-500:#00c758;--color-green-600:#00a544;--color-blue-400:#54a2ff;--color-blue-500:#3080ff;--color-blue-600:#155dfc;--color-gray-500:#6a7282;--color-gray-600:#4a5565;--color-zinc-50:#fafafa;--color-zinc-100:#f4f4f5;--color-zinc-200:#e4e4e7;--color-zinc-300:#d4d4d8;--color-zinc-400:#9f9fa9;--color-zinc-500:#71717b;--color-zinc-600:#52525c;--color-zinc-700:#3f3f46;--color-zinc-800:#27272a;--color-zinc-900:#18181b;--color-black:#000;--color-white:#fff;--spacing:.25rem;--container-2xl:42rem;--text-xs:.75rem;--text-xs--line-height:calc(1/.75);--text-sm:.875rem;--text-sm--line-height:calc(1.25/.875);--font-weight-medium:500;--radius-md:.375rem;--radius-lg:.5rem;--ease-in-out:cubic-bezier(.4,0,.2,1);--blur-sm:8px;--default-transition-duration:.15s;--default-transition-timing-function:cubic-bezier(.4,0,.2,1);--default-font-family:var(--font-sans);--default-mono-font-family:var(--font-mono)}@supports (color:color(display-p3 0 0 0)){:root,:host{--color-red-500:color(display-p3 .903738 .262579 .253307);--color-red-600:color(display-p3 .830323 .140383 .133196);--color-orange-500:color(display-p3 .946589 .449788 .0757345);--color-green-500:color(display-p3 .308734 .774754 .374307);--color-green-600:color(display-p3 .243882 .640824 .294808);--color-blue-400:color(display-p3 .397443 .62813 .992116);--color-blue-500:color(display-p3 .266422 .491219 .988624);--color-blue-600:color(display-p3 .174493 .358974 .950247);--color-gray-500:color(display-p3 .421287 .446085 .504784);--color-gray-600:color(display-p3 .297358 .332176 .39043);--color-zinc-50:color(display-p3 .980256 .980256 .980256);--color-zinc-100:color(display-p3 .956385 .956385 .959079);--color-zinc-200:color(display-p3 .894477 .894477 .905114);--color-zinc-300:color(display-p3 .831087 .831083 .846819);--color-zinc-400:color(display-p3 .622604 .622563 .659842);--color-zinc-500:color(display-p3 .442983 .442931 .480324);--color-zinc-600:color(display-p3 .321166 .321093 .358668);--color-zinc-700:color(display-p3 .246478 .246448 .273934);--color-zinc-800:color(display-p3 .152895 .152887 .16466);--color-zinc-900:color(display-p3 .0937957 .093793 .104806)}}@supports (color:lab(0% 0 0)){:root,:host{--color-red-500:lab(55.4814% 75.0732 48.8528);--color-red-600:lab(48.4493% 77.4328 61.5452);--color-orange-500:lab(64.272% 57.1788 90.3583);--color-green-500:lab(70.5521% -66.5147 45.8073);--color-green-600:lab(59.0978% -58.6621 41.2579);--color-blue-400:lab(65.0361% -1.42065 -56.9802);--color-blue-500:lab(54.1736% 13.3369 -74.6839);--color-blue-600:lab(44.0605% 29.0279 -86.0352);--color-gray-500:lab(47.7841% -.393182 -10.0268);--color-gray-600:lab(35.6337% -1.58697 -10.8425);--color-zinc-50:lab(98.26% 0 0);--color-zinc-100:lab(96.1634% .0993311 -.364041);--color-zinc-200:lab(90.6853% .399232 -1.45452);--color-zinc-300:lab(84.9837% .601262 -2.17986);--color-zinc-400:lab(65.6464% 1.53497 -5.42429);--color-zinc-500:lab(47.8878% 1.65477 -5.77283);--color-zinc-600:lab(35.1166% 1.78212 -6.1173);--color-zinc-700:lab(26.8019% 1.35387 -4.68303);--color-zinc-800:lab(15.7305% .613764 -2.16959);--color-zinc-900:lab(8.30603% .618205 -2.16572)}}}@layer base{*,:after,:before{box-sizing:border-box;border:0 solid;margin:0;padding:0}::backdrop{box-sizing:border-box;border:0 solid;margin:0;padding:0}::-webkit-file-upload-button{box-sizing:border-box;border:0 solid;margin:0;padding:0}::file-selector-button{box-sizing:border-box;border:0 solid;margin:0;padding:0}html,:host{-webkit-text-size-adjust:100%;-moz-tab-size:4;tab-size:4;line-height:1.5;font-family:var(--default-font-family,ui-sans-serif,system-ui,sans-serif,"Apple Color Emoji","Segoe UI Emoji","Segoe UI Symbol","Noto Color Emoji");font-feature-settings:var(--default-font-feature-settings,normal);font-variation-settings:var(--default-font-variation-settings,normal);-webkit-tap-highlight-color:transparent}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:var(--default-mono-font-family,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,"Liberation Mono","Courier New",monospace);font-feature-settings:var(--default-mono-font-feature-settings,normal);font-variation-settings:var(--default-mono-font-variation-settings,normal);font-size:1em}small{font-size:80%}sub,sup{vertical-align:baseline;font-size:75%;line-height:0;position:relative}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}:-moz-focusring{outline:auto}progress{vertical-align:baseline}summary{display:list-item}ol,ul,menu{list-style:none}img,svg,video,canvas,audio,iframe,embed,object{vertical-align:middle;display:block}img,video{max-width:100%;height:auto}button,input,select,optgroup,textarea{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}::-webkit-file-upload-button{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}::file-selector-button{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}:where(select:-webkit-any([multiple],[size])) optgroup{font-weight:bolder}:where(select:-moz-any([multiple],[size])) optgroup{font-weight:bolder}:where(select:-webkit-any([multiple],[size])) optgroup{font-weight:bolder}:where(select:-moz-any([multiple],[size])) optgroup{font-weight:bolder}:where(select:is([multiple],[size])) optgroup{font-weight:bolder}:where(select:-webkit-any([multiple],[size])) optgroup option{padding-inline-start:20px}:where(select:-moz-any([multiple],[size])) optgroup option{padding-inline-start:20px}:where(select:-webkit-any([multiple],[size])) optgroup option{padding-inline-start:20px}:where(select:-moz-any([multiple],[size])) optgroup option{padding-inline-start:20px}:where(select:is([multiple],[size])) optgroup option{padding-inline-start:20px}::-webkit-file-upload-button{margin-inline-end:4px}::file-selector-button{margin-inline-end:4px}::placeholder{opacity:1}@supports (not ((-webkit-appearance:-apple-pay-button))) or (contain-intrinsic-size:1px){::placeholder{color:currentColor}@supports (color:color-mix(in lab, red, red)){::placeholder{color:color-mix(in oklab,currentcolor 50%,transparent)}}}textarea{resize:vertical}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-date-and-time-value{min-height:1lh;text-align:inherit}::-webkit-datetime-edit{display:inline-flex}::-webkit-datetime-edit-fields-wrapper{padding:0}::-webkit-datetime-edit{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-year-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-month-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-day-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-hour-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-minute-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-second-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-millisecond-field{padding-block-start:0;padding-block-end:0}::-webkit-datetime-edit-meridiem-field{padding-block-start:0;padding-block-end:0}::-webkit-calendar-picker-indicator{line-height:1}:-moz-ui-invalid{box-shadow:none}button{-webkit-appearance:button;-moz-appearance:button;appearance:button}input:where([type=button],[type=reset],[type=submit]){-webkit-appearance:button;-moz-appearance:button;appearance:button}::-webkit-file-upload-button{-webkit-appearance:button;-moz-appearance:button;appearance:button}::file-selector-button{-webkit-appearance:button;-moz-appearance:button;appearance:button}::-webkit-inner-spin-button{height:auto}::-webkit-outer-spin-button{height:auto}[hidden]:where(:not([hidden=until-found])){display:none!important}}@layer components;@layer utilities{.pointer-events-none{pointer-events:none}.absolute{position:absolute}.fixed{position:fixed}.relative{position:relative}.sticky{position:sticky}.inset-0{inset:calc(var(--spacing)*0)}.-top-px{top:-1px}.z-10{z-index:10}.z-50{z-index:50}.z-90{z-index:90}.mt-1{margin-top:calc(var(--spacing)*1)}.mt-3{margin-top:calc(var(--spacing)*3)}.mr-2{margin-right:calc(var(--spacing)*2)}.mr-4{margin-right:calc(var(--spacing)*4)}.mb-1{margin-bottom:calc(var(--spacing)*1)}.mb-2{margin-bottom:calc(var(--spacing)*2)}.mb-3{margin-bottom:calc(var(--spacing)*3)}.mb-6{margin-bottom:calc(var(--spacing)*6)}.box-border{box-sizing:border-box}.block{display:block}.flex{display:flex}.hidden{display:none}.h-full{height:100%}.max-h-\[80\%\]{max-height:80%}.min-h-\[300px\]{min-height:300px}.w-3{width:calc(var(--spacing)*3)}.w-\[250px\]{width:250px}.w-\[400px\]{width:400px}.w-full{width:100%}.max-w-2xl{max-width:var(--container-2xl)}.min-w-full{min-width:100%}.flex-1{flex:1}.border-collapse{border-collapse:collapse}.translate-x-0{--tw-translate-x:calc(var(--spacing)*0);translate:var(--tw-translate-x)var(--tw-translate-y)}.translate-x-4{--tw-translate-x:calc(var(--spacing)*4);translate:var(--tw-translate-x)var(--tw-translate-y)}.flex-col{flex-direction:column}.flex-wrap{flex-wrap:wrap}.items-center{align-items:center}.justify-between{justify-content:space-between}.justify-center{justify-content:center}.justify-end{justify-content:flex-end}.gap-2{gap:calc(var(--spacing)*2)}.gap-3{gap:calc(var(--spacing)*3)}.gap-4{gap:calc(var(--spacing)*4)}:where(.space-y-3>:not(:last-child)){--tw-space-y-reverse:0;margin-block-start:calc(calc(var(--spacing)*3)*var(--tw-space-y-reverse));margin-block-end:calc(calc(var(--spacing)*3)*calc(1 - var(--tw-space-y-reverse)))}:where(.space-y-6>:not(:last-child)){--tw-space-y-reverse:0;margin-block-start:calc(calc(var(--spacing)*6)*var(--tw-space-y-reverse));margin-block-end:calc(calc(var(--spacing)*6)*calc(1 - var(--tw-space-y-reverse)))}:where(.space-x-1>:not(:last-child)){--tw-space-x-reverse:0;margin-inline-start:calc(calc(var(--spacing)*1)*var(--tw-space-x-reverse));margin-inline-end:calc(calc(var(--spacing)*1)*calc(1 - var(--tw-space-x-reverse)))}:where(.space-x-2>:not(:last-child)){--tw-space-x-reverse:0;margin-inline-start:calc(calc(var(--spacing)*2)*var(--tw-space-x-reverse));margin-inline-end:calc(calc(var(--spacing)*2)*calc(1 - var(--tw-space-x-reverse)))}.overflow-auto{overflow:auto}.overflow-hidden{overflow:hidden}.overflow-x-auto{overflow-x:auto}.rounded-lg{border-radius:var(--radius-lg)}.rounded-md{border-radius:var(--radius-md)}.border{border-style:var(--tw-border-style);border-width:1px}.border-b{border-bottom-style:var(--tw-border-style);border-bottom-width:1px}.border-b-2{border-bottom-style:var(--tw-border-style);border-bottom-width:2px}.border-blue-500{border-color:var(--color-blue-500)}.border-zinc-200{border-color:var(--color-zinc-200)}.border-zinc-300{border-color:var(--color-zinc-300)}.bg-black\/30{background-color:#0000004d}@supports (color:color-mix(in lab, red, red)){.bg-black\/30{background-color:color-mix(in oklab,var(--color-black)30%,transparent)}}.bg-blue-500{background-color:var(--color-blue-500)}.bg-gray-500{background-color:var(--color-gray-500)}.bg-green-500{background-color:var(--color-green-500)}.bg-red-500{background-color:var(--color-red-500)}.bg-white{background-color:var(--color-white)}.bg-white\/90{background-color:#ffffffe6}@supports (color:color-mix(in lab, red, red)){.bg-white\/90{background-color:color-mix(in oklab,var(--color-white)90%,transparent)}}.bg-zinc-50{background-color:var(--color-zinc-50)}.bg-zinc-100{background-color:var(--color-zinc-100)}.p-3{padding:calc(var(--spacing)*3)}.p-4{padding:calc(var(--spacing)*4)}.p-6{padding:calc(var(--spacing)*6)}.px-2{padding-inline:calc(var(--spacing)*2)}.px-3{padding-inline:calc(var(--spacing)*3)}.px-4{padding-inline:calc(var(--spacing)*4)}.py-0\.5{padding-block:calc(var(--spacing)*.5)}.py-1{padding-block:calc(var(--spacing)*1)}.py-2{padding-block:calc(var(--spacing)*2)}.py-8{padding-block:calc(var(--spacing)*8)}.text-center{text-align:center}.text-left{text-align:left}.text-sm{font-size:var(--text-sm);line-height:var(--tw-leading,var(--text-sm--line-height))}.text-xs{font-size:var(--text-xs);line-height:var(--tw-leading,var(--text-xs--line-height))}.font-medium{--tw-font-weight:var(--font-weight-medium);font-weight:var(--font-weight-medium)}.whitespace-nowrap{white-space:nowrap}.text-blue-500{color:var(--color-blue-500)}.text-blue-600{color:var(--color-blue-600)}.text-green-500{color:var(--color-green-500)}.text-orange-500{color:var(--color-orange-500)}.text-red-500{color:var(--color-red-500)}.text-white{color:var(--color-white)}.text-zinc-500{color:var(--color-zinc-500)}.text-zinc-600{color:var(--color-zinc-600)}.text-zinc-700{color:var(--color-zinc-700)}.text-zinc-800{color:var(--color-zinc-800)}.opacity-0{opacity:0}.opacity-100{opacity:1}.shadow-md{--tw-shadow:0 4px 6px -1px var(--tw-shadow-color,#0000001a),0 2px 4px -2px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow),var(--tw-inset-ring-shadow),var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow)}.shadow-xl{--tw-shadow:0 20px 25px -5px var(--tw-shadow-color,#0000001a),0 8px 10px -6px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow),var(--tw-inset-ring-shadow),var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow)}.backdrop-blur-sm{--tw-backdrop-blur:blur(var(--blur-sm));-webkit-backdrop-filter:var(--tw-backdrop-blur, )var(--tw-backdrop-brightness, )var(--tw-backdrop-contrast, )var(--tw-backdrop-grayscale, )var(--tw-backdrop-hue-rotate, )var(--tw-backdrop-invert, )var(--tw-backdrop-opacity, )var(--tw-backdrop-saturate, )var(--tw-backdrop-sepia, );backdrop-filter:var(--tw-backdrop-blur, )var(--tw-backdrop-brightness, )var(--tw-backdrop-contrast, )var(--tw-backdrop-grayscale, )var(--tw-backdrop-hue-rotate, )var(--tw-backdrop-invert, )var(--tw-backdrop-opacity, )var(--tw-backdrop-saturate, )var(--tw-backdrop-sepia, )}.transition-all{transition-property:all;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-colors{transition-property:color,background-color,border-color,outline-color,text-decoration-color,fill,stroke,--tw-gradient-from,--tw-gradient-via,--tw-gradient-to;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.duration-300{--tw-duration:.3s;transition-duration:.3s}.ease-in-out{--tw-ease:var(--ease-in-out);transition-timing-function:var(--ease-in-out)}@media (hover:hover){.hover\:bg-blue-600:hover{background-color:var(--color-blue-600)}.hover\:bg-gray-600:hover{background-color:var(--color-gray-600)}.hover\:bg-green-600:hover{background-color:var(--color-green-600)}.hover\:bg-red-600:hover{background-color:var(--color-red-600)}.hover\:bg-zinc-50:hover{background-color:var(--color-zinc-50)}.hover\:bg-zinc-100:hover{background-color:var(--color-zinc-100)}.hover\:text-zinc-700:hover{color:var(--color-zinc-700)}.hover\:underline:hover{text-decoration-line:underline}}.focus\:ring-2:focus{--tw-ring-shadow:var(--tw-ring-inset, )0 0 0 calc(2px + var(--tw-ring-offset-width))var(--tw-ring-color,currentcolor);box-shadow:var(--tw-inset-shadow),var(--tw-inset-ring-shadow),var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow)}.focus\:ring-blue-500:focus{--tw-ring-color:var(--color-blue-500)}.focus\:outline-none:focus{--tw-outline-style:none;outline-style:none}@media (min-width:40rem){.sm\:p-6{padding:calc(var(--spacing)*6)}}@media (prefers-color-scheme:dark){.dark\:border-zinc-600{border-color:var(--color-zinc-600)}.dark\:border-zinc-700{border-color:var(--color-zinc-700)}.dark\:bg-black{background-color:var(--color-black)}.dark\:bg-zinc-700{background-color:var(--color-zinc-700)}.dark\:bg-zinc-800{background-color:var(--color-zinc-800)}.dark\:bg-zinc-900{background-color:var(--color-zinc-900)}.dark\:bg-zinc-900\/90{background-color:#18181be6}@supports (color:color-mix(in lab, red, red)){.dark\:bg-zinc-900\/90{background-color:color-mix(in oklab,var(--color-zinc-900)90%,transparent)}}.dark\:text-blue-400{color:var(--color-blue-400)}.dark\:text-white{color:var(--color-white)}.dark\:text-zinc-100{color:var(--color-zinc-100)}.dark\:text-zinc-200{color:var(--color-zinc-200)}.dark\:text-zinc-300{color:var(--color-zinc-300)}.dark\:text-zinc-400{color:var(--color-zinc-400)}@media (hover:hover){.dark\:hover\:bg-zinc-600:hover{background-color:var(--color-zinc-600)}.dark\:hover\:bg-zinc-800:hover{background-color:var(--color-zinc-800)}.dark\:hover\:text-zinc-200:hover{color:var(--color-zinc-200)}}}}html,body,#root{height:100%;overflow:hidden}@property --tw-translate-x{syntax:"*";inherits:false;initial-value:0}@property --tw-translate-y{syntax:"*";inherits:false;initial-value:0}@property --tw-translate-z{syntax:"*";inherits:false;initial-value:0}@property --tw-space-y-reverse{syntax:"*";inherits:false;initial-value:0}@property --tw-space-x-reverse{syntax:"*";inherits:false;initial-value:0}@property --tw-border-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-font-weight{syntax:"*";inherits:false}@property --tw-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-shadow-color{syntax:"*";inherits:false}@property --tw-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-inset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-shadow-color{syntax:"*";inherits:false}@property --tw-inset-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-ring-color{syntax:"*";inherits:false}@property --tw-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-ring-color{syntax:"*";inherits:false}@property --tw-inset-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-ring-inset{syntax:"*";inherits:false}@property --tw-ring-offset-width{syntax:"<length>";inherits:false;initial-value:0}@property --tw-ring-offset-color{syntax:"*";inherits:false;initial-value:#fff}@property --tw-ring-offset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-backdrop-blur{syntax:"*";inherits:false}@property --tw-backdrop-brightness{syntax:"*";inherits:false}@property --tw-backdrop-contrast{syntax:"*";inherits:false}@property --tw-backdrop-grayscale{syntax:"*";inherits:false}@property --tw-backdrop-hue-rotate{syntax:"*";inherits:false}@property --tw-backdrop-invert{syntax:"*";inherits:false}@property --tw-backdrop-opacity{syntax:"*";inherits:false}@property --tw-backdrop-saturate{syntax:"*";inherits:false}@property --tw-backdrop-sepia{syntax:"*";inherits:false}@property --tw-duration{syntax:"*";inherits:false}@property --tw-ease{syntax:"*";inherits:false}
|