vome-core 0.0.8 → 0.0.11
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/dist/admin/api/client.d.ts +32 -0
- package/dist/admin/api/client.js +1 -0
- package/dist/admin/config/plugin-dev.d.ts +30 -0
- package/dist/admin/config/plugin-dev.js +1 -0
- package/dist/admin/crud/config.d.ts +5 -0
- package/dist/admin/crud/config.js +1 -0
- package/dist/admin/crud/confirm.d.ts +11 -0
- package/dist/admin/crud/confirm.js +1 -0
- package/dist/admin/crud/dict.d.ts +3 -0
- package/dist/admin/crud/dict.js +1 -0
- package/dist/admin/crud/index.d.ts +40 -0
- package/dist/admin/crud/index.js +1 -0
- package/dist/admin/crud/key.d.ts +22 -0
- package/dist/admin/crud/key.js +1 -0
- package/dist/admin/crud/mitt.d.ts +10 -0
- package/dist/admin/crud/mitt.js +1 -0
- package/dist/admin/crud/plugins.d.ts +48 -0
- package/dist/admin/crud/plugins.js +1 -0
- package/dist/admin/crud/registry.d.ts +5 -0
- package/dist/admin/crud/registry.js +26 -0
- package/dist/admin/crud/span.d.ts +17 -0
- package/dist/admin/crud/span.js +1 -0
- package/dist/admin/crud/style.d.ts +36 -0
- package/dist/admin/crud/style.js +1 -0
- package/dist/admin/crud/useCrud.d.ts +18 -0
- package/dist/admin/crud/useCrud.js +1 -0
- package/dist/admin/crud/validate.d.ts +14 -0
- package/dist/admin/crud/validate.js +1 -0
- package/dist/admin/directives/perm.d.ts +3 -0
- package/dist/admin/directives/perm.js +1 -0
- package/dist/admin/hooks/useBrowser.d.ts +5 -0
- package/dist/admin/hooks/useBrowser.js +1 -0
- package/dist/admin/hooks/useUpload.d.ts +8 -0
- package/dist/admin/hooks/useUpload.js +1 -0
- package/dist/admin/hooks/useVome.d.ts +8 -0
- package/dist/admin/hooks/useVome.js +1 -0
- package/dist/admin/index.d.ts +26 -0
- package/dist/admin/index.js +1 -0
- package/dist/admin/lib/browser.d.ts +3 -0
- package/dist/admin/lib/browser.js +1 -0
- package/dist/admin/lib/cn.d.ts +2 -0
- package/dist/admin/lib/cn.js +1 -0
- package/dist/admin/lib/dialog-float.d.ts +4 -0
- package/dist/admin/lib/dialog-float.js +1 -0
- package/dist/admin/lib/eps.d.ts +11 -0
- package/dist/admin/lib/eps.js +1 -0
- package/dist/admin/lib/menu.d.ts +2 -0
- package/dist/admin/lib/menu.js +1 -0
- package/dist/admin/lib/module.d.ts +21 -0
- package/dist/admin/lib/module.js +1 -0
- package/dist/admin/lib/tree.d.ts +2 -0
- package/dist/admin/lib/tree.js +1 -0
- package/dist/admin/lib/upload.d.ts +13 -0
- package/dist/admin/lib/upload.js +1 -0
- package/dist/admin/router/index.d.ts +3 -0
- package/dist/admin/router/index.js +1 -0
- package/dist/admin/router/menu-routes.d.ts +7 -0
- package/dist/admin/router/menu-routes.js +1 -0
- package/dist/admin/service/base.d.ts +27 -0
- package/dist/admin/service/base.js +1 -0
- package/dist/admin/service/index.d.ts +15 -0
- package/dist/admin/service/index.js +1 -0
- package/dist/admin/stores/app.d.ts +1 -0
- package/dist/admin/stores/app.js +1 -0
- package/dist/admin/stores/tags.d.ts +1 -0
- package/dist/admin/stores/tags.js +1 -0
- package/dist/admin/stores/user.d.ts +1 -0
- package/dist/admin/stores/user.js +1 -0
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -236
- package/dist/server/index.d.ts +1 -1
- package/dist/server/index.js +1 -3261
- package/dist/shared/index.js +1 -0
- package/dist/shared/tree.d.ts +18 -0
- package/dist/shared/tree.js +1 -0
- package/package.json +13 -10
- package/src/shared/tree.d.ts +18 -0
- package/typings/admin/base/auth.d.ts +20 -0
- package/typings/admin/base/permission.d.ts +19 -0
- package/typings/admin/comm/crud.d.ts +282 -0
- package/typings/admin/comm/request.d.ts +11 -0
- package/typings/admin/comm/service.d.ts +40 -0
- package/typings/admin/comm/upload.d.ts +26 -0
- package/typings/admin/vome/browser.d.ts +10 -0
- package/typings/admin/vome/module.d.ts +13 -0
- package/src/admin/api/client.ts +0 -184
- package/src/admin/config/plugin-dev.ts +0 -31
- package/src/admin/crud/config.ts +0 -38
- package/src/admin/crud/confirm.ts +0 -135
- package/src/admin/crud/dict.ts +0 -49
- package/src/admin/crud/index.ts +0 -79
- package/src/admin/crud/key.ts +0 -47
- package/src/admin/crud/mitt.ts +0 -27
- package/src/admin/crud/plugins.ts +0 -298
- package/src/admin/crud/registry.ts +0 -45
- package/src/admin/crud/span.ts +0 -48
- package/src/admin/crud/style.ts +0 -112
- package/src/admin/crud/useCrud.ts +0 -81
- package/src/admin/crud/validate.ts +0 -109
- package/src/admin/directives/perm.ts +0 -18
- package/src/admin/hooks/useBrowser.ts +0 -27
- package/src/admin/hooks/useUpload.ts +0 -82
- package/src/admin/hooks/useVome.ts +0 -13
- package/src/admin/index.ts +0 -59
- package/src/admin/lib/browser.ts +0 -28
- package/src/admin/lib/cn.ts +0 -7
- package/src/admin/lib/dialog-float.ts +0 -14
- package/src/admin/lib/eps.ts +0 -44
- package/src/admin/lib/menu.ts +0 -14
- package/src/admin/lib/module.ts +0 -112
- package/src/admin/lib/tree.ts +0 -2
- package/src/admin/lib/upload.ts +0 -102
- package/src/admin/router/index.ts +0 -68
- package/src/admin/router/menu-routes.ts +0 -126
- package/src/admin/service/base.ts +0 -96
- package/src/admin/service/index.ts +0 -378
- package/src/admin/stores/app.ts +0 -30
- package/src/admin/stores/tags.ts +0 -73
- package/src/admin/stores/user.ts +0 -52
- /package/{src → dist}/admin/components/vm-aside.vue +0 -0
- /package/{src → dist}/admin/components/vm-auto-perm-dialog.vue +0 -0
- /package/{src → dist}/admin/components/vm-check-tree.vue +0 -0
- /package/{src → dist}/admin/components/vm-dept-tree.vue +0 -0
- /package/{src → dist}/admin/components/vm-empty.vue +0 -0
- /package/{src → dist}/admin/components/vm-eps-perm-picker.vue +0 -0
- /package/{src → dist}/admin/components/vm-group-cascader.vue +0 -0
- /package/{src → dist}/admin/components/vm-icon-picker.vue +0 -0
- /package/{src → dist}/admin/components/vm-markdown.vue +0 -0
- /package/{src → dist}/admin/components/vm-ri-icon.vue +0 -0
- /package/{src → dist}/admin/components/vm-role-picker.vue +0 -0
- /package/{src → dist}/admin/components/vm-view-path-picker.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-column-custom.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-context-menu.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-date-picker.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-date-range.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-date-text.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-dict-tag.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-file-icon.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-multi-select.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-number-range.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-radio.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-select.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-switch.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-tree-select.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-upload-item.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-upload.vue +0 -0
- /package/{src → dist}/admin/crud/components/vm-user-select.vue +0 -0
- /package/{src → dist}/admin/crud/vm-add-btn.vue +0 -0
- /package/{src → dist}/admin/crud/vm-adv-search.vue +0 -0
- /package/{src → dist}/admin/crud/vm-crud.vue +0 -0
- /package/{src → dist}/admin/crud/vm-dialog.vue +0 -0
- /package/{src → dist}/admin/crud/vm-flex1.vue +0 -0
- /package/{src → dist}/admin/crud/vm-form.vue +0 -0
- /package/{src → dist}/admin/crud/vm-multi-delete-btn.vue +0 -0
- /package/{src → dist}/admin/crud/vm-pagination.vue +0 -0
- /package/{src → dist}/admin/crud/vm-refresh-btn.vue +0 -0
- /package/{src → dist}/admin/crud/vm-row.vue +0 -0
- /package/{src → dist}/admin/crud/vm-search-key.vue +0 -0
- /package/{src → dist}/admin/crud/vm-search.vue +0 -0
- /package/{src → dist}/admin/crud/vm-table.vue +0 -0
- /package/{src → dist}/admin/crud/vm-toolbar.vue +0 -0
- /package/{src → dist}/admin/crud/vm-upsert.vue +0 -0
- /package/{src → dist}/admin/data/remixicon-all.json +0 -0
- /package/{src → dist}/admin/env.d.ts +0 -0
- /package/{src → dist}/admin/static/fileicon/demo.css +0 -0
- /package/{src → dist}/admin/static/fileicon/demo_index.html +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.css +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.js +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.json +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.ttf +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.woff +0 -0
- /package/{src → dist}/admin/static/fileicon/iconfont.woff2 +0 -0
- /package/{src → dist}/admin/static/scarce//344/270/213/350/275/275/345/244/261/350/264/245.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/224/257/344/273/230/346/210/220/345/212/237.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/344/274/230/346/203/240/345/210/270.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/345/206/205/345/256/271.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/345/217/221/347/245/250.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/345/233/276/347/211/207.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/345/234/260/345/235/200.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/345/272/227/351/223/272.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/216/250/351/200/201.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/220/234/347/264/242/347/273/223/346/236/234.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/224/266/350/227/217.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/225/260/346/215/256.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/235/203/351/231/220.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/346/266/210/346/201/257.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/347/244/274/347/211/251.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/347/247/257/345/210/206.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/347/275/221/347/273/234.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/350/247/206/351/242/221.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/350/256/242/345/215/225.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/350/257/204/350/256/272.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/351/205/215/351/200/201.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/351/223/266/350/241/214/345/215/241.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//346/232/202/346/227/240/351/237/263/344/271/220.svg" +0 -0
- /package/{src → dist}/admin/static/scarce//351/241/265/351/235/242/344/270/215/345/255/230/345/234/250.svg" +0 -0
- /package/{src → dist}/admin/styles/base.css +0 -0
- /package/{src → dist}/admin/tsconfig.json +0 -0
package/dist/server/index.js
CHANGED
|
@@ -1,3261 +1 @@
|
|
|
1
|
-
// @bun
|
|
2
|
-
// src/core/config.ts
|
|
3
|
-
import { join } from "path";
|
|
4
|
-
import { pathToFileURL } from "url";
|
|
5
|
-
|
|
6
|
-
// src/comm/env.ts
|
|
7
|
-
function getEnv() {
|
|
8
|
-
return Bun.env.NODE_ENV === "dev" ? "dev" : "prod";
|
|
9
|
-
}
|
|
10
|
-
|
|
11
|
-
// src/comm/merge.ts
|
|
12
|
-
function merge(base, override) {
|
|
13
|
-
const result = { ...base };
|
|
14
|
-
for (const key of Object.keys(override)) {
|
|
15
|
-
const baseVal = result[key];
|
|
16
|
-
const overrideVal = override[key];
|
|
17
|
-
if (baseVal && overrideVal && typeof baseVal === "object" && typeof overrideVal === "object" && !Array.isArray(baseVal) && !Array.isArray(overrideVal)) {
|
|
18
|
-
result[key] = merge(baseVal, overrideVal);
|
|
19
|
-
continue;
|
|
20
|
-
}
|
|
21
|
-
result[key] = overrideVal;
|
|
22
|
-
}
|
|
23
|
-
return result;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
// src/core/config.ts
|
|
27
|
-
async function loadConfig(configDir = join(process.cwd(), "src/config")) {
|
|
28
|
-
const envFile = getEnv() === "dev" ? "dev.ts" : "prod.ts";
|
|
29
|
-
const defaultMod = await import(pathToFileURL(join(configDir, "default.ts")).href);
|
|
30
|
-
const envMod = await import(pathToFileURL(join(configDir, envFile)).href);
|
|
31
|
-
return merge(defaultMod.default, envMod.default);
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
// src/core/vome-config.ts
|
|
35
|
-
var VomeConfig = await loadConfig();
|
|
36
|
-
// src/core/app.ts
|
|
37
|
-
import { Elysia as Elysia2 } from "elysia";
|
|
38
|
-
|
|
39
|
-
// src/routing/register.ts
|
|
40
|
-
import { Elysia } from "elysia";
|
|
41
|
-
|
|
42
|
-
// src/core/context/index.ts
|
|
43
|
-
import { AsyncLocalStorage } from "async_hooks";
|
|
44
|
-
var storage = new AsyncLocalStorage;
|
|
45
|
-
var warnedOutsideRequest = false;
|
|
46
|
-
function resolveClientIp(request) {
|
|
47
|
-
const forwarded = request.headers.get("x-forwarded-for");
|
|
48
|
-
if (forwarded) {
|
|
49
|
-
const first = forwarded.split(",")[0]?.trim();
|
|
50
|
-
if (first)
|
|
51
|
-
return first;
|
|
52
|
-
}
|
|
53
|
-
return request.headers.get("x-real-ip")?.trim() || request.headers.get("cf-connecting-ip")?.trim() || "";
|
|
54
|
-
}
|
|
55
|
-
function initContextFromRequest(request) {
|
|
56
|
-
const url = new URL(request.url);
|
|
57
|
-
const forwardedHost = request.headers.get("x-forwarded-host")?.split(",")[0]?.trim();
|
|
58
|
-
const hostHeader = request.headers.get("host")?.trim();
|
|
59
|
-
return {
|
|
60
|
-
requestId: crypto.randomUUID(),
|
|
61
|
-
method: request.method,
|
|
62
|
-
path: url.pathname,
|
|
63
|
-
ip: resolveClientIp(request),
|
|
64
|
-
host: forwardedHost || hostHeader || url.host,
|
|
65
|
-
startTime: Date.now()
|
|
66
|
-
};
|
|
67
|
-
}
|
|
68
|
-
function enterContextWith(ctx) {
|
|
69
|
-
storage.enterWith(ctx);
|
|
70
|
-
}
|
|
71
|
-
function getContext() {
|
|
72
|
-
return storage.getStore();
|
|
73
|
-
}
|
|
74
|
-
function assignContext(patch) {
|
|
75
|
-
const store = storage.getStore();
|
|
76
|
-
if (!store) {
|
|
77
|
-
if (getEnv() === "dev" && !warnedOutsideRequest) {
|
|
78
|
-
warnedOutsideRequest = true;
|
|
79
|
-
console.warn("[Context] \u5F53\u524D\u65E0\u8BF7\u6C42\u4E0A\u4E0B\u6587\uFF0C\u5199\u5165\u88AB\u5FFD\u7565\uFF08\u8BF7\u786E\u8BA4 asyncContextManager \u5DF2\u542F\u7528\uFF09");
|
|
80
|
-
}
|
|
81
|
-
return;
|
|
82
|
-
}
|
|
83
|
-
Object.assign(store, patch);
|
|
84
|
-
}
|
|
85
|
-
function runContext(ctx, fn) {
|
|
86
|
-
return storage.run(ctx, fn);
|
|
87
|
-
}
|
|
88
|
-
var Context = Object.assign(assignContext, {
|
|
89
|
-
get: getContext,
|
|
90
|
-
run: runContext
|
|
91
|
-
});
|
|
92
|
-
|
|
93
|
-
// src/ioc/container.ts
|
|
94
|
-
import"reflect-metadata";
|
|
95
|
-
|
|
96
|
-
// src/ioc/metadata.ts
|
|
97
|
-
var INJECT_METADATA_KEY = "vome:inject";
|
|
98
|
-
var providers = new Map;
|
|
99
|
-
function registerProvider(meta) {
|
|
100
|
-
providers.set(meta.token, meta);
|
|
101
|
-
}
|
|
102
|
-
function getProvider(token) {
|
|
103
|
-
return providers.get(token);
|
|
104
|
-
}
|
|
105
|
-
function listProviders() {
|
|
106
|
-
const seen = new Set;
|
|
107
|
-
const list = [];
|
|
108
|
-
for (const meta of providers.values()) {
|
|
109
|
-
if (seen.has(meta.useClass))
|
|
110
|
-
continue;
|
|
111
|
-
seen.add(meta.useClass);
|
|
112
|
-
list.push(meta);
|
|
113
|
-
}
|
|
114
|
-
return list;
|
|
115
|
-
}
|
|
116
|
-
function tokenLabel(token) {
|
|
117
|
-
if (typeof token === "string" || typeof token === "symbol")
|
|
118
|
-
return String(token);
|
|
119
|
-
return token.name || "(anonymous)";
|
|
120
|
-
}
|
|
121
|
-
function appendInjectMeta(target, inject) {
|
|
122
|
-
const list = Reflect.getMetadata(INJECT_METADATA_KEY, target) ?? [];
|
|
123
|
-
list.push(inject);
|
|
124
|
-
Reflect.defineMetadata(INJECT_METADATA_KEY, list, target);
|
|
125
|
-
}
|
|
126
|
-
function getInjectMetas(target) {
|
|
127
|
-
return Reflect.getMetadata(INJECT_METADATA_KEY, target) ?? [];
|
|
128
|
-
}
|
|
129
|
-
function resetProviders() {
|
|
130
|
-
providers.clear();
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
// src/ioc/scope.ts
|
|
134
|
-
var ScopeEnum;
|
|
135
|
-
((ScopeEnum2) => {
|
|
136
|
-
ScopeEnum2["Singleton"] = "singleton";
|
|
137
|
-
ScopeEnum2["Request"] = "request";
|
|
138
|
-
ScopeEnum2["Prototype"] = "prototype";
|
|
139
|
-
})(ScopeEnum ||= {});
|
|
140
|
-
|
|
141
|
-
// src/ioc/container.ts
|
|
142
|
-
var singletons = new Map;
|
|
143
|
-
var creating = new Set;
|
|
144
|
-
var requestCaches = new WeakMap;
|
|
145
|
-
function injectProperties(instance, useClass) {
|
|
146
|
-
for (const meta of getInjectMetas(useClass)) {
|
|
147
|
-
const { propertyKey, token: dep, resolve } = meta;
|
|
148
|
-
if (!resolve && dep == null) {
|
|
149
|
-
throw new Error(`[Ioc] ${String(propertyKey)} \u7F3A\u5C11 token \u6216 resolve`);
|
|
150
|
-
}
|
|
151
|
-
const value = resolve ? resolve() : Ioc.get(dep);
|
|
152
|
-
instance[propertyKey] = value;
|
|
153
|
-
const bind = instance.bindEntity;
|
|
154
|
-
if (resolve && typeof bind === "function") {
|
|
155
|
-
bind.call(instance, value);
|
|
156
|
-
}
|
|
157
|
-
}
|
|
158
|
-
}
|
|
159
|
-
function createInstance(useClass) {
|
|
160
|
-
if (creating.has(useClass)) {
|
|
161
|
-
throw new Error(`[Ioc] \u68C0\u6D4B\u5230\u5FAA\u73AF\u4F9D\u8D56: ${useClass.name}`);
|
|
162
|
-
}
|
|
163
|
-
creating.add(useClass);
|
|
164
|
-
try {
|
|
165
|
-
const instance = new useClass;
|
|
166
|
-
injectProperties(instance, useClass);
|
|
167
|
-
return instance;
|
|
168
|
-
} finally {
|
|
169
|
-
creating.delete(useClass);
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
|
-
function getSingleton(useClass) {
|
|
173
|
-
const cached = singletons.get(useClass);
|
|
174
|
-
if (cached)
|
|
175
|
-
return cached;
|
|
176
|
-
const instance = createInstance(useClass);
|
|
177
|
-
singletons.set(useClass, instance);
|
|
178
|
-
return instance;
|
|
179
|
-
}
|
|
180
|
-
function getRequestCache() {
|
|
181
|
-
const ctx = Context.get();
|
|
182
|
-
if (!ctx) {
|
|
183
|
-
throw new Error("[Ioc] Request \u4F5C\u7528\u57DF\u987B\u5728\u8BF7\u6C42\u4E0A\u4E0B\u6587\u4E2D\u89E3\u6790\uFF08\u8BF7\u786E\u8BA4 asyncContextManager.enable\uFF09");
|
|
184
|
-
}
|
|
185
|
-
let cache = requestCaches.get(ctx);
|
|
186
|
-
if (!cache) {
|
|
187
|
-
cache = new Map;
|
|
188
|
-
requestCaches.set(ctx, cache);
|
|
189
|
-
}
|
|
190
|
-
return cache;
|
|
191
|
-
}
|
|
192
|
-
function getRequestScoped(useClass) {
|
|
193
|
-
const cache = getRequestCache();
|
|
194
|
-
const cached = cache.get(useClass);
|
|
195
|
-
if (cached)
|
|
196
|
-
return cached;
|
|
197
|
-
const instance = createInstance(useClass);
|
|
198
|
-
cache.set(useClass, instance);
|
|
199
|
-
return instance;
|
|
200
|
-
}
|
|
201
|
-
function resolveByScope(useClass, scope) {
|
|
202
|
-
switch (scope) {
|
|
203
|
-
case "singleton" /* Singleton */:
|
|
204
|
-
return getSingleton(useClass);
|
|
205
|
-
case "prototype" /* Prototype */:
|
|
206
|
-
return createInstance(useClass);
|
|
207
|
-
case "request" /* Request */:
|
|
208
|
-
return getRequestScoped(useClass);
|
|
209
|
-
default:
|
|
210
|
-
throw new Error(`[Ioc] \u672A\u77E5\u4F5C\u7528\u57DF: ${scope}`);
|
|
211
|
-
}
|
|
212
|
-
}
|
|
213
|
-
function resolveMeta(token) {
|
|
214
|
-
const meta = getProvider(token);
|
|
215
|
-
if (!meta) {
|
|
216
|
-
throw new Error(`[Ioc] \u672A\u6CE8\u518C\u7684 Provider: ${tokenLabel(token)}`);
|
|
217
|
-
}
|
|
218
|
-
return meta;
|
|
219
|
-
}
|
|
220
|
-
function bootstrapIoc() {
|
|
221
|
-
for (const { useClass, scope } of listProviders()) {
|
|
222
|
-
if (scope === "singleton" /* Singleton */) {
|
|
223
|
-
getSingleton(useClass);
|
|
224
|
-
}
|
|
225
|
-
}
|
|
226
|
-
console.log(`[Ioc] bootstrap \u2190 ${singletons.size} singleton(s)`);
|
|
227
|
-
}
|
|
228
|
-
function get(token) {
|
|
229
|
-
const meta = resolveMeta(token);
|
|
230
|
-
return resolveByScope(meta.useClass, meta.scope);
|
|
231
|
-
}
|
|
232
|
-
function set(token, instance) {
|
|
233
|
-
if (typeof token === "function") {
|
|
234
|
-
registerProvider({
|
|
235
|
-
token,
|
|
236
|
-
useClass: token,
|
|
237
|
-
scope: "singleton" /* Singleton */
|
|
238
|
-
});
|
|
239
|
-
singletons.set(token, instance);
|
|
240
|
-
return;
|
|
241
|
-
}
|
|
242
|
-
const ctor = instance?.constructor;
|
|
243
|
-
if (!ctor || ctor === Object) {
|
|
244
|
-
throw new Error(`[Ioc] Ioc.set(${tokenLabel(token)}) \u9700\u8981 class \u5B9E\u4F8B\uFF0C\u4EE5\u4FBF\u786E\u5B9A useClass`);
|
|
245
|
-
}
|
|
246
|
-
registerProvider({ token, useClass: ctor, scope: "singleton" /* Singleton */ });
|
|
247
|
-
registerProvider({ token: ctor, useClass: ctor, scope: "singleton" /* Singleton */ });
|
|
248
|
-
singletons.set(ctor, instance);
|
|
249
|
-
}
|
|
250
|
-
function resetIoc() {
|
|
251
|
-
singletons.clear();
|
|
252
|
-
creating.clear();
|
|
253
|
-
resetProviders();
|
|
254
|
-
}
|
|
255
|
-
var Ioc = {
|
|
256
|
-
get,
|
|
257
|
-
set
|
|
258
|
-
};
|
|
259
|
-
|
|
260
|
-
// src/routing/metadata.ts
|
|
261
|
-
import"reflect-metadata";
|
|
262
|
-
var controllers = new Map;
|
|
263
|
-
function registerController(meta) {
|
|
264
|
-
controllers.set(meta.token, meta);
|
|
265
|
-
}
|
|
266
|
-
function listControllers(side) {
|
|
267
|
-
const all = [...controllers.values()];
|
|
268
|
-
return side ? all.filter((c) => c.side === side) : all;
|
|
269
|
-
}
|
|
270
|
-
var ROUTE_PARAMS_KEY = "vome:controller:route-params";
|
|
271
|
-
var ROUTE_PUBLIC_KEY = "vome:controller:route-public";
|
|
272
|
-
var ROUTE_MW_KEY = "vome:controller:route-middleware";
|
|
273
|
-
var ROUTE_PERMS_KEY = "vome:controller:route-perms";
|
|
274
|
-
var ROUTE_IGNORE_PERMS_KEY = "vome:controller:route-ignore-perms";
|
|
275
|
-
function appendRouteParam(token, handler, param) {
|
|
276
|
-
const map = Reflect.getMetadata(ROUTE_PARAMS_KEY, token) ?? {};
|
|
277
|
-
const list = map[handler] ?? [];
|
|
278
|
-
list.push(param);
|
|
279
|
-
map[handler] = list;
|
|
280
|
-
Reflect.defineMetadata(ROUTE_PARAMS_KEY, map, token);
|
|
281
|
-
}
|
|
282
|
-
function getRouteParams(token, handler) {
|
|
283
|
-
const map = Reflect.getMetadata(ROUTE_PARAMS_KEY, token);
|
|
284
|
-
return map?.[handler] ?? [];
|
|
285
|
-
}
|
|
286
|
-
function clearRouteParams(token) {
|
|
287
|
-
Reflect.deleteMetadata(ROUTE_PARAMS_KEY, token);
|
|
288
|
-
}
|
|
289
|
-
function markRoutePublic(token, handler) {
|
|
290
|
-
const map = Reflect.getMetadata(ROUTE_PUBLIC_KEY, token) ?? {};
|
|
291
|
-
map[handler] = true;
|
|
292
|
-
Reflect.defineMetadata(ROUTE_PUBLIC_KEY, map, token);
|
|
293
|
-
}
|
|
294
|
-
function isRoutePublic(token, handler) {
|
|
295
|
-
const map = Reflect.getMetadata(ROUTE_PUBLIC_KEY, token);
|
|
296
|
-
return !!map?.[handler];
|
|
297
|
-
}
|
|
298
|
-
function clearRoutePublic(token) {
|
|
299
|
-
Reflect.deleteMetadata(ROUTE_PUBLIC_KEY, token);
|
|
300
|
-
}
|
|
301
|
-
function appendRouteMiddleware(token, handler, middleware) {
|
|
302
|
-
const map = Reflect.getMetadata(ROUTE_MW_KEY, token) ?? {};
|
|
303
|
-
map[handler] = [...map[handler] ?? [], ...middleware];
|
|
304
|
-
Reflect.defineMetadata(ROUTE_MW_KEY, map, token);
|
|
305
|
-
}
|
|
306
|
-
function getRouteMiddleware(token, handler) {
|
|
307
|
-
const map = Reflect.getMetadata(ROUTE_MW_KEY, token);
|
|
308
|
-
return map?.[handler] ?? [];
|
|
309
|
-
}
|
|
310
|
-
function clearRouteMiddleware(token) {
|
|
311
|
-
Reflect.deleteMetadata(ROUTE_MW_KEY, token);
|
|
312
|
-
}
|
|
313
|
-
function setRoutePerms(token, handler, perms) {
|
|
314
|
-
const map = Reflect.getMetadata(ROUTE_PERMS_KEY, token) ?? {};
|
|
315
|
-
map[handler] = perms;
|
|
316
|
-
Reflect.defineMetadata(ROUTE_PERMS_KEY, map, token);
|
|
317
|
-
}
|
|
318
|
-
function getRoutePerms(token, handler) {
|
|
319
|
-
const map = Reflect.getMetadata(ROUTE_PERMS_KEY, token);
|
|
320
|
-
return map?.[handler];
|
|
321
|
-
}
|
|
322
|
-
function clearRoutePerms(token) {
|
|
323
|
-
Reflect.deleteMetadata(ROUTE_PERMS_KEY, token);
|
|
324
|
-
}
|
|
325
|
-
function markRouteIgnorePerms(token, handler) {
|
|
326
|
-
const map = Reflect.getMetadata(ROUTE_IGNORE_PERMS_KEY, token) ?? {};
|
|
327
|
-
map[handler] = true;
|
|
328
|
-
Reflect.defineMetadata(ROUTE_IGNORE_PERMS_KEY, map, token);
|
|
329
|
-
}
|
|
330
|
-
function isRouteIgnorePerms(token, handler) {
|
|
331
|
-
const map = Reflect.getMetadata(ROUTE_IGNORE_PERMS_KEY, token);
|
|
332
|
-
return !!map?.[handler];
|
|
333
|
-
}
|
|
334
|
-
function clearRouteIgnorePerms(token) {
|
|
335
|
-
Reflect.deleteMetadata(ROUTE_IGNORE_PERMS_KEY, token);
|
|
336
|
-
}
|
|
337
|
-
function schemaFromParams(params) {
|
|
338
|
-
const schema = {};
|
|
339
|
-
for (const param of params) {
|
|
340
|
-
if (param.source === "body" && param.schema !== undefined)
|
|
341
|
-
schema.body = param.schema;
|
|
342
|
-
if (param.source === "query" && param.schema !== undefined)
|
|
343
|
-
schema.query = param.schema;
|
|
344
|
-
if (param.source === "params" && param.schema !== undefined)
|
|
345
|
-
schema.params = param.schema;
|
|
346
|
-
}
|
|
347
|
-
return Object.keys(schema).length > 0 ? schema : undefined;
|
|
348
|
-
}
|
|
349
|
-
|
|
350
|
-
// src/routing/openapi-tags.ts
|
|
351
|
-
function openApiTag(module, side) {
|
|
352
|
-
return `${module}.${side}`;
|
|
353
|
-
}
|
|
354
|
-
function sideOrder(side) {
|
|
355
|
-
if (side === "admin")
|
|
356
|
-
return 0;
|
|
357
|
-
if (side === "app")
|
|
358
|
-
return 1;
|
|
359
|
-
return 2;
|
|
360
|
-
}
|
|
361
|
-
function parseTag(tag) {
|
|
362
|
-
const i = tag.lastIndexOf(".");
|
|
363
|
-
if (i < 0)
|
|
364
|
-
return { module: tag, side: "" };
|
|
365
|
-
return { module: tag.slice(0, i), side: tag.slice(i + 1) };
|
|
366
|
-
}
|
|
367
|
-
function buildOpenApiTagDocs() {
|
|
368
|
-
const controllers2 = listControllers();
|
|
369
|
-
const tagMap = new Map;
|
|
370
|
-
const groupMap = new Map;
|
|
371
|
-
for (const meta of controllers2) {
|
|
372
|
-
const tag = openApiTag(meta.module, meta.side);
|
|
373
|
-
if (!tagMap.has(tag)) {
|
|
374
|
-
tagMap.set(tag, {
|
|
375
|
-
name: tag,
|
|
376
|
-
description: `${meta.module} ${meta.side}`,
|
|
377
|
-
"x-displayName": meta.side
|
|
378
|
-
});
|
|
379
|
-
}
|
|
380
|
-
let set2 = groupMap.get(meta.module);
|
|
381
|
-
if (!set2) {
|
|
382
|
-
set2 = new Set;
|
|
383
|
-
groupMap.set(meta.module, set2);
|
|
384
|
-
}
|
|
385
|
-
set2.add(tag);
|
|
386
|
-
}
|
|
387
|
-
const tags = [...tagMap.values()].sort((a, b) => {
|
|
388
|
-
const pa = parseTag(a.name);
|
|
389
|
-
const pb = parseTag(b.name);
|
|
390
|
-
return pa.module.localeCompare(pb.module) || sideOrder(pa.side) - sideOrder(pb.side);
|
|
391
|
-
});
|
|
392
|
-
const tagGroups = [...groupMap.entries()].sort(([a], [b]) => a.localeCompare(b)).map(([name, set2]) => ({
|
|
393
|
-
name,
|
|
394
|
-
tags: [...set2].sort((a, b) => {
|
|
395
|
-
const sa = parseTag(a).side;
|
|
396
|
-
const sb = parseTag(b).side;
|
|
397
|
-
return sideOrder(sa) - sideOrder(sb);
|
|
398
|
-
})
|
|
399
|
-
}));
|
|
400
|
-
return { tags, tagGroups };
|
|
401
|
-
}
|
|
402
|
-
|
|
403
|
-
// src/routing/path-utils.ts
|
|
404
|
-
function normalizePrefix(prefix) {
|
|
405
|
-
if (!prefix)
|
|
406
|
-
return "";
|
|
407
|
-
return prefix.startsWith("/") ? prefix : `/${prefix}`;
|
|
408
|
-
}
|
|
409
|
-
function joinPrefix(...parts) {
|
|
410
|
-
const segments = parts.map((part) => normalizePrefix(part).replace(/^\/+|\/+$/g, "")).filter(Boolean);
|
|
411
|
-
return segments.length ? `/${segments.join("/")}` : "/";
|
|
412
|
-
}
|
|
413
|
-
function getRouteSubPath(routePath, controllerPrefix) {
|
|
414
|
-
const ctrl = normalizePrefix(controllerPrefix).replace(/\/$/, "");
|
|
415
|
-
const full = normalizePrefix(routePath);
|
|
416
|
-
if (!ctrl)
|
|
417
|
-
return full || "/";
|
|
418
|
-
if (full === ctrl)
|
|
419
|
-
return "/";
|
|
420
|
-
if (full.startsWith(`${ctrl}/`))
|
|
421
|
-
return full.slice(ctrl.length) || "/";
|
|
422
|
-
const sub = routePath.startsWith("/") ? routePath : `/${routePath}`;
|
|
423
|
-
return sub || "/";
|
|
424
|
-
}
|
|
425
|
-
|
|
426
|
-
// src/routing/perm.ts
|
|
427
|
-
function resolveRoutePerm(module, prefix, action) {
|
|
428
|
-
let resource = prefix.replace(/^\//, "").replace(/\/+/g, ":");
|
|
429
|
-
if (resource === module) {
|
|
430
|
-
resource = module;
|
|
431
|
-
} else if (resource.startsWith(`${module}:`)) {
|
|
432
|
-
resource = resource.slice(module.length + 1);
|
|
433
|
-
}
|
|
434
|
-
const head = `${module}-`;
|
|
435
|
-
if (resource.startsWith(head)) {
|
|
436
|
-
resource = resource.slice(head.length);
|
|
437
|
-
}
|
|
438
|
-
resource = resource.replace(/-/g, ":");
|
|
439
|
-
if (!resource)
|
|
440
|
-
resource = module;
|
|
441
|
-
return `${module}:${resource}:${action}`;
|
|
442
|
-
}
|
|
443
|
-
function actionFromSubPath(subPath) {
|
|
444
|
-
const cleaned = subPath.replace(/^\/+|\/+$/g, "");
|
|
445
|
-
if (!cleaned)
|
|
446
|
-
return "index";
|
|
447
|
-
const parts = cleaned.split("/");
|
|
448
|
-
return parts[parts.length - 1] || "index";
|
|
449
|
-
}
|
|
450
|
-
function effectivePerms(route, meta, action) {
|
|
451
|
-
if (meta.side !== "admin" || route.public || route.ignorePerms)
|
|
452
|
-
return;
|
|
453
|
-
if (route.perms?.length)
|
|
454
|
-
return route.perms;
|
|
455
|
-
const act = action ?? actionFromSubPath(getRouteSubPath(route.path ?? "/", meta.prefix));
|
|
456
|
-
return [resolveRoutePerm(meta.module, meta.prefix, act)];
|
|
457
|
-
}
|
|
458
|
-
|
|
459
|
-
// src/routing/register.ts
|
|
460
|
-
var crudRegistrar;
|
|
461
|
-
function setCrudRegistrar(fn) {
|
|
462
|
-
crudRegistrar = fn;
|
|
463
|
-
}
|
|
464
|
-
var SIDE_PREFIX = {
|
|
465
|
-
admin: "/admin",
|
|
466
|
-
app: "/app"
|
|
467
|
-
};
|
|
468
|
-
var ADMIN_GUARD = "adminAuth";
|
|
469
|
-
var APP_GUARD = "auth";
|
|
470
|
-
var ELYSIA_METHODS = {
|
|
471
|
-
GET: "get",
|
|
472
|
-
POST: "post",
|
|
473
|
-
PUT: "put",
|
|
474
|
-
DELETE: "delete",
|
|
475
|
-
PATCH: "patch"
|
|
476
|
-
};
|
|
477
|
-
function getSidePrefix(side) {
|
|
478
|
-
return normalizePrefix(SIDE_PREFIX[side]);
|
|
479
|
-
}
|
|
480
|
-
function buildRouteSchema(route) {
|
|
481
|
-
if (route.params?.length)
|
|
482
|
-
return schemaFromParams(route.params);
|
|
483
|
-
const schema = {};
|
|
484
|
-
if (route.body !== undefined)
|
|
485
|
-
schema.body = route.body;
|
|
486
|
-
if (route.query !== undefined)
|
|
487
|
-
schema.query = route.query;
|
|
488
|
-
if (route.routeParams !== undefined)
|
|
489
|
-
schema.params = route.routeParams;
|
|
490
|
-
return Object.keys(schema).length > 0 ? schema : undefined;
|
|
491
|
-
}
|
|
492
|
-
function assertRouteParams(params, handler, controller) {
|
|
493
|
-
const seen = new Set;
|
|
494
|
-
for (const param of params) {
|
|
495
|
-
if (seen.has(param.source)) {
|
|
496
|
-
const label = param.source === "body" ? "Body" : param.source === "query" ? "Query" : "Param";
|
|
497
|
-
throw new Error(`[Router] ${controller}.${handler} \u91CD\u590D @${label}`);
|
|
498
|
-
}
|
|
499
|
-
seen.add(param.source);
|
|
500
|
-
}
|
|
501
|
-
}
|
|
502
|
-
function createParamHandler(instance, handlerName, params) {
|
|
503
|
-
const method = instance[handlerName];
|
|
504
|
-
const bound = method.bind(instance);
|
|
505
|
-
if (!params?.length)
|
|
506
|
-
return bound;
|
|
507
|
-
const sorted = [...params].sort((a, b) => a.index - b.index);
|
|
508
|
-
return (ctx) => {
|
|
509
|
-
const args = sorted.map((param) => {
|
|
510
|
-
if (param.source === "body")
|
|
511
|
-
return ctx.body;
|
|
512
|
-
if (param.source === "query")
|
|
513
|
-
return ctx.query;
|
|
514
|
-
if (param.source === "params")
|
|
515
|
-
return ctx.params;
|
|
516
|
-
throw new Error(`[Router] \u672A\u77E5\u53C2\u6570\u6765\u6E90: ${param.source}`);
|
|
517
|
-
});
|
|
518
|
-
return bound(...args, ctx);
|
|
519
|
-
};
|
|
520
|
-
}
|
|
521
|
-
function createPermsGuard(codes) {
|
|
522
|
-
return (ctx) => {
|
|
523
|
-
const status = ctx.status;
|
|
524
|
-
const store = Context.get();
|
|
525
|
-
if (store?.isSuper)
|
|
526
|
-
return;
|
|
527
|
-
const held = store?.perms ?? [];
|
|
528
|
-
if (codes.some((code) => held.includes(code)))
|
|
529
|
-
return;
|
|
530
|
-
return status(403);
|
|
531
|
-
};
|
|
532
|
-
}
|
|
533
|
-
function openApiSummary(name, remark) {
|
|
534
|
-
const title = name.replace(/^\/+|\/+$/g, "").split("/").pop() || name;
|
|
535
|
-
return remark ? `${title} ${remark}` : title;
|
|
536
|
-
}
|
|
537
|
-
function buildRouteOptions(route, meta) {
|
|
538
|
-
const schema = buildRouteSchema(route) ?? {};
|
|
539
|
-
const options = {
|
|
540
|
-
...schema,
|
|
541
|
-
detail: {
|
|
542
|
-
tags: [openApiTag(meta.module, meta.side)],
|
|
543
|
-
summary: openApiSummary(route.handler, route.summary)
|
|
544
|
-
}
|
|
545
|
-
};
|
|
546
|
-
if (meta.side === "admin" && !route.public) {
|
|
547
|
-
options[ADMIN_GUARD] = true;
|
|
548
|
-
}
|
|
549
|
-
if (meta.side === "app" && !route.public) {
|
|
550
|
-
options[APP_GUARD] = true;
|
|
551
|
-
}
|
|
552
|
-
const before = [];
|
|
553
|
-
const perms = effectivePerms(route, meta);
|
|
554
|
-
if (perms?.length)
|
|
555
|
-
before.push(createPermsGuard(perms));
|
|
556
|
-
if (route.middleware?.length)
|
|
557
|
-
before.push(...route.middleware);
|
|
558
|
-
if (before.length)
|
|
559
|
-
options.beforeHandle = before;
|
|
560
|
-
return options;
|
|
561
|
-
}
|
|
562
|
-
function normalizeCrudRouteOpts(opts) {
|
|
563
|
-
if (opts == null)
|
|
564
|
-
return {};
|
|
565
|
-
if (typeof opts === "boolean")
|
|
566
|
-
return { public: opts };
|
|
567
|
-
return opts;
|
|
568
|
-
}
|
|
569
|
-
function registerControllerPlugin(meta, _vomeConfig) {
|
|
570
|
-
const sidePrefix = getSidePrefix(meta.side);
|
|
571
|
-
const pluginPrefix = joinPrefix(sidePrefix, meta.prefix);
|
|
572
|
-
const instance = Ioc.get(meta.token);
|
|
573
|
-
let plugin = new Elysia({
|
|
574
|
-
prefix: pluginPrefix,
|
|
575
|
-
name: meta.token.name,
|
|
576
|
-
tags: [openApiTag(meta.module, meta.side)]
|
|
577
|
-
});
|
|
578
|
-
for (const mw of meta.middleware ?? []) {
|
|
579
|
-
plugin = plugin.onBeforeHandle(mw);
|
|
580
|
-
}
|
|
581
|
-
const autoRoutes = [];
|
|
582
|
-
for (const route of meta.routes) {
|
|
583
|
-
const handler = instance[route.handler];
|
|
584
|
-
if (typeof handler !== "function") {
|
|
585
|
-
throw new Error(`[Router] ${meta.token.name}.${route.handler} \u4E0D\u662F\u6709\u6548 handler`);
|
|
586
|
-
}
|
|
587
|
-
assertRouteParams(route.params ?? [], route.handler, meta.token.name);
|
|
588
|
-
const wrapped = createParamHandler(instance, route.handler, route.params);
|
|
589
|
-
const subPath = getRouteSubPath(route.path, meta.prefix);
|
|
590
|
-
const options = buildRouteOptions(route, meta);
|
|
591
|
-
const method = ELYSIA_METHODS[route.method];
|
|
592
|
-
plugin = plugin[method](subPath, wrapped, options);
|
|
593
|
-
}
|
|
594
|
-
if (meta.crud?.api?.length || meta.crud?.serviceApis?.length) {
|
|
595
|
-
if (!crudRegistrar) {
|
|
596
|
-
throw new Error(`[Router] ${meta.token.name} \u914D\u7F6E\u4E86 api/serviceApis\uFF0C\u4F46\u672A\u627E\u5230 CRUD \u5B9E\u73B0\uFF08@vome-core attachCrudRoutes \u672A\u6302\u8F7D\uFF09`);
|
|
597
|
-
}
|
|
598
|
-
plugin = crudRegistrar(plugin, meta, {
|
|
599
|
-
controller: instance,
|
|
600
|
-
routeOptions: (opts) => {
|
|
601
|
-
const { public: isPublic, action, summary } = normalizeCrudRouteOpts(opts);
|
|
602
|
-
const options = {
|
|
603
|
-
detail: {
|
|
604
|
-
tags: [openApiTag(meta.module, meta.side)],
|
|
605
|
-
summary: openApiSummary(action ?? "action", summary)
|
|
606
|
-
}
|
|
607
|
-
};
|
|
608
|
-
if (meta.side === "admin" && !isPublic) {
|
|
609
|
-
options[ADMIN_GUARD] = true;
|
|
610
|
-
if (action) {
|
|
611
|
-
const code = resolveRoutePerm(meta.module, meta.prefix, action);
|
|
612
|
-
options.beforeHandle = [createPermsGuard([code])];
|
|
613
|
-
}
|
|
614
|
-
}
|
|
615
|
-
return options;
|
|
616
|
-
}
|
|
617
|
-
});
|
|
618
|
-
for (const name of meta.crud?.api ?? []) {
|
|
619
|
-
const method = name === "info" ? "GET" : "POST";
|
|
620
|
-
autoRoutes.push({
|
|
621
|
-
method,
|
|
622
|
-
path: joinPrefix(meta.prefix, name),
|
|
623
|
-
handler: name,
|
|
624
|
-
autoCrud: true
|
|
625
|
-
});
|
|
626
|
-
}
|
|
627
|
-
for (const name of meta.crud?.serviceApis ?? []) {
|
|
628
|
-
autoRoutes.push({
|
|
629
|
-
method: "POST",
|
|
630
|
-
path: joinPrefix(meta.prefix, name),
|
|
631
|
-
handler: name,
|
|
632
|
-
autoCrud: true
|
|
633
|
-
});
|
|
634
|
-
}
|
|
635
|
-
}
|
|
636
|
-
return { plugin, pluginPrefix, autoRoutes };
|
|
637
|
-
}
|
|
638
|
-
function registerControllers(app, vomeConfig) {
|
|
639
|
-
let result = app;
|
|
640
|
-
let routeCount = 0;
|
|
641
|
-
const lines = [];
|
|
642
|
-
for (const meta of listControllers()) {
|
|
643
|
-
const { plugin, pluginPrefix, autoRoutes } = registerControllerPlugin(meta, vomeConfig);
|
|
644
|
-
result = result.use(plugin);
|
|
645
|
-
for (const route of [...meta.routes, ...autoRoutes]) {
|
|
646
|
-
routeCount += 1;
|
|
647
|
-
const subPath = getRouteSubPath(route.path, meta.prefix);
|
|
648
|
-
const fullPath = subPath === "/" ? pluginPrefix : joinPrefix(pluginPrefix, subPath.replace(/^\//, ""));
|
|
649
|
-
const flag = route.public ? " (public)" : route.autoCrud ? " (crud)" : "";
|
|
650
|
-
lines.push(`${route.method} ${fullPath}${flag}`);
|
|
651
|
-
}
|
|
652
|
-
}
|
|
653
|
-
if (routeCount > 0) {
|
|
654
|
-
console.log(`[Router] registered \u2190 ${routeCount} route(s)`);
|
|
655
|
-
for (const line of lines)
|
|
656
|
-
console.log(` ${line}`);
|
|
657
|
-
}
|
|
658
|
-
return result;
|
|
659
|
-
}
|
|
660
|
-
|
|
661
|
-
// src/comm/scan.ts
|
|
662
|
-
var {Glob } = globalThis.Bun;
|
|
663
|
-
var DEFAULT_EXT = /\.tsx?$/;
|
|
664
|
-
async function scanFiles(patterns, options = {}) {
|
|
665
|
-
const { cwd = process.cwd(), ext = DEFAULT_EXT } = options;
|
|
666
|
-
const list = Array.isArray(patterns) ? patterns : [patterns];
|
|
667
|
-
const files = [];
|
|
668
|
-
for (const pattern of list) {
|
|
669
|
-
const glob = new Glob(pattern);
|
|
670
|
-
for await (const path of glob.scan({ cwd, onlyFiles: true })) {
|
|
671
|
-
if (ext.test(path))
|
|
672
|
-
files.push(path);
|
|
673
|
-
}
|
|
674
|
-
}
|
|
675
|
-
return [...new Set(files)].sort();
|
|
676
|
-
}
|
|
677
|
-
|
|
678
|
-
// src/routing/context.ts
|
|
679
|
-
var context = null;
|
|
680
|
-
function setControllerScanContext(next) {
|
|
681
|
-
context = next;
|
|
682
|
-
}
|
|
683
|
-
function getControllerScanContext() {
|
|
684
|
-
return context;
|
|
685
|
-
}
|
|
686
|
-
function parseModuleFromPath(file) {
|
|
687
|
-
const matched = file.match(/modules\/([^/]+)\/controller\//);
|
|
688
|
-
if (!matched)
|
|
689
|
-
return "unknown";
|
|
690
|
-
return matched[1];
|
|
691
|
-
}
|
|
692
|
-
function parseControllerAutoPrefix(file) {
|
|
693
|
-
const matched = file.replace(/\\/g, "/").match(/modules\/([^/]+)\/controller\/(?:admin|app)\/(.+)\.tsx?$/);
|
|
694
|
-
if (!matched)
|
|
695
|
-
return "";
|
|
696
|
-
const module = matched[1];
|
|
697
|
-
const rest = matched[2].replace(/\/+/g, "/").replace(/^\/|\/$/g, "");
|
|
698
|
-
if (!rest)
|
|
699
|
-
return `/${module}`;
|
|
700
|
-
return `/${module}/${rest}`;
|
|
701
|
-
}
|
|
702
|
-
|
|
703
|
-
// src/comm/format-time.ts
|
|
704
|
-
var TIME_KEY_RE = /(?:Time|Date|At)$/;
|
|
705
|
-
var ISO_RE = /^\d{4}-\d{2}-\d{2}[T ]\d{2}:\d{2}:\d{2}(?:\.\d+)?(?:Z|[+-]\d{2}:?\d{2})?$/;
|
|
706
|
-
function formatDateTime(value) {
|
|
707
|
-
const d = value instanceof Date ? value : new Date(value);
|
|
708
|
-
if (Number.isNaN(d.getTime()))
|
|
709
|
-
return String(value);
|
|
710
|
-
return new Intl.DateTimeFormat("sv-SE", {
|
|
711
|
-
timeZone: "Asia/Shanghai",
|
|
712
|
-
year: "numeric",
|
|
713
|
-
month: "2-digit",
|
|
714
|
-
day: "2-digit",
|
|
715
|
-
hour: "2-digit",
|
|
716
|
-
minute: "2-digit",
|
|
717
|
-
second: "2-digit",
|
|
718
|
-
hour12: false
|
|
719
|
-
}).format(d).replace("T", " ");
|
|
720
|
-
}
|
|
721
|
-
function isTimeKey(key) {
|
|
722
|
-
return TIME_KEY_RE.test(key);
|
|
723
|
-
}
|
|
724
|
-
function formatApiDates(data) {
|
|
725
|
-
return walk(data);
|
|
726
|
-
}
|
|
727
|
-
function walk(value, key) {
|
|
728
|
-
if (value == null)
|
|
729
|
-
return value;
|
|
730
|
-
if (value instanceof Date)
|
|
731
|
-
return formatDateTime(value);
|
|
732
|
-
if (typeof value === "string" && key && isTimeKey(key) && ISO_RE.test(value)) {
|
|
733
|
-
return formatDateTime(value);
|
|
734
|
-
}
|
|
735
|
-
if (Array.isArray(value))
|
|
736
|
-
return value.map((item) => walk(item));
|
|
737
|
-
if (typeof value === "object") {
|
|
738
|
-
if (Object.prototype.toString.call(value) !== "[object Object]")
|
|
739
|
-
return value;
|
|
740
|
-
const out = {};
|
|
741
|
-
for (const [k, v] of Object.entries(value)) {
|
|
742
|
-
out[k] = walk(v, k);
|
|
743
|
-
}
|
|
744
|
-
return out;
|
|
745
|
-
}
|
|
746
|
-
return value;
|
|
747
|
-
}
|
|
748
|
-
|
|
749
|
-
// src/routing/base.ts
|
|
750
|
-
var RES_CODE = {
|
|
751
|
-
SUCCESS: 1000,
|
|
752
|
-
ERROR: 1001
|
|
753
|
-
};
|
|
754
|
-
|
|
755
|
-
class BaseController {
|
|
756
|
-
ok(data) {
|
|
757
|
-
const raw = data === undefined ? null : data;
|
|
758
|
-
return {
|
|
759
|
-
code: RES_CODE.SUCCESS,
|
|
760
|
-
message: "success",
|
|
761
|
-
data: raw == null ? raw : formatApiDates(raw)
|
|
762
|
-
};
|
|
763
|
-
}
|
|
764
|
-
fail(message = "error", code = RES_CODE.ERROR) {
|
|
765
|
-
return { code, message };
|
|
766
|
-
}
|
|
767
|
-
}
|
|
768
|
-
// src/ioc/decorators.ts
|
|
769
|
-
import"reflect-metadata";
|
|
770
|
-
function normalizeProvideArgs(idOrOptions) {
|
|
771
|
-
if (idOrOptions == null)
|
|
772
|
-
return {};
|
|
773
|
-
if (typeof idOrOptions === "string" || typeof idOrOptions === "symbol") {
|
|
774
|
-
return { id: idOrOptions };
|
|
775
|
-
}
|
|
776
|
-
return idOrOptions;
|
|
777
|
-
}
|
|
778
|
-
function Provide(idOrOptions) {
|
|
779
|
-
return (target) => {
|
|
780
|
-
const options = normalizeProvideArgs(idOrOptions);
|
|
781
|
-
const scope = options.scope ?? "singleton" /* Singleton */;
|
|
782
|
-
registerProvider({ token: target, useClass: target, scope });
|
|
783
|
-
if (options.id != null) {
|
|
784
|
-
registerProvider({ token: options.id, useClass: target, scope });
|
|
785
|
-
}
|
|
786
|
-
};
|
|
787
|
-
}
|
|
788
|
-
function Inject(token) {
|
|
789
|
-
return (target, propertyKey) => {
|
|
790
|
-
const designType = Reflect.getMetadata("design:type", target, propertyKey);
|
|
791
|
-
const injectToken = token ?? designType;
|
|
792
|
-
if (injectToken == null) {
|
|
793
|
-
throw new Error(`[Ioc] @Inject \u65E0\u6CD5\u63A8\u65AD ${String(propertyKey)} \u7684\u7C7B\u578B\uFF0C\u8BF7\u663E\u5F0F\u4F20\u5165 token`);
|
|
794
|
-
}
|
|
795
|
-
appendInjectMeta(target.constructor, {
|
|
796
|
-
propertyKey,
|
|
797
|
-
token: injectToken
|
|
798
|
-
});
|
|
799
|
-
};
|
|
800
|
-
}
|
|
801
|
-
// src/orm/query-op.ts
|
|
802
|
-
import {
|
|
803
|
-
and,
|
|
804
|
-
arrayContains,
|
|
805
|
-
arrayOverlaps,
|
|
806
|
-
asc,
|
|
807
|
-
desc,
|
|
808
|
-
eq,
|
|
809
|
-
gte,
|
|
810
|
-
inArray,
|
|
811
|
-
like,
|
|
812
|
-
lte,
|
|
813
|
-
or,
|
|
814
|
-
sql
|
|
815
|
-
} from "drizzle-orm";
|
|
816
|
-
function colName(ref) {
|
|
817
|
-
if (typeof ref === "string") {
|
|
818
|
-
const name = ref.includes(".") ? ref.split(".").pop() : ref;
|
|
819
|
-
return { column: name, param: name, none: false };
|
|
820
|
-
}
|
|
821
|
-
const column = ref.column.includes(".") ? ref.column.split(".").pop() : ref.column;
|
|
822
|
-
return {
|
|
823
|
-
column,
|
|
824
|
-
param: ref.requestParam ?? column,
|
|
825
|
-
none: Boolean(ref.none)
|
|
826
|
-
};
|
|
827
|
-
}
|
|
828
|
-
function rangeColumn(r) {
|
|
829
|
-
return r.column.includes(".") ? r.column.split(".").pop() : r.column;
|
|
830
|
-
}
|
|
831
|
-
function tableCol(table, name) {
|
|
832
|
-
const col = table[name];
|
|
833
|
-
if (col == null)
|
|
834
|
-
throw new Error(`[QueryOp] \u8868\u65E0\u5B57\u6BB5: ${name}`);
|
|
835
|
-
return col;
|
|
836
|
-
}
|
|
837
|
-
function isBlank(value) {
|
|
838
|
-
return value === undefined || value === null || value === "";
|
|
839
|
-
}
|
|
840
|
-
function compactWhere(result) {
|
|
841
|
-
if (result == null || result === false)
|
|
842
|
-
return [];
|
|
843
|
-
const list = Array.isArray(result) ? result : [result];
|
|
844
|
-
return list.filter((x) => x != null && x !== false);
|
|
845
|
-
}
|
|
846
|
-
var q = {
|
|
847
|
-
between(col, min, max) {
|
|
848
|
-
if (isBlank(min) || isBlank(max))
|
|
849
|
-
return;
|
|
850
|
-
return sql`${col} between ${min} and ${max}`;
|
|
851
|
-
},
|
|
852
|
-
range(col, start, end) {
|
|
853
|
-
const parts = [];
|
|
854
|
-
if (!isBlank(start))
|
|
855
|
-
parts.push(gte(col, start));
|
|
856
|
-
if (!isBlank(end))
|
|
857
|
-
parts.push(lte(col, end));
|
|
858
|
-
if (!parts.length)
|
|
859
|
-
return;
|
|
860
|
-
return parts.length === 1 ? parts[0] : and(...parts);
|
|
861
|
-
},
|
|
862
|
-
eqRest(params, table, map) {
|
|
863
|
-
const out = [];
|
|
864
|
-
for (const [key, value] of Object.entries(params)) {
|
|
865
|
-
if (isBlank(value))
|
|
866
|
-
continue;
|
|
867
|
-
const col = map?.[key] ?? table[key];
|
|
868
|
-
if (col == null)
|
|
869
|
-
continue;
|
|
870
|
-
out.push(eq(col, value));
|
|
871
|
-
}
|
|
872
|
-
return out;
|
|
873
|
-
},
|
|
874
|
-
contains(col, value) {
|
|
875
|
-
if (isBlank(value))
|
|
876
|
-
return;
|
|
877
|
-
const values = Array.isArray(value) ? value : [value];
|
|
878
|
-
if (!values.length)
|
|
879
|
-
return;
|
|
880
|
-
return values.length === 1 ? arrayContains(col, values) : arrayOverlaps(col, values);
|
|
881
|
-
}
|
|
882
|
-
};
|
|
883
|
-
function buildFieldClauses(table, body, op) {
|
|
884
|
-
const clauses = [];
|
|
885
|
-
if (op.keyWordLikeFields?.length && !isBlank(body.keyWord)) {
|
|
886
|
-
const kw = `%${String(body.keyWord)}%`;
|
|
887
|
-
const likes = op.keyWordLikeFields.map((f) => {
|
|
888
|
-
const name = f.includes(".") ? f.split(".").pop() : f;
|
|
889
|
-
return like(tableCol(table, name), kw);
|
|
890
|
-
});
|
|
891
|
-
if (likes.length === 1)
|
|
892
|
-
clauses.push(likes[0]);
|
|
893
|
-
else if (likes.length > 1)
|
|
894
|
-
clauses.push(or(...likes));
|
|
895
|
-
}
|
|
896
|
-
for (const ref of op.fieldEq ?? []) {
|
|
897
|
-
const { column, param } = colName(ref);
|
|
898
|
-
const value = body[param];
|
|
899
|
-
if (isBlank(value))
|
|
900
|
-
continue;
|
|
901
|
-
if (Array.isArray(value)) {
|
|
902
|
-
if (!value.length)
|
|
903
|
-
continue;
|
|
904
|
-
clauses.push(inArray(tableCol(table, column), value));
|
|
905
|
-
} else {
|
|
906
|
-
clauses.push(eq(tableCol(table, column), value));
|
|
907
|
-
}
|
|
908
|
-
}
|
|
909
|
-
for (const ref of op.fieldLike ?? []) {
|
|
910
|
-
const { column, param } = colName(ref);
|
|
911
|
-
const value = body[param];
|
|
912
|
-
if (isBlank(value))
|
|
913
|
-
continue;
|
|
914
|
-
clauses.push(like(tableCol(table, column), `%${String(value)}%`));
|
|
915
|
-
}
|
|
916
|
-
for (const ref of op.fieldArray ?? []) {
|
|
917
|
-
const { column, param } = colName(ref);
|
|
918
|
-
const clause = q.contains(tableCol(table, column), body[param]);
|
|
919
|
-
if (clause)
|
|
920
|
-
clauses.push(clause);
|
|
921
|
-
}
|
|
922
|
-
for (const r of op.fieldRange ?? []) {
|
|
923
|
-
const col = tableCol(table, rangeColumn(r));
|
|
924
|
-
const clause = q.range(col, body[r.min], body[r.max]);
|
|
925
|
-
if (clause)
|
|
926
|
-
clauses.push(clause);
|
|
927
|
-
}
|
|
928
|
-
return clauses;
|
|
929
|
-
}
|
|
930
|
-
function buildOrderBy(table, body, op) {
|
|
931
|
-
const orderBy = [];
|
|
932
|
-
const orderField = body.order != null ? String(body.order) : undefined;
|
|
933
|
-
const sortDir = body.sort === "asc" || body.sort === "desc" ? body.sort : undefined;
|
|
934
|
-
if (orderField) {
|
|
935
|
-
const col = tableCol(table, orderField);
|
|
936
|
-
orderBy.push(sortDir === "asc" ? asc(col) : desc(col));
|
|
937
|
-
} else if (op.addOrderBy) {
|
|
938
|
-
for (const [field, dir] of Object.entries(op.addOrderBy)) {
|
|
939
|
-
const name = field.includes(".") ? field.split(".").pop() : field;
|
|
940
|
-
const col = tableCol(table, name);
|
|
941
|
-
orderBy.push(dir === "asc" ? asc(col) : desc(col));
|
|
942
|
-
}
|
|
943
|
-
}
|
|
944
|
-
return orderBy;
|
|
945
|
-
}
|
|
946
|
-
function needsAdvancedQuery(op) {
|
|
947
|
-
return !!(op?.join?.length || op?.select);
|
|
948
|
-
}
|
|
949
|
-
async function buildQueryOp(table, body, op = {}, request) {
|
|
950
|
-
const clauses = buildFieldClauses(table, body, op);
|
|
951
|
-
const orderBySql = buildOrderBy(table, body, op);
|
|
952
|
-
const ctx = { body, request: request ?? new Request("http://local") };
|
|
953
|
-
if (op.where) {
|
|
954
|
-
clauses.push(...compactWhere(await op.where(ctx)));
|
|
955
|
-
}
|
|
956
|
-
if (op.extend) {
|
|
957
|
-
const qb = {
|
|
958
|
-
andWhere(condition) {
|
|
959
|
-
if (condition != null && condition !== false)
|
|
960
|
-
clauses.push(condition);
|
|
961
|
-
},
|
|
962
|
-
orderBy(...orders) {
|
|
963
|
-
for (const o of orders) {
|
|
964
|
-
if (o != null)
|
|
965
|
-
orderBySql.push(o);
|
|
966
|
-
}
|
|
967
|
-
}
|
|
968
|
-
};
|
|
969
|
-
await op.extend(qb, ctx);
|
|
970
|
-
}
|
|
971
|
-
const where = clauses.length === 0 ? undefined : clauses.length === 1 ? clauses[0] : and(...clauses);
|
|
972
|
-
return { where, orderBySql };
|
|
973
|
-
}
|
|
974
|
-
|
|
975
|
-
// src/orm/query-builder.ts
|
|
976
|
-
import {
|
|
977
|
-
and as and4,
|
|
978
|
-
count,
|
|
979
|
-
countDistinct,
|
|
980
|
-
getTableColumns,
|
|
981
|
-
isNotNull,
|
|
982
|
-
isNull,
|
|
983
|
-
sql as sql4
|
|
984
|
-
} from "drizzle-orm";
|
|
985
|
-
|
|
986
|
-
// src/orm/crud-config.ts
|
|
987
|
-
function readCrudConfig() {
|
|
988
|
-
return VomeConfig.vome?.crud ?? {};
|
|
989
|
-
}
|
|
990
|
-
function resolveUpsert(override) {
|
|
991
|
-
return override ?? readCrudConfig().upsert ?? "insert";
|
|
992
|
-
}
|
|
993
|
-
function resolveSoftDelete(override) {
|
|
994
|
-
if (override != null)
|
|
995
|
-
return override;
|
|
996
|
-
return readCrudConfig().softDelete === true;
|
|
997
|
-
}
|
|
998
|
-
|
|
999
|
-
// src/orm/db-store.ts
|
|
1000
|
-
class DbStore {
|
|
1001
|
-
drizzle;
|
|
1002
|
-
client;
|
|
1003
|
-
schema;
|
|
1004
|
-
sql;
|
|
1005
|
-
constructor(drizzle, client, schema, sql2) {
|
|
1006
|
-
this.drizzle = drizzle;
|
|
1007
|
-
this.client = client;
|
|
1008
|
-
this.schema = schema;
|
|
1009
|
-
this.sql = sql2;
|
|
1010
|
-
}
|
|
1011
|
-
}
|
|
1012
|
-
|
|
1013
|
-
// src/orm/data-scope.ts
|
|
1014
|
-
import { and as and3, inArray as inArray2, sql as sql3 } from "drizzle-orm";
|
|
1015
|
-
|
|
1016
|
-
// src/orm/tenant.ts
|
|
1017
|
-
import { and as and2, eq as eq2, sql as sql2 } from "drizzle-orm";
|
|
1018
|
-
var SKIP_KEY = "__skipTenant";
|
|
1019
|
-
function isTenantEnabled() {
|
|
1020
|
-
return VomeConfig.vome?.tenant === true;
|
|
1021
|
-
}
|
|
1022
|
-
function tableHasTenantId(table) {
|
|
1023
|
-
return table.tenantId != null;
|
|
1024
|
-
}
|
|
1025
|
-
function resolveTenantScope() {
|
|
1026
|
-
if (!isTenantEnabled())
|
|
1027
|
-
return "off";
|
|
1028
|
-
const ctx = Context.get();
|
|
1029
|
-
if (ctx?.[SKIP_KEY])
|
|
1030
|
-
return "off";
|
|
1031
|
-
if (ctx?.isSuper)
|
|
1032
|
-
return "all";
|
|
1033
|
-
const raw = ctx?.tenantId;
|
|
1034
|
-
const id = typeof raw === "number" ? raw : Number(raw);
|
|
1035
|
-
if (!Number.isFinite(id) || id <= 0)
|
|
1036
|
-
return "none";
|
|
1037
|
-
return id;
|
|
1038
|
-
}
|
|
1039
|
-
function applyTenantWhere(table, where) {
|
|
1040
|
-
if (!tableHasTenantId(table))
|
|
1041
|
-
return where;
|
|
1042
|
-
const scope = resolveTenantScope();
|
|
1043
|
-
if (scope === "off" || scope === "all")
|
|
1044
|
-
return where;
|
|
1045
|
-
const col = table.tenantId;
|
|
1046
|
-
const tenantClause = scope === "none" ? sql2`false` : eq2(col, scope);
|
|
1047
|
-
if (where && tenantClause)
|
|
1048
|
-
return and2(where, tenantClause);
|
|
1049
|
-
return where ?? tenantClause;
|
|
1050
|
-
}
|
|
1051
|
-
function stampTenantId(table, data) {
|
|
1052
|
-
if (!tableHasTenantId(table))
|
|
1053
|
-
return data;
|
|
1054
|
-
const scope = resolveTenantScope();
|
|
1055
|
-
if (typeof scope !== "number")
|
|
1056
|
-
return data;
|
|
1057
|
-
if (data.tenantId != null)
|
|
1058
|
-
return data;
|
|
1059
|
-
return { ...data, tenantId: scope };
|
|
1060
|
-
}
|
|
1061
|
-
async function noTenant(fn) {
|
|
1062
|
-
const ctx = Context.get();
|
|
1063
|
-
if (!ctx)
|
|
1064
|
-
return fn();
|
|
1065
|
-
const prev = ctx[SKIP_KEY];
|
|
1066
|
-
ctx[SKIP_KEY] = true;
|
|
1067
|
-
try {
|
|
1068
|
-
return await fn();
|
|
1069
|
-
} finally {
|
|
1070
|
-
if (prev === undefined)
|
|
1071
|
-
delete ctx[SKIP_KEY];
|
|
1072
|
-
else
|
|
1073
|
-
ctx[SKIP_KEY] = prev;
|
|
1074
|
-
}
|
|
1075
|
-
}
|
|
1076
|
-
function normalizeHost(host) {
|
|
1077
|
-
if (!host)
|
|
1078
|
-
return "";
|
|
1079
|
-
return host.trim().toLowerCase().replace(/:\d+$/, "");
|
|
1080
|
-
}
|
|
1081
|
-
|
|
1082
|
-
// src/orm/data-scope.ts
|
|
1083
|
-
var SKIP_KEY2 = "__skipDataScope";
|
|
1084
|
-
function tableHasDepartmentId(table) {
|
|
1085
|
-
return table.departmentId != null;
|
|
1086
|
-
}
|
|
1087
|
-
function resolveDataScope() {
|
|
1088
|
-
const ctx = Context.get();
|
|
1089
|
-
if (!ctx)
|
|
1090
|
-
return "off";
|
|
1091
|
-
if (ctx[SKIP_KEY2])
|
|
1092
|
-
return "off";
|
|
1093
|
-
if (ctx.isSuper)
|
|
1094
|
-
return "all";
|
|
1095
|
-
const mode = ctx.dataScope;
|
|
1096
|
-
if (mode == null || mode === "")
|
|
1097
|
-
return "off";
|
|
1098
|
-
if (mode === "all")
|
|
1099
|
-
return "all";
|
|
1100
|
-
if (mode === "none")
|
|
1101
|
-
return "none";
|
|
1102
|
-
const raw = ctx.dataScopeDeptIds;
|
|
1103
|
-
const ids = Array.isArray(raw) ? raw.map((id) => Number(id)).filter((id) => Number.isFinite(id) && id > 0) : [];
|
|
1104
|
-
if (!ids.length)
|
|
1105
|
-
return "none";
|
|
1106
|
-
return [...new Set(ids)];
|
|
1107
|
-
}
|
|
1108
|
-
function applyDataScopeWhere(table, where) {
|
|
1109
|
-
if (!tableHasDepartmentId(table))
|
|
1110
|
-
return where;
|
|
1111
|
-
const scope = resolveDataScope();
|
|
1112
|
-
if (scope === "off" || scope === "all")
|
|
1113
|
-
return where;
|
|
1114
|
-
const col = table.departmentId;
|
|
1115
|
-
const clause = scope === "none" ? sql3`false` : inArray2(col, scope);
|
|
1116
|
-
if (where)
|
|
1117
|
-
return and3(where, clause);
|
|
1118
|
-
return clause;
|
|
1119
|
-
}
|
|
1120
|
-
function applyRowScopes(table, where) {
|
|
1121
|
-
return applyDataScopeWhere(table, applyTenantWhere(table, where));
|
|
1122
|
-
}
|
|
1123
|
-
async function noDataScope(fn) {
|
|
1124
|
-
const ctx = Context.get();
|
|
1125
|
-
if (!ctx)
|
|
1126
|
-
return fn();
|
|
1127
|
-
const prev = ctx[SKIP_KEY2];
|
|
1128
|
-
ctx[SKIP_KEY2] = true;
|
|
1129
|
-
try {
|
|
1130
|
-
return await fn();
|
|
1131
|
-
} finally {
|
|
1132
|
-
if (prev === undefined)
|
|
1133
|
-
delete ctx[SKIP_KEY2];
|
|
1134
|
-
else
|
|
1135
|
-
ctx[SKIP_KEY2] = prev;
|
|
1136
|
-
}
|
|
1137
|
-
}
|
|
1138
|
-
|
|
1139
|
-
// src/orm/query-builder.ts
|
|
1140
|
-
function deletedAtColumn(table) {
|
|
1141
|
-
return table.deletedAt;
|
|
1142
|
-
}
|
|
1143
|
-
function trashClause(table, options) {
|
|
1144
|
-
if (!resolveSoftDelete(options?.softDelete))
|
|
1145
|
-
return;
|
|
1146
|
-
const col = deletedAtColumn(table);
|
|
1147
|
-
if (col == null)
|
|
1148
|
-
return;
|
|
1149
|
-
if (options?.onlyTrashed)
|
|
1150
|
-
return isNotNull(col);
|
|
1151
|
-
if (options?.withTrashed)
|
|
1152
|
-
return;
|
|
1153
|
-
return isNull(col);
|
|
1154
|
-
}
|
|
1155
|
-
function mergeWhere(where, trash) {
|
|
1156
|
-
if (where && trash)
|
|
1157
|
-
return and4(trash, where);
|
|
1158
|
-
return where ?? trash;
|
|
1159
|
-
}
|
|
1160
|
-
function applyJoins(query, main, op) {
|
|
1161
|
-
let next = query;
|
|
1162
|
-
for (const join2 of op.join ?? []) {
|
|
1163
|
-
const table = join2.table;
|
|
1164
|
-
const on = join2.on(main);
|
|
1165
|
-
const type = join2.type ?? "leftJoin";
|
|
1166
|
-
if (type === "innerJoin" || type === "join") {
|
|
1167
|
-
next = next.innerJoin(table, on);
|
|
1168
|
-
} else {
|
|
1169
|
-
next = next.leftJoin(table, on);
|
|
1170
|
-
}
|
|
1171
|
-
}
|
|
1172
|
-
return next;
|
|
1173
|
-
}
|
|
1174
|
-
function resolveSelect(main, op) {
|
|
1175
|
-
if (op.select)
|
|
1176
|
-
return op.select;
|
|
1177
|
-
return getTableColumns(main);
|
|
1178
|
-
}
|
|
1179
|
-
function countExpr(main, hasJoin) {
|
|
1180
|
-
const idCol = main.id;
|
|
1181
|
-
if (idCol != null && hasJoin)
|
|
1182
|
-
return countDistinct(idCol);
|
|
1183
|
-
if (idCol != null)
|
|
1184
|
-
return count(idCol);
|
|
1185
|
-
return count(sql4`*`);
|
|
1186
|
-
}
|
|
1187
|
-
async function queryWithOp(main, body, op, options) {
|
|
1188
|
-
const built = await buildQueryOp(main, body, op, options.request);
|
|
1189
|
-
const trash = trashClause(main, options.trash);
|
|
1190
|
-
const where = applyRowScopes(main, mergeWhere(built.where, trash));
|
|
1191
|
-
const select = resolveSelect(main, op);
|
|
1192
|
-
const hasJoin = !!op.join?.length;
|
|
1193
|
-
const db = Ioc.get(DbStore).drizzle;
|
|
1194
|
-
let listQuery = applyJoins(db.select(select).from(main), main, op);
|
|
1195
|
-
if (where)
|
|
1196
|
-
listQuery = listQuery.where(where);
|
|
1197
|
-
if (built.orderBySql.length)
|
|
1198
|
-
listQuery = listQuery.orderBy(...built.orderBySql);
|
|
1199
|
-
if (options.mode === "list") {
|
|
1200
|
-
return await listQuery;
|
|
1201
|
-
}
|
|
1202
|
-
const page = Math.max(1, Number(body.page ?? 1));
|
|
1203
|
-
const size = Math.min(100, Math.max(1, Number(body.size ?? 20)));
|
|
1204
|
-
const offset = (page - 1) * size;
|
|
1205
|
-
const list = await listQuery.limit(size).offset(offset);
|
|
1206
|
-
let countQuery = applyJoins(db.select({ value: countExpr(main, hasJoin) }).from(main), main, op);
|
|
1207
|
-
if (where)
|
|
1208
|
-
countQuery = countQuery.where(where);
|
|
1209
|
-
const rows = await countQuery;
|
|
1210
|
-
const total = Number(rows[0]?.value ?? 0);
|
|
1211
|
-
return { list, pagination: { page, size, total } };
|
|
1212
|
-
}
|
|
1213
|
-
|
|
1214
|
-
// src/orm/repository.ts
|
|
1215
|
-
import { and as and5, count as count2, eq as eq3, inArray as inArray3, isNotNull as isNotNull2, isNull as isNull2 } from "drizzle-orm";
|
|
1216
|
-
|
|
1217
|
-
// src/orm/entity-schema.ts
|
|
1218
|
-
import { createInsertSchema, createSelectSchema, createUpdateSchema } from "drizzle-zod";
|
|
1219
|
-
function entitySchemas(table) {
|
|
1220
|
-
return {
|
|
1221
|
-
select: createSelectSchema(table),
|
|
1222
|
-
insert: createInsertSchema(table),
|
|
1223
|
-
update: createUpdateSchema(table)
|
|
1224
|
-
};
|
|
1225
|
-
}
|
|
1226
|
-
|
|
1227
|
-
// src/orm/repository.ts
|
|
1228
|
-
var WRITE_META_KEYS = ["createTime", "updateTime", "deletedAt"];
|
|
1229
|
-
function sanitizeWritePayload(data) {
|
|
1230
|
-
const raw = data && typeof data === "object" && !Array.isArray(data) ? { ...data } : {};
|
|
1231
|
-
for (const k of WRITE_META_KEYS)
|
|
1232
|
-
delete raw[k];
|
|
1233
|
-
for (const [k, v] of Object.entries(raw)) {
|
|
1234
|
-
if (typeof v !== "string")
|
|
1235
|
-
continue;
|
|
1236
|
-
if (!/^\d{4}-\d{2}-\d{2}/.test(v))
|
|
1237
|
-
continue;
|
|
1238
|
-
const d = new Date(v);
|
|
1239
|
-
if (!Number.isNaN(d.getTime()))
|
|
1240
|
-
raw[k] = d;
|
|
1241
|
-
}
|
|
1242
|
-
return raw;
|
|
1243
|
-
}
|
|
1244
|
-
function isSqlLike(v) {
|
|
1245
|
-
return !!v && typeof v === "object" && v.getSQL != null;
|
|
1246
|
-
}
|
|
1247
|
-
function db() {
|
|
1248
|
-
return Ioc.get(DbStore).drizzle;
|
|
1249
|
-
}
|
|
1250
|
-
function tableId(table) {
|
|
1251
|
-
const id = table.id;
|
|
1252
|
-
if (!id) {
|
|
1253
|
-
throw new Error("[Repository] \u8868\u65E0 id \u5217\uFF0C\u8BF7\u6539\u7528 find(where) / findOne(where)");
|
|
1254
|
-
}
|
|
1255
|
-
return id;
|
|
1256
|
-
}
|
|
1257
|
-
function deletedAtColumn2(table) {
|
|
1258
|
-
return table.deletedAt;
|
|
1259
|
-
}
|
|
1260
|
-
function mergeWhere2(where, trash) {
|
|
1261
|
-
if (where && trash)
|
|
1262
|
-
return and5(trash, where);
|
|
1263
|
-
return where ?? trash;
|
|
1264
|
-
}
|
|
1265
|
-
function trashClause2(table, options) {
|
|
1266
|
-
if (!resolveSoftDelete(options?.softDelete))
|
|
1267
|
-
return;
|
|
1268
|
-
const col = deletedAtColumn2(table);
|
|
1269
|
-
if (col == null)
|
|
1270
|
-
return;
|
|
1271
|
-
if (options?.onlyTrashed)
|
|
1272
|
-
return isNotNull2(col);
|
|
1273
|
-
if (options?.withTrashed)
|
|
1274
|
-
return;
|
|
1275
|
-
return isNull2(col);
|
|
1276
|
-
}
|
|
1277
|
-
|
|
1278
|
-
class Repository {
|
|
1279
|
-
table;
|
|
1280
|
-
schema;
|
|
1281
|
-
constructor(table, schema) {
|
|
1282
|
-
this.table = table;
|
|
1283
|
-
this.schema = schema ?? entitySchemas(table);
|
|
1284
|
-
}
|
|
1285
|
-
supportsSoftDelete() {
|
|
1286
|
-
return deletedAtColumn2(this.table) != null;
|
|
1287
|
-
}
|
|
1288
|
-
scopedWhere(where, options) {
|
|
1289
|
-
return applyRowScopes(this.table, mergeWhere2(where, trashClause2(this.table, options)));
|
|
1290
|
-
}
|
|
1291
|
-
async find(where, options) {
|
|
1292
|
-
const scoped = this.scopedWhere(where, options);
|
|
1293
|
-
let query = db().select().from(this.table);
|
|
1294
|
-
if (scoped)
|
|
1295
|
-
query = query.where(scoped);
|
|
1296
|
-
if (options?.orderBy?.length)
|
|
1297
|
-
query = query.orderBy(...options.orderBy);
|
|
1298
|
-
return await query;
|
|
1299
|
-
}
|
|
1300
|
-
async findOne(where, options) {
|
|
1301
|
-
const [row] = await this.find(where, options);
|
|
1302
|
-
return row;
|
|
1303
|
-
}
|
|
1304
|
-
async findById(id, options) {
|
|
1305
|
-
return this.findOne(eq3(tableId(this.table), id), options);
|
|
1306
|
-
}
|
|
1307
|
-
async count(where, options) {
|
|
1308
|
-
const scoped = this.scopedWhere(where, options);
|
|
1309
|
-
const query = db().select({ value: count2() }).from(this.table);
|
|
1310
|
-
const rows = scoped ? await query.where(scoped) : await query;
|
|
1311
|
-
return Number(rows[0]?.value ?? 0);
|
|
1312
|
-
}
|
|
1313
|
-
async findPage(options) {
|
|
1314
|
-
const { page, size, where, orderBy, withTrashed, onlyTrashed, softDelete } = options;
|
|
1315
|
-
const trashOpts = { withTrashed, onlyTrashed, softDelete };
|
|
1316
|
-
const scoped = this.scopedWhere(where, trashOpts);
|
|
1317
|
-
const offset = (page - 1) * size;
|
|
1318
|
-
let query = db().select().from(this.table);
|
|
1319
|
-
if (scoped)
|
|
1320
|
-
query = query.where(scoped);
|
|
1321
|
-
if (orderBy?.length)
|
|
1322
|
-
query = query.orderBy(...orderBy);
|
|
1323
|
-
const list = await query.limit(size).offset(offset);
|
|
1324
|
-
const total = await this.count(where, trashOpts);
|
|
1325
|
-
return { list, pagination: { page, size, total } };
|
|
1326
|
-
}
|
|
1327
|
-
parseInsert(item) {
|
|
1328
|
-
const stamped = stampTenantId(this.table, sanitizeWritePayload(item));
|
|
1329
|
-
return this.schema.insert.parse(stamped);
|
|
1330
|
-
}
|
|
1331
|
-
async create(data) {
|
|
1332
|
-
if (Array.isArray(data)) {
|
|
1333
|
-
if (!data.length)
|
|
1334
|
-
return [];
|
|
1335
|
-
const values = data.map((item) => this.parseInsert(item));
|
|
1336
|
-
return await db().insert(this.table).values(values).returning();
|
|
1337
|
-
}
|
|
1338
|
-
const [row] = await db().insert(this.table).values(this.parseInsert(data)).returning();
|
|
1339
|
-
return row;
|
|
1340
|
-
}
|
|
1341
|
-
async save(data) {
|
|
1342
|
-
if (Array.isArray(data)) {
|
|
1343
|
-
if (!data.length)
|
|
1344
|
-
return [];
|
|
1345
|
-
const rows = data;
|
|
1346
|
-
const idCol = tableId(this.table);
|
|
1347
|
-
const withId = rows.filter((r) => r?.id != null && r.id !== "");
|
|
1348
|
-
const withoutId = rows.filter((r) => r?.id == null || r.id === "");
|
|
1349
|
-
let existingIds = new Set;
|
|
1350
|
-
if (withId.length) {
|
|
1351
|
-
const found = await this.find(inArray3(idCol, withId.map((r) => r.id)));
|
|
1352
|
-
existingIds = new Set(found.map((r) => r.id));
|
|
1353
|
-
}
|
|
1354
|
-
const toUpdate = [];
|
|
1355
|
-
const toInsert = [...withoutId];
|
|
1356
|
-
for (const r of withId) {
|
|
1357
|
-
if (existingIds.has(r.id))
|
|
1358
|
-
toUpdate.push(r);
|
|
1359
|
-
else
|
|
1360
|
-
toInsert.push(r);
|
|
1361
|
-
}
|
|
1362
|
-
const updated = toUpdate.length ? await this.update(toUpdate) : [];
|
|
1363
|
-
const inserted = toInsert.length ? await this.create(toInsert) : [];
|
|
1364
|
-
return [
|
|
1365
|
-
...Array.isArray(updated) ? updated : updated ? [updated] : [],
|
|
1366
|
-
...Array.isArray(inserted) ? inserted : inserted ? [inserted] : []
|
|
1367
|
-
];
|
|
1368
|
-
}
|
|
1369
|
-
const record = data;
|
|
1370
|
-
const id = record?.id;
|
|
1371
|
-
if (id != null && id !== "") {
|
|
1372
|
-
const existing = await this.findById(id);
|
|
1373
|
-
if (existing) {
|
|
1374
|
-
const { id: _omit, ...patch } = record;
|
|
1375
|
-
const updated = await this.update(eq3(tableId(this.table), id), patch);
|
|
1376
|
-
return updated ?? existing;
|
|
1377
|
-
}
|
|
1378
|
-
}
|
|
1379
|
-
return await this.create(data);
|
|
1380
|
-
}
|
|
1381
|
-
async update(whereOrRows, data) {
|
|
1382
|
-
if (Array.isArray(whereOrRows)) {
|
|
1383
|
-
return this.updateByRows(whereOrRows);
|
|
1384
|
-
}
|
|
1385
|
-
const patch = this.schema.update.parse(sanitizeWritePayload(data));
|
|
1386
|
-
const scoped = applyRowScopes(this.table, whereOrRows);
|
|
1387
|
-
if (!scoped)
|
|
1388
|
-
return;
|
|
1389
|
-
const [row] = await db().update(this.table).set(patch).where(scoped).returning();
|
|
1390
|
-
return row;
|
|
1391
|
-
}
|
|
1392
|
-
async updateByRows(rows) {
|
|
1393
|
-
if (!rows.length)
|
|
1394
|
-
return [];
|
|
1395
|
-
const idCol = tableId(this.table);
|
|
1396
|
-
const groups = new Map;
|
|
1397
|
-
for (const row of rows) {
|
|
1398
|
-
const id = row.id;
|
|
1399
|
-
if (id == null || id === "") {
|
|
1400
|
-
throw new Error("[Repository] \u6279\u91CF\u66F4\u65B0\u6BCF\u6761\u9700\u5E26 id");
|
|
1401
|
-
}
|
|
1402
|
-
const { id: _omit, ...rest } = row;
|
|
1403
|
-
const patch = this.schema.update.parse(sanitizeWritePayload(rest));
|
|
1404
|
-
const key = JSON.stringify(patch);
|
|
1405
|
-
const g = groups.get(key);
|
|
1406
|
-
if (g)
|
|
1407
|
-
g.ids.push(id);
|
|
1408
|
-
else
|
|
1409
|
-
groups.set(key, { ids: [id], patch });
|
|
1410
|
-
}
|
|
1411
|
-
const out = [];
|
|
1412
|
-
for (const { ids, patch } of groups.values()) {
|
|
1413
|
-
const scoped = applyRowScopes(this.table, inArray3(idCol, ids));
|
|
1414
|
-
if (!scoped)
|
|
1415
|
-
continue;
|
|
1416
|
-
const updated = await db().update(this.table).set(patch).where(scoped).returning();
|
|
1417
|
-
out.push(...updated);
|
|
1418
|
-
}
|
|
1419
|
-
return out;
|
|
1420
|
-
}
|
|
1421
|
-
resolveIdWhere(whereOrIds) {
|
|
1422
|
-
if (isSqlLike(whereOrIds)) {
|
|
1423
|
-
return applyRowScopes(this.table, whereOrIds);
|
|
1424
|
-
}
|
|
1425
|
-
const ids = Array.isArray(whereOrIds) ? whereOrIds : [whereOrIds];
|
|
1426
|
-
if (!ids.length)
|
|
1427
|
-
return;
|
|
1428
|
-
return applyRowScopes(this.table, inArray3(tableId(this.table), ids));
|
|
1429
|
-
}
|
|
1430
|
-
async softDelete(whereOrIds) {
|
|
1431
|
-
if (!this.supportsSoftDelete()) {
|
|
1432
|
-
throw new Error("[Repository] \u8868\u65E0 deletedAt\uFF0C\u65E0\u6CD5\u8F6F\u5220\u9664");
|
|
1433
|
-
}
|
|
1434
|
-
const scoped = this.resolveIdWhere(whereOrIds);
|
|
1435
|
-
if (!scoped)
|
|
1436
|
-
return;
|
|
1437
|
-
await db().update(this.table).set({ deletedAt: new Date }).where(scoped);
|
|
1438
|
-
}
|
|
1439
|
-
async restore(whereOrIds) {
|
|
1440
|
-
if (!this.supportsSoftDelete()) {
|
|
1441
|
-
throw new Error("[Repository] \u8868\u65E0 deletedAt\uFF0C\u65E0\u6CD5\u6062\u590D");
|
|
1442
|
-
}
|
|
1443
|
-
const scoped = this.resolveIdWhere(whereOrIds);
|
|
1444
|
-
if (!scoped)
|
|
1445
|
-
return;
|
|
1446
|
-
await db().update(this.table).set({ deletedAt: null }).where(scoped);
|
|
1447
|
-
}
|
|
1448
|
-
async forceDelete(whereOrIds) {
|
|
1449
|
-
const scoped = this.resolveIdWhere(whereOrIds);
|
|
1450
|
-
if (!scoped)
|
|
1451
|
-
return;
|
|
1452
|
-
await db().delete(this.table).where(scoped);
|
|
1453
|
-
}
|
|
1454
|
-
}
|
|
1455
|
-
var repoCache = new WeakMap;
|
|
1456
|
-
function getRepository(table) {
|
|
1457
|
-
const cached = repoCache.get(table);
|
|
1458
|
-
if (cached)
|
|
1459
|
-
return cached;
|
|
1460
|
-
const repo = new Repository(table);
|
|
1461
|
-
repoCache.set(table, repo);
|
|
1462
|
-
return repo;
|
|
1463
|
-
}
|
|
1464
|
-
function InjectRepository(table) {
|
|
1465
|
-
return (target, propertyKey) => {
|
|
1466
|
-
appendInjectMeta(target.constructor, {
|
|
1467
|
-
propertyKey,
|
|
1468
|
-
resolve: () => getRepository(table)
|
|
1469
|
-
});
|
|
1470
|
-
};
|
|
1471
|
-
}
|
|
1472
|
-
|
|
1473
|
-
// src/orm/service.ts
|
|
1474
|
-
function isSql(v) {
|
|
1475
|
-
return !!v && typeof v === "object" && v.getSQL != null;
|
|
1476
|
-
}
|
|
1477
|
-
|
|
1478
|
-
class BaseService {
|
|
1479
|
-
entity;
|
|
1480
|
-
bindEntity(repo) {
|
|
1481
|
-
if (!this.entity)
|
|
1482
|
-
this.entity = repo;
|
|
1483
|
-
}
|
|
1484
|
-
setEntity(repo) {
|
|
1485
|
-
this.entity = repo;
|
|
1486
|
-
}
|
|
1487
|
-
hasEntity() {
|
|
1488
|
-
return !!this.entity;
|
|
1489
|
-
}
|
|
1490
|
-
getRepo() {
|
|
1491
|
-
return this.requireEntity();
|
|
1492
|
-
}
|
|
1493
|
-
requireEntity() {
|
|
1494
|
-
if (!this.entity) {
|
|
1495
|
-
throw new Error("[BaseService] \u672A\u7ED1\u5B9A\u5B9E\u4F53\uFF0C\u8BF7\u4F7F\u7528 @InjectRepository \u6216 setEntity");
|
|
1496
|
-
}
|
|
1497
|
-
return this.entity;
|
|
1498
|
-
}
|
|
1499
|
-
async modifyBefore(_data, _type) {}
|
|
1500
|
-
async modifyAfter(_data, _type) {}
|
|
1501
|
-
async add(data, options) {
|
|
1502
|
-
const mode = resolveUpsert(options?.upsert);
|
|
1503
|
-
const payload = Array.isArray(data) ? data.map((item) => item != null && typeof item === "object" ? { ...item } : item) : data != null && typeof data === "object" ? { ...data } : data;
|
|
1504
|
-
await this.modifyBefore(payload, "add");
|
|
1505
|
-
const result = mode === "save" ? await this.requireEntity().save(payload) : await this.requireEntity().create(payload);
|
|
1506
|
-
await this.modifyAfter(result ?? payload, "add");
|
|
1507
|
-
return result;
|
|
1508
|
-
}
|
|
1509
|
-
async update(whereOrData, data) {
|
|
1510
|
-
if (Array.isArray(whereOrData)) {
|
|
1511
|
-
const payloads = whereOrData.map((item) => ({ ...item }));
|
|
1512
|
-
await this.modifyBefore(payloads, "update");
|
|
1513
|
-
const result2 = await this.requireEntity().update(payloads);
|
|
1514
|
-
await this.modifyAfter(result2 ?? payloads, "update");
|
|
1515
|
-
return result2;
|
|
1516
|
-
}
|
|
1517
|
-
if (isSql(whereOrData)) {
|
|
1518
|
-
const payload = data != null && typeof data === "object" ? { ...data } : data;
|
|
1519
|
-
await this.modifyBefore(payload, "update");
|
|
1520
|
-
const result2 = await this.requireEntity().update(whereOrData, payload);
|
|
1521
|
-
await this.modifyAfter(result2 ?? payload, "update");
|
|
1522
|
-
return result2;
|
|
1523
|
-
}
|
|
1524
|
-
const row = { ...whereOrData };
|
|
1525
|
-
await this.modifyBefore(row, "update");
|
|
1526
|
-
const result = await this.requireEntity().update([row]);
|
|
1527
|
-
await this.modifyAfter(result ?? row, "update");
|
|
1528
|
-
return Array.isArray(result) ? result[0] : result;
|
|
1529
|
-
}
|
|
1530
|
-
async delete(whereOrIds, options) {
|
|
1531
|
-
const entity = this.requireEntity();
|
|
1532
|
-
await this.modifyBefore(whereOrIds, "delete");
|
|
1533
|
-
const soft = resolveSoftDelete(options?.softDelete);
|
|
1534
|
-
if (options?.force || !soft || !entity.supportsSoftDelete()) {
|
|
1535
|
-
await entity.forceDelete(whereOrIds);
|
|
1536
|
-
} else {
|
|
1537
|
-
await entity.softDelete(whereOrIds);
|
|
1538
|
-
}
|
|
1539
|
-
await this.modifyAfter(whereOrIds, "delete");
|
|
1540
|
-
}
|
|
1541
|
-
restore(whereOrIds) {
|
|
1542
|
-
return this.requireEntity().restore(whereOrIds);
|
|
1543
|
-
}
|
|
1544
|
-
list(where, options) {
|
|
1545
|
-
return this.requireEntity().find(where, options);
|
|
1546
|
-
}
|
|
1547
|
-
info(idOrWhere, options) {
|
|
1548
|
-
const entity = this.requireEntity();
|
|
1549
|
-
if (typeof idOrWhere === "object")
|
|
1550
|
-
return entity.findOne(idOrWhere, options);
|
|
1551
|
-
return entity.findById(idOrWhere, options);
|
|
1552
|
-
}
|
|
1553
|
-
page(query = {}) {
|
|
1554
|
-
const page = Math.max(1, query.page ?? 1);
|
|
1555
|
-
const size = Math.min(100, Math.max(1, query.size ?? 20));
|
|
1556
|
-
return this.requireEntity().findPage({
|
|
1557
|
-
page,
|
|
1558
|
-
size,
|
|
1559
|
-
where: query.where,
|
|
1560
|
-
orderBy: query.orderBy,
|
|
1561
|
-
withTrashed: query.withTrashed,
|
|
1562
|
-
onlyTrashed: query.onlyTrashed,
|
|
1563
|
-
softDelete: query.softDelete
|
|
1564
|
-
});
|
|
1565
|
-
}
|
|
1566
|
-
}
|
|
1567
|
-
|
|
1568
|
-
// src/routing/crud-summary.ts
|
|
1569
|
-
var CRUD_SUMMARY = {
|
|
1570
|
-
add: "\u65B0\u589E",
|
|
1571
|
-
delete: "\u5220\u9664",
|
|
1572
|
-
update: "\u4FEE\u6539",
|
|
1573
|
-
info: "\u5355\u4E2A\u4FE1\u606F",
|
|
1574
|
-
list: "\u5217\u8868\u67E5\u8BE2",
|
|
1575
|
-
page: "\u5206\u9875\u67E5\u8BE2",
|
|
1576
|
-
restore: "\u6062\u590D"
|
|
1577
|
-
};
|
|
1578
|
-
|
|
1579
|
-
// src/orm/crud-register.ts
|
|
1580
|
-
var CRUD_APIS = [
|
|
1581
|
-
"add",
|
|
1582
|
-
"delete",
|
|
1583
|
-
"update",
|
|
1584
|
-
"info",
|
|
1585
|
-
"list",
|
|
1586
|
-
"page",
|
|
1587
|
-
"restore"
|
|
1588
|
-
];
|
|
1589
|
-
var BEFORE_APIS = new Set(["add", "update", "delete", "restore"]);
|
|
1590
|
-
function omitProps(row, keys) {
|
|
1591
|
-
if (!row || !keys?.length)
|
|
1592
|
-
return row;
|
|
1593
|
-
const next = { ...row };
|
|
1594
|
-
for (const key of keys)
|
|
1595
|
-
delete next[key];
|
|
1596
|
-
return next;
|
|
1597
|
-
}
|
|
1598
|
-
function resolveIds(body) {
|
|
1599
|
-
if (Array.isArray(body)) {
|
|
1600
|
-
return body.map((item) => {
|
|
1601
|
-
if (item != null && typeof item === "object" && "id" in item) {
|
|
1602
|
-
return item.id;
|
|
1603
|
-
}
|
|
1604
|
-
return item;
|
|
1605
|
-
});
|
|
1606
|
-
}
|
|
1607
|
-
if (body && typeof body === "object") {
|
|
1608
|
-
const o = body;
|
|
1609
|
-
if (Array.isArray(o.ids))
|
|
1610
|
-
return o.ids;
|
|
1611
|
-
if (o.id != null)
|
|
1612
|
-
return [o.id];
|
|
1613
|
-
}
|
|
1614
|
-
return [];
|
|
1615
|
-
}
|
|
1616
|
-
function resolveService(meta) {
|
|
1617
|
-
const crud = meta.crud;
|
|
1618
|
-
const table = crud.entity;
|
|
1619
|
-
if (crud.service) {
|
|
1620
|
-
const svc2 = Ioc.get(crud.service);
|
|
1621
|
-
if (table && !svc2.hasEntity())
|
|
1622
|
-
svc2.setEntity(getRepository(table));
|
|
1623
|
-
return svc2;
|
|
1624
|
-
}
|
|
1625
|
-
if (!table) {
|
|
1626
|
-
throw new Error(`[CRUD] ${meta.token.name} \u9700\u914D\u7F6E entity \u6216 service`);
|
|
1627
|
-
}
|
|
1628
|
-
const svc = new class extends BaseService {
|
|
1629
|
-
};
|
|
1630
|
-
svc.setEntity(getRepository(table));
|
|
1631
|
-
return svc;
|
|
1632
|
-
}
|
|
1633
|
-
function tableOf(svc, meta) {
|
|
1634
|
-
const fromCrud = meta.crud?.entity;
|
|
1635
|
-
if (fromCrud)
|
|
1636
|
-
return fromCrud;
|
|
1637
|
-
return svc.getRepo().table;
|
|
1638
|
-
}
|
|
1639
|
-
var attachCrudRoutes = (plugin, meta, ctx) => {
|
|
1640
|
-
const crud = meta.crud;
|
|
1641
|
-
if (!crud)
|
|
1642
|
-
return plugin;
|
|
1643
|
-
const apis = (crud.api ?? []).filter((a) => CRUD_APIS.includes(a));
|
|
1644
|
-
const serviceApis = crud.serviceApis ?? [];
|
|
1645
|
-
if (!apis.length && !serviceApis.length)
|
|
1646
|
-
return plugin;
|
|
1647
|
-
const responder = ctx.controller instanceof BaseController ? ctx.controller : new BaseController;
|
|
1648
|
-
const needsEntity = apis.length > 0;
|
|
1649
|
-
const svc = needsEntity || crud.service ? resolveService(meta) : undefined;
|
|
1650
|
-
const table = needsEntity && svc ? tableOf(svc, meta) : undefined;
|
|
1651
|
-
const idCol = table ? table.id : undefined;
|
|
1652
|
-
if (needsEntity && idCol == null) {
|
|
1653
|
-
throw new Error(`[CRUD] ${meta.token.name} \u8868\u65E0 id \u5217`);
|
|
1654
|
-
}
|
|
1655
|
-
let next = plugin;
|
|
1656
|
-
const mount = (method, path, action, handler) => {
|
|
1657
|
-
next = next[method](path, handler, ctx.routeOptions({ action, summary: CRUD_SUMMARY[action] }));
|
|
1658
|
-
};
|
|
1659
|
-
const runBefore = async (api, body, request) => {
|
|
1660
|
-
if (!crud.before || !BEFORE_APIS.has(api))
|
|
1661
|
-
return body;
|
|
1662
|
-
await crud.before({ body, request, api });
|
|
1663
|
-
return body;
|
|
1664
|
-
};
|
|
1665
|
-
if (apis.includes("add") && svc) {
|
|
1666
|
-
mount("post", "/add", "add", async ({ body, request }) => {
|
|
1667
|
-
try {
|
|
1668
|
-
const raw = body;
|
|
1669
|
-
if (Array.isArray(raw)) {
|
|
1670
|
-
let list = raw;
|
|
1671
|
-
if (crud.before && BEFORE_APIS.has("add")) {
|
|
1672
|
-
for (let i = 0;i < list.length; i++) {
|
|
1673
|
-
list[i] = await runBefore("add", { ...list[i] ?? {} }, request);
|
|
1674
|
-
}
|
|
1675
|
-
}
|
|
1676
|
-
if (crud.insertParam) {
|
|
1677
|
-
const extra = await crud.insertParam({ body: list[0] ?? {}, request });
|
|
1678
|
-
list = list.map((row2) => ({ ...row2, ...extra }));
|
|
1679
|
-
}
|
|
1680
|
-
const rows = await svc.add(list);
|
|
1681
|
-
return responder.ok(rows);
|
|
1682
|
-
}
|
|
1683
|
-
let data = { ...raw ?? {} };
|
|
1684
|
-
data = await runBefore("add", data, request);
|
|
1685
|
-
if (crud.insertParam) {
|
|
1686
|
-
Object.assign(data, await crud.insertParam({ body: data, request }));
|
|
1687
|
-
}
|
|
1688
|
-
const row = await svc.add(data);
|
|
1689
|
-
return responder.ok(row);
|
|
1690
|
-
} catch (e) {
|
|
1691
|
-
return responder.fail(e instanceof Error ? e.message : "add failed");
|
|
1692
|
-
}
|
|
1693
|
-
});
|
|
1694
|
-
}
|
|
1695
|
-
if (apis.includes("delete") && svc && idCol) {
|
|
1696
|
-
mount("post", "/delete", "delete", async ({ body, request }) => {
|
|
1697
|
-
try {
|
|
1698
|
-
const raw = body;
|
|
1699
|
-
const data = Array.isArray(raw) ? raw : await runBefore("delete", { ...raw ?? {} }, request);
|
|
1700
|
-
const ids = resolveIds(data);
|
|
1701
|
-
if (!ids.length)
|
|
1702
|
-
return responder.fail("ids required");
|
|
1703
|
-
const force = !Array.isArray(data) && !!data.force;
|
|
1704
|
-
await svc.delete(ids, { force });
|
|
1705
|
-
return responder.ok();
|
|
1706
|
-
} catch (e) {
|
|
1707
|
-
return responder.fail(e instanceof Error ? e.message : "delete failed");
|
|
1708
|
-
}
|
|
1709
|
-
});
|
|
1710
|
-
}
|
|
1711
|
-
if (apis.includes("update") && svc && idCol) {
|
|
1712
|
-
mount("post", "/update", "update", async ({ body, request }) => {
|
|
1713
|
-
try {
|
|
1714
|
-
const raw = body;
|
|
1715
|
-
if (Array.isArray(raw)) {
|
|
1716
|
-
let list = raw;
|
|
1717
|
-
if (crud.before && BEFORE_APIS.has("update")) {
|
|
1718
|
-
for (let i = 0;i < list.length; i++) {
|
|
1719
|
-
list[i] = await runBefore("update", { ...list[i] ?? {} }, request);
|
|
1720
|
-
}
|
|
1721
|
-
}
|
|
1722
|
-
const rows = await svc.update(list);
|
|
1723
|
-
return responder.ok(rows);
|
|
1724
|
-
}
|
|
1725
|
-
const data = await runBefore("update", { ...raw ?? {} }, request);
|
|
1726
|
-
const id = data.id;
|
|
1727
|
-
if (id == null)
|
|
1728
|
-
return responder.fail("id required");
|
|
1729
|
-
const row = await svc.update(data);
|
|
1730
|
-
return responder.ok(row);
|
|
1731
|
-
} catch (e) {
|
|
1732
|
-
return responder.fail(e instanceof Error ? e.message : "update failed");
|
|
1733
|
-
}
|
|
1734
|
-
});
|
|
1735
|
-
}
|
|
1736
|
-
if (apis.includes("info") && svc) {
|
|
1737
|
-
mount("get", "/info", "info", async ({ query }) => {
|
|
1738
|
-
try {
|
|
1739
|
-
const id = query?.id;
|
|
1740
|
-
if (id == null || id === "")
|
|
1741
|
-
return responder.fail("id required");
|
|
1742
|
-
const row = await svc.info(id);
|
|
1743
|
-
return responder.ok(omitProps(row, crud.infoIgnoreProperty));
|
|
1744
|
-
} catch (e) {
|
|
1745
|
-
return responder.fail(e instanceof Error ? e.message : "info failed");
|
|
1746
|
-
}
|
|
1747
|
-
});
|
|
1748
|
-
}
|
|
1749
|
-
if (apis.includes("list") && svc && table) {
|
|
1750
|
-
mount("post", "/list", "list", async ({ body, request }) => {
|
|
1751
|
-
try {
|
|
1752
|
-
const payload = body ?? {};
|
|
1753
|
-
const op = crud.listQueryOp ?? {};
|
|
1754
|
-
const trash = {
|
|
1755
|
-
onlyTrashed: payload.onlyTrashed === true,
|
|
1756
|
-
withTrashed: payload.withTrashed === true
|
|
1757
|
-
};
|
|
1758
|
-
if (needsAdvancedQuery(op)) {
|
|
1759
|
-
const list2 = await queryWithOp(table, payload, op, {
|
|
1760
|
-
request,
|
|
1761
|
-
mode: "list",
|
|
1762
|
-
trash
|
|
1763
|
-
});
|
|
1764
|
-
return responder.ok(list2);
|
|
1765
|
-
}
|
|
1766
|
-
const { where, orderBySql } = await buildQueryOp(table, payload, op, request);
|
|
1767
|
-
const list = await svc.list(where, { orderBy: orderBySql, ...trash });
|
|
1768
|
-
return responder.ok(list);
|
|
1769
|
-
} catch (e) {
|
|
1770
|
-
return responder.fail(e instanceof Error ? e.message : "list failed");
|
|
1771
|
-
}
|
|
1772
|
-
});
|
|
1773
|
-
}
|
|
1774
|
-
if (apis.includes("page") && svc && table) {
|
|
1775
|
-
mount("post", "/page", "page", async ({ body, request }) => {
|
|
1776
|
-
try {
|
|
1777
|
-
const payload = body ?? {};
|
|
1778
|
-
const op = crud.pageQueryOp ?? {};
|
|
1779
|
-
const trash = {
|
|
1780
|
-
onlyTrashed: payload.onlyTrashed === true,
|
|
1781
|
-
withTrashed: payload.withTrashed === true
|
|
1782
|
-
};
|
|
1783
|
-
if (needsAdvancedQuery(op)) {
|
|
1784
|
-
const result2 = await queryWithOp(table, payload, op, {
|
|
1785
|
-
request,
|
|
1786
|
-
mode: "page",
|
|
1787
|
-
trash
|
|
1788
|
-
});
|
|
1789
|
-
return responder.ok(result2);
|
|
1790
|
-
}
|
|
1791
|
-
const { where, orderBySql } = await buildQueryOp(table, payload, op, request);
|
|
1792
|
-
const result = await svc.page({
|
|
1793
|
-
page: Number(payload.page ?? 1),
|
|
1794
|
-
size: Number(payload.size ?? 20),
|
|
1795
|
-
where,
|
|
1796
|
-
orderBy: orderBySql,
|
|
1797
|
-
...trash
|
|
1798
|
-
});
|
|
1799
|
-
return responder.ok(result);
|
|
1800
|
-
} catch (e) {
|
|
1801
|
-
return responder.fail(e instanceof Error ? e.message : "page failed");
|
|
1802
|
-
}
|
|
1803
|
-
});
|
|
1804
|
-
}
|
|
1805
|
-
if (apis.includes("restore") && svc && idCol) {
|
|
1806
|
-
mount("post", "/restore", "restore", async ({ body, request }) => {
|
|
1807
|
-
try {
|
|
1808
|
-
const raw = body;
|
|
1809
|
-
const data = Array.isArray(raw) ? raw : await runBefore("restore", { ...raw ?? {} }, request);
|
|
1810
|
-
const ids = resolveIds(data);
|
|
1811
|
-
if (!ids.length)
|
|
1812
|
-
return responder.fail("ids required");
|
|
1813
|
-
await svc.restore(ids);
|
|
1814
|
-
return responder.ok();
|
|
1815
|
-
} catch (e) {
|
|
1816
|
-
return responder.fail(e instanceof Error ? e.message : "restore failed");
|
|
1817
|
-
}
|
|
1818
|
-
});
|
|
1819
|
-
}
|
|
1820
|
-
if (serviceApis.length) {
|
|
1821
|
-
if (!crud.service) {
|
|
1822
|
-
throw new Error(`[CRUD] ${meta.token.name} \u914D\u7F6E\u4E86 serviceApis\uFF0C\u9700\u540C\u65F6\u914D\u7F6E service`);
|
|
1823
|
-
}
|
|
1824
|
-
const biz = Ioc.get(crud.service);
|
|
1825
|
-
for (const name of serviceApis) {
|
|
1826
|
-
const method = biz[name];
|
|
1827
|
-
if (typeof method !== "function") {
|
|
1828
|
-
throw new Error(`[CRUD] ${crud.service.name}.${name} \u4E0D\u662F\u6709\u6548\u65B9\u6CD5`);
|
|
1829
|
-
}
|
|
1830
|
-
const bound = method.bind(biz);
|
|
1831
|
-
mount("post", `/${name}`, name, async ({ body }) => {
|
|
1832
|
-
try {
|
|
1833
|
-
const result = await bound(body);
|
|
1834
|
-
return responder.ok(result);
|
|
1835
|
-
} catch (e) {
|
|
1836
|
-
return responder.fail(e instanceof Error ? e.message : `${name} failed`);
|
|
1837
|
-
}
|
|
1838
|
-
});
|
|
1839
|
-
}
|
|
1840
|
-
}
|
|
1841
|
-
return next;
|
|
1842
|
-
};
|
|
1843
|
-
|
|
1844
|
-
// src/ioc/host.ts
|
|
1845
|
-
import { join as join2 } from "path";
|
|
1846
|
-
import { pathToFileURL as pathToFileURL2 } from "url";
|
|
1847
|
-
var SERVICE_PATTERN = "**/modules/*/service/**/*.ts";
|
|
1848
|
-
var CONTROLLER_SCANS = [
|
|
1849
|
-
{ pattern: "**/modules/*/controller/admin/**/*.ts", side: "admin" },
|
|
1850
|
-
{ pattern: "**/modules/*/controller/app/**/*.ts", side: "app" }
|
|
1851
|
-
];
|
|
1852
|
-
async function importWithContext(cwd, file, side) {
|
|
1853
|
-
setControllerScanContext({
|
|
1854
|
-
module: parseModuleFromPath(file),
|
|
1855
|
-
side,
|
|
1856
|
-
file
|
|
1857
|
-
});
|
|
1858
|
-
try {
|
|
1859
|
-
const href = pathToFileURL2(join2(cwd, file)).href;
|
|
1860
|
-
await import(href);
|
|
1861
|
-
} finally {
|
|
1862
|
-
setControllerScanContext(null);
|
|
1863
|
-
}
|
|
1864
|
-
}
|
|
1865
|
-
async function scanHost() {
|
|
1866
|
-
const cwd = process.cwd();
|
|
1867
|
-
const serviceFiles = await scanFiles(SERVICE_PATTERN, { cwd });
|
|
1868
|
-
for (const file of serviceFiles) {
|
|
1869
|
-
const href = pathToFileURL2(join2(cwd, file)).href;
|
|
1870
|
-
await import(href);
|
|
1871
|
-
}
|
|
1872
|
-
let controllerCount = 0;
|
|
1873
|
-
for (const { pattern, side } of CONTROLLER_SCANS) {
|
|
1874
|
-
const files = await scanFiles(pattern, { cwd });
|
|
1875
|
-
controllerCount += files.length;
|
|
1876
|
-
for (const file of files) {
|
|
1877
|
-
await importWithContext(cwd, file, side);
|
|
1878
|
-
}
|
|
1879
|
-
}
|
|
1880
|
-
setCrudRegistrar(attachCrudRoutes);
|
|
1881
|
-
console.log(`[Host] crud \u2190 @vome-core/orm`);
|
|
1882
|
-
console.log(`[Host] scan \u2190 ${serviceFiles.length} service, ${controllerCount} controller file(s)`);
|
|
1883
|
-
}
|
|
1884
|
-
|
|
1885
|
-
// src/logger/pino.ts
|
|
1886
|
-
import { join as join4 } from "path";
|
|
1887
|
-
import { createPinoLogger } from "@bogeychan/elysia-logger";
|
|
1888
|
-
import pinoPretty from "pino-pretty";
|
|
1889
|
-
|
|
1890
|
-
// src/comm/daily-log.ts
|
|
1891
|
-
import {
|
|
1892
|
-
createWriteStream,
|
|
1893
|
-
mkdirSync,
|
|
1894
|
-
readdirSync,
|
|
1895
|
-
unlinkSync
|
|
1896
|
-
} from "fs";
|
|
1897
|
-
import { join as join3 } from "path";
|
|
1898
|
-
import { Writable } from "stream";
|
|
1899
|
-
var FILE_PATTERN = /^(\d{4}-\d{2}-\d{2})\.log$/;
|
|
1900
|
-
function formatLocalDate(date = new Date) {
|
|
1901
|
-
const y = date.getFullYear();
|
|
1902
|
-
const m = String(date.getMonth() + 1).padStart(2, "0");
|
|
1903
|
-
const d = String(date.getDate()).padStart(2, "0");
|
|
1904
|
-
return `${y}-${m}-${d}`;
|
|
1905
|
-
}
|
|
1906
|
-
function purgeOldLogs(dir, maxDays) {
|
|
1907
|
-
const cutoff = new Date;
|
|
1908
|
-
cutoff.setDate(cutoff.getDate() - maxDays);
|
|
1909
|
-
const cutoffStr = formatLocalDate(cutoff);
|
|
1910
|
-
for (const name of readdirSync(dir)) {
|
|
1911
|
-
const matched = name.match(FILE_PATTERN);
|
|
1912
|
-
if (!matched || matched[1] >= cutoffStr)
|
|
1913
|
-
continue;
|
|
1914
|
-
unlinkSync(join3(dir, name));
|
|
1915
|
-
}
|
|
1916
|
-
}
|
|
1917
|
-
function openDailyStream(dir, date) {
|
|
1918
|
-
return createWriteStream(join3(dir, `${date}.log`), { flags: "a" });
|
|
1919
|
-
}
|
|
1920
|
-
function createDailyLogStream(dir, maxDays = 30) {
|
|
1921
|
-
mkdirSync(dir, { recursive: true });
|
|
1922
|
-
purgeOldLogs(dir, maxDays);
|
|
1923
|
-
let currentDate = formatLocalDate();
|
|
1924
|
-
let fileStream = openDailyStream(dir, currentDate);
|
|
1925
|
-
return new Writable({
|
|
1926
|
-
write(chunk, _encoding, callback) {
|
|
1927
|
-
const today = formatLocalDate();
|
|
1928
|
-
if (today !== currentDate) {
|
|
1929
|
-
fileStream.end();
|
|
1930
|
-
currentDate = today;
|
|
1931
|
-
fileStream = openDailyStream(dir, currentDate);
|
|
1932
|
-
purgeOldLogs(dir, maxDays);
|
|
1933
|
-
}
|
|
1934
|
-
fileStream.write(chunk, callback);
|
|
1935
|
-
},
|
|
1936
|
-
final(callback) {
|
|
1937
|
-
fileStream.end(callback);
|
|
1938
|
-
}
|
|
1939
|
-
});
|
|
1940
|
-
}
|
|
1941
|
-
|
|
1942
|
-
// src/logger/pino.ts
|
|
1943
|
-
var pinoInstance;
|
|
1944
|
-
function buildPino() {
|
|
1945
|
-
const logging = VomeConfig.logging ?? {};
|
|
1946
|
-
const level = logging.level ?? "info";
|
|
1947
|
-
if (logging.transport === "file") {
|
|
1948
|
-
const dir = join4(process.cwd(), logging.dir ?? "logging");
|
|
1949
|
-
const maxDays = logging.maxDays ?? 30;
|
|
1950
|
-
return createPinoLogger({
|
|
1951
|
-
level,
|
|
1952
|
-
stream: createDailyLogStream(dir, maxDays)
|
|
1953
|
-
});
|
|
1954
|
-
}
|
|
1955
|
-
return createPinoLogger({
|
|
1956
|
-
level,
|
|
1957
|
-
stream: pinoPretty({
|
|
1958
|
-
colorize: true,
|
|
1959
|
-
translateTime: "SYS:standard",
|
|
1960
|
-
ignore: "pid,hostname"
|
|
1961
|
-
})
|
|
1962
|
-
});
|
|
1963
|
-
}
|
|
1964
|
-
function getPinoLogger() {
|
|
1965
|
-
if (!pinoInstance)
|
|
1966
|
-
pinoInstance = buildPino();
|
|
1967
|
-
return pinoInstance;
|
|
1968
|
-
}
|
|
1969
|
-
function resetPinoLogger() {
|
|
1970
|
-
pinoInstance = undefined;
|
|
1971
|
-
}
|
|
1972
|
-
|
|
1973
|
-
// src/logger/logger.ts
|
|
1974
|
-
class Logger {
|
|
1975
|
-
info(msg, ...args) {
|
|
1976
|
-
const log = getPinoLogger();
|
|
1977
|
-
if (args.length)
|
|
1978
|
-
log.info({ args }, msg);
|
|
1979
|
-
else
|
|
1980
|
-
log.info(msg);
|
|
1981
|
-
}
|
|
1982
|
-
warn(msg, ...args) {
|
|
1983
|
-
const log = getPinoLogger();
|
|
1984
|
-
if (args.length)
|
|
1985
|
-
log.warn({ args }, msg);
|
|
1986
|
-
else
|
|
1987
|
-
log.warn(msg);
|
|
1988
|
-
}
|
|
1989
|
-
debug(msg, ...args) {
|
|
1990
|
-
const log = getPinoLogger();
|
|
1991
|
-
if (args.length)
|
|
1992
|
-
log.debug({ args }, msg);
|
|
1993
|
-
else
|
|
1994
|
-
log.debug(msg);
|
|
1995
|
-
}
|
|
1996
|
-
error(msg, ...args) {
|
|
1997
|
-
const log = getPinoLogger();
|
|
1998
|
-
if (msg instanceof Error) {
|
|
1999
|
-
log.error(msg);
|
|
2000
|
-
return;
|
|
2001
|
-
}
|
|
2002
|
-
if (args[0] instanceof Error) {
|
|
2003
|
-
log.error(args[0], msg);
|
|
2004
|
-
return;
|
|
2005
|
-
}
|
|
2006
|
-
if (args.length)
|
|
2007
|
-
log.error({ args }, msg);
|
|
2008
|
-
else
|
|
2009
|
-
log.error(msg);
|
|
2010
|
-
}
|
|
2011
|
-
}
|
|
2012
|
-
// src/logger/exception.ts
|
|
2013
|
-
class CommException extends Error {
|
|
2014
|
-
statusCode;
|
|
2015
|
-
code;
|
|
2016
|
-
constructor(message, options) {
|
|
2017
|
-
super(message);
|
|
2018
|
-
this.name = "CommException";
|
|
2019
|
-
this.statusCode = options?.statusCode ?? 200;
|
|
2020
|
-
this.code = options?.code ?? RES_CODE.ERROR;
|
|
2021
|
-
}
|
|
2022
|
-
}
|
|
2023
|
-
function isCommException(error) {
|
|
2024
|
-
return error instanceof CommException;
|
|
2025
|
-
}
|
|
2026
|
-
// src/logger/bootstrap.ts
|
|
2027
|
-
function bootstrapLogger() {
|
|
2028
|
-
getPinoLogger();
|
|
2029
|
-
Ioc.set(Logger, new Logger);
|
|
2030
|
-
}
|
|
2031
|
-
// src/comm/startBanner.ts
|
|
2032
|
-
var VOME_BANNER = `
|
|
2033
|
-
\u2588\u2588\u2557 \u2588\u2588\u2557 \u2588\u2588\u2588\u2588\u2588\u2588\u2557 \u2588\u2588\u2588\u2557 \u2588\u2588\u2588\u2557 \u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2557
|
|
2034
|
-
\u2588\u2588\u2551 \u2588\u2588\u2551 \u2588\u2588\u2554\u2550\u2550\u2550\u2588\u2588\u2557 \u2588\u2588\u2588\u2588\u2557 \u2588\u2588\u2588\u2588\u2551 \u2588\u2588\u2554\u2550\u2550\u2550\u2550\u255D
|
|
2035
|
-
\u2588\u2588\u2551 \u2588\u2588\u2551 \u2588\u2588\u2551 \u2588\u2588\u2551 \u2588\u2588\u2554\u2588\u2588\u2588\u2588\u2554\u2588\u2588\u2551 \u2588\u2588\u2588\u2588\u2588\u2557
|
|
2036
|
-
\u2588\u2588\u2557 \u2588\u2588\u2554\u255D \u2588\u2588\u2551 \u2588\u2588\u2551 \u2588\u2588\u2551\u255A\u2588\u2588\u2554\u255D\u2588\u2588\u2551 \u2588\u2588\u2554\u2550\u2550\u255D
|
|
2037
|
-
\u255A\u2588\u2588\u2588\u2554\u255D \u255A\u2588\u2588\u2588\u2588\u2588\u2588\u2554\u255D \u2588\u2588\u2551 \u255A\u2550\u255D \u2588\u2588\u2551 \u2588\u2588\u2588\u2588\u2588\u2588\u2588\u2557
|
|
2038
|
-
\u255A\u2550\u2550\u255D \u255A\u2550\u2550\u2550\u2550\u2550\u255D \u255A\u2550\u255D \u255A\u2550\u255D \u255A\u2550\u2550\u2550\u2550\u2550\u2550\u255D
|
|
2039
|
-
`;
|
|
2040
|
-
function resetViewport() {
|
|
2041
|
-
if (!process.stdout.isTTY)
|
|
2042
|
-
return;
|
|
2043
|
-
process.stdout.write("\x1B[2J\x1B[H");
|
|
2044
|
-
}
|
|
2045
|
-
function printStartupBanner() {
|
|
2046
|
-
resetViewport();
|
|
2047
|
-
const env = getEnv();
|
|
2048
|
-
const port = VomeConfig.system?.port ?? 3001;
|
|
2049
|
-
const docsPath = VomeConfig.openapi?.path ?? "/docs";
|
|
2050
|
-
const baseUrl = `http://localhost:${port}`;
|
|
2051
|
-
console.log(VOME_BANNER);
|
|
2052
|
-
console.log(`\uD83C\uDF0D \u8FD0\u884C\u73AF\u5883: ${env}`);
|
|
2053
|
-
if (env === "dev") {
|
|
2054
|
-
console.log(`\uD83D\uDCE1 \u670D\u52A1\u5730\u5740: ${baseUrl}`);
|
|
2055
|
-
console.log(`\uD83D\uDCDA API\u6587\u6863: ${baseUrl}${docsPath.startsWith("/") ? docsPath : `/${docsPath}`}`);
|
|
2056
|
-
}
|
|
2057
|
-
}
|
|
2058
|
-
|
|
2059
|
-
// src/core/host-infra.ts
|
|
2060
|
-
import { access } from "fs/promises";
|
|
2061
|
-
import { join as join5 } from "path";
|
|
2062
|
-
import { pathToFileURL as pathToFileURL3 } from "url";
|
|
2063
|
-
async function exists(abs) {
|
|
2064
|
-
try {
|
|
2065
|
-
await access(abs);
|
|
2066
|
-
return true;
|
|
2067
|
-
} catch {
|
|
2068
|
-
return false;
|
|
2069
|
-
}
|
|
2070
|
-
}
|
|
2071
|
-
async function importHostModule(relPath) {
|
|
2072
|
-
const abs = join5(process.cwd(), relPath);
|
|
2073
|
-
if (!await exists(abs)) {
|
|
2074
|
-
console.warn(`[Host] skip \u2190 missing ${relPath}`);
|
|
2075
|
-
return;
|
|
2076
|
-
}
|
|
2077
|
-
return await import(pathToFileURL3(abs).href);
|
|
2078
|
-
}
|
|
2079
|
-
async function bootstrapHostInfra() {
|
|
2080
|
-
const dbMod = await importHostModule("src/lib/db/index.ts");
|
|
2081
|
-
if (dbMod?.Db?.bootstrap)
|
|
2082
|
-
await dbMod.Db.bootstrap();
|
|
2083
|
-
const cacheMod = await importHostModule("src/lib/cache/index.ts");
|
|
2084
|
-
if (cacheMod?.Cache?.bootstrap)
|
|
2085
|
-
await cacheMod.Cache.bootstrap();
|
|
2086
|
-
const authMod = await importHostModule("src/lib/auth/index.ts");
|
|
2087
|
-
if (authMod?.Auth?.bootstrap)
|
|
2088
|
-
await authMod.Auth.bootstrap();
|
|
2089
|
-
}
|
|
2090
|
-
async function bootstrapHostTasks() {
|
|
2091
|
-
const mod = await importHostModule("src/lib/task/index.ts");
|
|
2092
|
-
if (mod?.Task?.bootstrap)
|
|
2093
|
-
await mod.Task.bootstrap();
|
|
2094
|
-
}
|
|
2095
|
-
async function bootstrapHostPlugins() {
|
|
2096
|
-
const mod = await importHostModule("src/lib/plugin/index.ts");
|
|
2097
|
-
if (mod?.Plugin?.bootstrap)
|
|
2098
|
-
await mod.Plugin.bootstrap();
|
|
2099
|
-
}
|
|
2100
|
-
async function bootstrapHostModules() {
|
|
2101
|
-
const mod = await importHostModule("src/lib/module/index.ts");
|
|
2102
|
-
if (mod?.Module?.bootstrap)
|
|
2103
|
-
await mod.Module.bootstrap();
|
|
2104
|
-
}
|
|
2105
|
-
async function shutdownHostTasks() {
|
|
2106
|
-
const mod = await importHostModule("src/lib/task/index.ts");
|
|
2107
|
-
if (mod?.Task?.close)
|
|
2108
|
-
await mod.Task.close();
|
|
2109
|
-
}
|
|
2110
|
-
async function shutdownHostInfra() {
|
|
2111
|
-
const cacheMod = await importHostModule("src/lib/cache/index.ts");
|
|
2112
|
-
if (cacheMod?.Cache?.close)
|
|
2113
|
-
await cacheMod.Cache.close();
|
|
2114
|
-
const dbMod = await importHostModule("src/lib/db/index.ts");
|
|
2115
|
-
if (dbMod?.Db?.close)
|
|
2116
|
-
await dbMod.Db.close();
|
|
2117
|
-
}
|
|
2118
|
-
async function applyHostAuthMiddleware(app) {
|
|
2119
|
-
const mod = await importHostModule("src/middleware/index.ts");
|
|
2120
|
-
if (!mod)
|
|
2121
|
-
return app;
|
|
2122
|
-
let next = app;
|
|
2123
|
-
if (mod.webAuth)
|
|
2124
|
-
next = next.use(mod.webAuth);
|
|
2125
|
-
if (mod.adminAuth)
|
|
2126
|
-
next = next.use(mod.adminAuth);
|
|
2127
|
-
if (mod.requestLog)
|
|
2128
|
-
next = next.use(mod.requestLog);
|
|
2129
|
-
if (mod.microApps)
|
|
2130
|
-
next = next.use(mod.microApps);
|
|
2131
|
-
if (mod.moduleGateway)
|
|
2132
|
-
next = next.use(mod.moduleGateway);
|
|
2133
|
-
return next;
|
|
2134
|
-
}
|
|
2135
|
-
|
|
2136
|
-
// src/core/plugins/async-context.ts
|
|
2137
|
-
function applyAsyncContext(app) {
|
|
2138
|
-
const cfg = VomeConfig.asyncContextManager ?? {};
|
|
2139
|
-
if (!cfg.enable)
|
|
2140
|
-
return app;
|
|
2141
|
-
return app.onRequest(({ request }) => {
|
|
2142
|
-
enterContextWith(initContextFromRequest(request));
|
|
2143
|
-
});
|
|
2144
|
-
}
|
|
2145
|
-
|
|
2146
|
-
// src/core/plugins/error.ts
|
|
2147
|
-
function applyErrorHandler(app) {
|
|
2148
|
-
return app.onError(({ error, set: set2, code }) => {
|
|
2149
|
-
const log = getPinoLogger();
|
|
2150
|
-
if (isCommException(error)) {
|
|
2151
|
-
log.error({ code: error.code }, error.message);
|
|
2152
|
-
set2.status = error.statusCode;
|
|
2153
|
-
return { code: error.code, message: error.message };
|
|
2154
|
-
}
|
|
2155
|
-
if (code === "VALIDATION") {
|
|
2156
|
-
const message = error instanceof Error ? error.message : "validation failed";
|
|
2157
|
-
log.error({ code }, message);
|
|
2158
|
-
set2.status = 422;
|
|
2159
|
-
return { code: RES_CODE.ERROR, message };
|
|
2160
|
-
}
|
|
2161
|
-
if (code === "NOT_FOUND") {
|
|
2162
|
-
set2.status = 404;
|
|
2163
|
-
return { code: RES_CODE.ERROR, message: "not found" };
|
|
2164
|
-
}
|
|
2165
|
-
const err = error instanceof Error ? error : new Error(String(error));
|
|
2166
|
-
log.error(err);
|
|
2167
|
-
set2.status = 500;
|
|
2168
|
-
return {
|
|
2169
|
-
code: RES_CODE.ERROR,
|
|
2170
|
-
message: getEnv() === "dev" ? err.message : "internal server error"
|
|
2171
|
-
};
|
|
2172
|
-
});
|
|
2173
|
-
}
|
|
2174
|
-
|
|
2175
|
-
// src/core/plugins/logging.ts
|
|
2176
|
-
function applyLogging(app) {
|
|
2177
|
-
const log = getPinoLogger();
|
|
2178
|
-
return app.use(log.into({
|
|
2179
|
-
autoLogging: {
|
|
2180
|
-
ignore: (ctx) => Boolean(ctx.isError)
|
|
2181
|
-
}
|
|
2182
|
-
}));
|
|
2183
|
-
}
|
|
2184
|
-
|
|
2185
|
-
// src/core/plugins/openapi.ts
|
|
2186
|
-
import { openapi } from "@elysiajs/openapi";
|
|
2187
|
-
function applyOpenapi(app) {
|
|
2188
|
-
const config = VomeConfig.openapi ?? { enable: false };
|
|
2189
|
-
if (config.enable === false)
|
|
2190
|
-
return app;
|
|
2191
|
-
const path = config.path ?? "/docs";
|
|
2192
|
-
const { tags, tagGroups } = buildOpenApiTagDocs();
|
|
2193
|
-
const userDoc = config.documentation ?? {};
|
|
2194
|
-
const userScalar = config.scalar ?? {};
|
|
2195
|
-
return app.use(openapi({
|
|
2196
|
-
path,
|
|
2197
|
-
documentation: {
|
|
2198
|
-
...userDoc,
|
|
2199
|
-
tags: [...userDoc.tags ?? [], ...tags],
|
|
2200
|
-
"x-tagGroups": tagGroups
|
|
2201
|
-
},
|
|
2202
|
-
scalar: {
|
|
2203
|
-
...userScalar,
|
|
2204
|
-
layout: userScalar.layout ?? "classic",
|
|
2205
|
-
operationTitleSource: userScalar.operationTitleSource ?? "summary"
|
|
2206
|
-
}
|
|
2207
|
-
}));
|
|
2208
|
-
}
|
|
2209
|
-
|
|
2210
|
-
// src/core/app.ts
|
|
2211
|
-
var app;
|
|
2212
|
-
var started = false;
|
|
2213
|
-
var signalsRegistered = false;
|
|
2214
|
-
var hostScanned = false;
|
|
2215
|
-
var bootstrapHooks = [];
|
|
2216
|
-
var shutdownHooks = [];
|
|
2217
|
-
var usePlugins = [];
|
|
2218
|
-
async function ensureHostScanned() {
|
|
2219
|
-
if (hostScanned)
|
|
2220
|
-
return;
|
|
2221
|
-
hostScanned = true;
|
|
2222
|
-
await scanHost();
|
|
2223
|
-
}
|
|
2224
|
-
function createApp() {
|
|
2225
|
-
return applyAsyncContext(applyErrorHandler(applyLogging(new Elysia2)));
|
|
2226
|
-
}
|
|
2227
|
-
function bootstrap(hook) {
|
|
2228
|
-
bootstrapHooks.push(hook);
|
|
2229
|
-
}
|
|
2230
|
-
function shutdown(hook) {
|
|
2231
|
-
shutdownHooks.push(hook);
|
|
2232
|
-
}
|
|
2233
|
-
function use(setup) {
|
|
2234
|
-
usePlugins.push(setup);
|
|
2235
|
-
}
|
|
2236
|
-
async function start() {
|
|
2237
|
-
if (started) {
|
|
2238
|
-
throw new Error("[App] \u5DF2\u542F\u52A8\uFF0C\u8BF7\u5148 App.stop() \u518D start");
|
|
2239
|
-
}
|
|
2240
|
-
let next = createApp();
|
|
2241
|
-
next = await applyHostAuthMiddleware(next);
|
|
2242
|
-
for (const setup of usePlugins) {
|
|
2243
|
-
next = setup(next);
|
|
2244
|
-
}
|
|
2245
|
-
await ensureHostScanned();
|
|
2246
|
-
next = applyOpenapi(next);
|
|
2247
|
-
await bootstrapHostInfra();
|
|
2248
|
-
for (const hook of bootstrapHooks)
|
|
2249
|
-
await hook();
|
|
2250
|
-
bootstrapLogger();
|
|
2251
|
-
bootstrapIoc();
|
|
2252
|
-
await bootstrapHostPlugins();
|
|
2253
|
-
await bootstrapHostModules();
|
|
2254
|
-
await bootstrapHostTasks();
|
|
2255
|
-
next = registerControllers(next, VomeConfig);
|
|
2256
|
-
const port = VomeConfig.system?.port ?? 3001;
|
|
2257
|
-
next.listen(port);
|
|
2258
|
-
app = next;
|
|
2259
|
-
started = true;
|
|
2260
|
-
printStartupBanner();
|
|
2261
|
-
registerShutdownSignals();
|
|
2262
|
-
return app;
|
|
2263
|
-
}
|
|
2264
|
-
async function stop() {
|
|
2265
|
-
if (!app)
|
|
2266
|
-
return;
|
|
2267
|
-
for (const hook of shutdownHooks)
|
|
2268
|
-
await hook();
|
|
2269
|
-
await shutdownHostTasks();
|
|
2270
|
-
await shutdownHostInfra();
|
|
2271
|
-
await app.stop();
|
|
2272
|
-
app = undefined;
|
|
2273
|
-
started = false;
|
|
2274
|
-
hostScanned = false;
|
|
2275
|
-
resetIoc();
|
|
2276
|
-
resetPinoLogger();
|
|
2277
|
-
setCrudRegistrar(undefined);
|
|
2278
|
-
signalsRegistered = false;
|
|
2279
|
-
}
|
|
2280
|
-
function registerShutdownSignals() {
|
|
2281
|
-
if (signalsRegistered)
|
|
2282
|
-
return;
|
|
2283
|
-
signalsRegistered = true;
|
|
2284
|
-
for (const signal of ["SIGINT", "SIGTERM"]) {
|
|
2285
|
-
process.once(signal, async () => {
|
|
2286
|
-
await stop();
|
|
2287
|
-
process.exit(0);
|
|
2288
|
-
});
|
|
2289
|
-
}
|
|
2290
|
-
}
|
|
2291
|
-
var App = {
|
|
2292
|
-
bootstrap,
|
|
2293
|
-
shutdown,
|
|
2294
|
-
use,
|
|
2295
|
-
start,
|
|
2296
|
-
stop
|
|
2297
|
-
};
|
|
2298
|
-
async function vome(setup) {
|
|
2299
|
-
if (setup)
|
|
2300
|
-
await setup({ App });
|
|
2301
|
-
return App.start();
|
|
2302
|
-
}
|
|
2303
|
-
// src/routing/eps.ts
|
|
2304
|
-
import { getTableColumns as getTableColumns3, getTableName as getTableName2 } from "drizzle-orm";
|
|
2305
|
-
|
|
2306
|
-
// src/orm/column-comments.ts
|
|
2307
|
-
import { getTableColumns as getTableColumns2, getTableName } from "drizzle-orm";
|
|
2308
|
-
|
|
2309
|
-
// src/orm/base-columns.ts
|
|
2310
|
-
import { integer, serial, timestamp } from "drizzle-orm/pg-core";
|
|
2311
|
-
var baseColumns = {
|
|
2312
|
-
id: serial("id").primaryKey(),
|
|
2313
|
-
createTime: timestamp("createTime", { withTimezone: true }).notNull().defaultNow(),
|
|
2314
|
-
updateTime: timestamp("updateTime", { withTimezone: true }).notNull().defaultNow().$onUpdate(() => new Date),
|
|
2315
|
-
deletedAt: timestamp("deletedAt", { withTimezone: true }),
|
|
2316
|
-
tenantId: integer("tenantId")
|
|
2317
|
-
};
|
|
2318
|
-
var BASE_COLUMN_COMMENTS = {
|
|
2319
|
-
id: "ID",
|
|
2320
|
-
createTime: "\u521B\u5EFA\u65F6\u95F4",
|
|
2321
|
-
updateTime: "\u66F4\u65B0\u65F6\u95F4",
|
|
2322
|
-
deletedAt: "\u5220\u9664\u65F6\u95F4",
|
|
2323
|
-
tenantId: "\u79DF\u6237"
|
|
2324
|
-
};
|
|
2325
|
-
|
|
2326
|
-
// src/orm/column-comments.ts
|
|
2327
|
-
var registry = new WeakMap;
|
|
2328
|
-
var tables = new Set;
|
|
2329
|
-
function columnComments(table, comments = {}) {
|
|
2330
|
-
tables.add(table);
|
|
2331
|
-
registry.set(table, {
|
|
2332
|
-
...BASE_COLUMN_COMMENTS,
|
|
2333
|
-
...registry.get(table) || {},
|
|
2334
|
-
...comments
|
|
2335
|
-
});
|
|
2336
|
-
return table;
|
|
2337
|
-
}
|
|
2338
|
-
function getColumnComments(table) {
|
|
2339
|
-
return registry.get(table) || {};
|
|
2340
|
-
}
|
|
2341
|
-
function listColumnCommentTables() {
|
|
2342
|
-
return [...tables];
|
|
2343
|
-
}
|
|
2344
|
-
function quoteIdent(name) {
|
|
2345
|
-
if (!/^[A-Za-z_][A-Za-z0-9_]*$/.test(name)) {
|
|
2346
|
-
throw new Error(`[columnComments] \u975E\u6CD5\u6807\u8BC6\u7B26: ${name}`);
|
|
2347
|
-
}
|
|
2348
|
-
return `"${name}"`;
|
|
2349
|
-
}
|
|
2350
|
-
function escapeLiteral(value) {
|
|
2351
|
-
return value.replace(/'/g, "''");
|
|
2352
|
-
}
|
|
2353
|
-
async function syncColumnCommentsToPg(sql5) {
|
|
2354
|
-
const registered = listColumnCommentTables();
|
|
2355
|
-
if (!registered.length)
|
|
2356
|
-
return 0;
|
|
2357
|
-
const desired = new Map;
|
|
2358
|
-
const tableNames = [];
|
|
2359
|
-
for (const table of registered) {
|
|
2360
|
-
let name;
|
|
2361
|
-
try {
|
|
2362
|
-
name = getTableName(table);
|
|
2363
|
-
} catch {
|
|
2364
|
-
continue;
|
|
2365
|
-
}
|
|
2366
|
-
const cols = getTableColumns2(table);
|
|
2367
|
-
const comments = getColumnComments(table);
|
|
2368
|
-
const colMap = new Map;
|
|
2369
|
-
for (const [prop, text] of Object.entries(comments)) {
|
|
2370
|
-
if (!text || !(prop in cols))
|
|
2371
|
-
continue;
|
|
2372
|
-
colMap.set(prop, text);
|
|
2373
|
-
}
|
|
2374
|
-
if (!colMap.size)
|
|
2375
|
-
continue;
|
|
2376
|
-
desired.set(name, colMap);
|
|
2377
|
-
tableNames.push(name);
|
|
2378
|
-
}
|
|
2379
|
-
if (!tableNames.length)
|
|
2380
|
-
return 0;
|
|
2381
|
-
const inList = tableNames.map((t) => `'${escapeLiteral(t)}'`).join(",");
|
|
2382
|
-
const rows = await sql5.unsafe(`
|
|
2383
|
-
SELECT
|
|
2384
|
-
c.relname AS table_name,
|
|
2385
|
-
a.attname AS column_name,
|
|
2386
|
-
col_description(a.attrelid, a.attnum) AS comment
|
|
2387
|
-
FROM pg_catalog.pg_class c
|
|
2388
|
-
JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
|
|
2389
|
-
JOIN pg_catalog.pg_attribute a ON a.attrelid = c.oid
|
|
2390
|
-
WHERE c.relkind = 'r'
|
|
2391
|
-
AND n.nspname = current_schema()
|
|
2392
|
-
AND a.attnum > 0
|
|
2393
|
-
AND NOT a.attisdropped
|
|
2394
|
-
AND c.relname IN (${inList})
|
|
2395
|
-
`);
|
|
2396
|
-
const existing = new Map;
|
|
2397
|
-
for (const row of rows || []) {
|
|
2398
|
-
if (!row.table_name || !row.column_name)
|
|
2399
|
-
continue;
|
|
2400
|
-
existing.set(`${row.table_name}.${row.column_name}`, row.comment ?? null);
|
|
2401
|
-
}
|
|
2402
|
-
let updated = 0;
|
|
2403
|
-
for (const [tableName, cols] of desired) {
|
|
2404
|
-
for (const [colName2, text] of cols) {
|
|
2405
|
-
const key = `${tableName}.${colName2}`;
|
|
2406
|
-
const cur = existing.get(key);
|
|
2407
|
-
if (cur === text)
|
|
2408
|
-
continue;
|
|
2409
|
-
await sql5.unsafe(`COMMENT ON COLUMN ${quoteIdent(tableName)}.${quoteIdent(colName2)} IS '${escapeLiteral(text)}'`);
|
|
2410
|
-
updated++;
|
|
2411
|
-
}
|
|
2412
|
-
}
|
|
2413
|
-
return updated;
|
|
2414
|
-
}
|
|
2415
|
-
|
|
2416
|
-
// src/routing/eps.ts
|
|
2417
|
-
var SIDE_PREFIX2 = {
|
|
2418
|
-
admin: "/admin",
|
|
2419
|
-
app: "/app"
|
|
2420
|
-
};
|
|
2421
|
-
function getSidePrefix2(side) {
|
|
2422
|
-
return normalizePrefix(SIDE_PREFIX2[side]);
|
|
2423
|
-
}
|
|
2424
|
-
function lastSegment(prefix) {
|
|
2425
|
-
const parts = prefix.replace(/^\/+|\/+$/g, "").split("/");
|
|
2426
|
-
return parts[parts.length - 1] || prefix || "index";
|
|
2427
|
-
}
|
|
2428
|
-
function toPascalEntityName(tableName) {
|
|
2429
|
-
return tableName.split("_").filter(Boolean).map((s) => s.charAt(0).toUpperCase() + s.slice(1)).join("") + "Entity";
|
|
2430
|
-
}
|
|
2431
|
-
function withAlias(fields) {
|
|
2432
|
-
if (!fields?.length)
|
|
2433
|
-
return [];
|
|
2434
|
-
return fields.map((f) => {
|
|
2435
|
-
if (typeof f !== "string") {
|
|
2436
|
-
const col = f.column;
|
|
2437
|
-
return {
|
|
2438
|
-
...f,
|
|
2439
|
-
column: col.includes(".") ? col : `a.${col}`
|
|
2440
|
-
};
|
|
2441
|
-
}
|
|
2442
|
-
return f.includes(".") ? f : `a.${f}`;
|
|
2443
|
-
});
|
|
2444
|
-
}
|
|
2445
|
-
function normalizePageQueryOp(op) {
|
|
2446
|
-
return {
|
|
2447
|
-
keyWordLikeFields: withAlias(op?.keyWordLikeFields),
|
|
2448
|
-
fieldEq: withAlias(op?.fieldEq),
|
|
2449
|
-
fieldLike: withAlias(op?.fieldLike),
|
|
2450
|
-
fieldArray: withAlias(op?.fieldArray),
|
|
2451
|
-
fieldRange: (op?.fieldRange ?? []).map((r) => ({
|
|
2452
|
-
...r,
|
|
2453
|
-
column: r.column.includes(".") ? r.column : `a.${r.column}`
|
|
2454
|
-
}))
|
|
2455
|
-
};
|
|
2456
|
-
}
|
|
2457
|
-
function applyFieldDictToColumns(columns, fieldEq) {
|
|
2458
|
-
for (const ref of fieldEq) {
|
|
2459
|
-
if (typeof ref === "string" || !ref.dict)
|
|
2460
|
-
continue;
|
|
2461
|
-
const name = ref.column.includes(".") ? ref.column.split(".").pop() : ref.column;
|
|
2462
|
-
const col = columns.find((c) => c.propertyName === name);
|
|
2463
|
-
if (col)
|
|
2464
|
-
col.dict = ref.dict;
|
|
2465
|
-
}
|
|
2466
|
-
}
|
|
2467
|
-
function columnsFromEntity(entity) {
|
|
2468
|
-
if (!entity || typeof entity !== "object")
|
|
2469
|
-
return [];
|
|
2470
|
-
try {
|
|
2471
|
-
const cols = getTableColumns3(entity);
|
|
2472
|
-
const comments = getColumnComments(entity);
|
|
2473
|
-
const list = [];
|
|
2474
|
-
for (const [propertyName, col] of Object.entries(cols)) {
|
|
2475
|
-
if (propertyName === "tenantId")
|
|
2476
|
-
continue;
|
|
2477
|
-
const c = col;
|
|
2478
|
-
list.push({
|
|
2479
|
-
propertyName,
|
|
2480
|
-
type: String(c.dataType ?? c.columnType ?? "string"),
|
|
2481
|
-
length: c.length != null ? String(c.length) : undefined,
|
|
2482
|
-
nullable: c.notNull !== true,
|
|
2483
|
-
source: `a.${propertyName}`,
|
|
2484
|
-
comment: comments[propertyName]
|
|
2485
|
-
});
|
|
2486
|
-
}
|
|
2487
|
-
const tail = new Set(["createTime", "updateTime", "deletedAt"]);
|
|
2488
|
-
const head = list.filter((c) => !tail.has(c.propertyName));
|
|
2489
|
-
const end = list.filter((c) => tail.has(c.propertyName));
|
|
2490
|
-
return [...head, ...end];
|
|
2491
|
-
} catch {
|
|
2492
|
-
return [];
|
|
2493
|
-
}
|
|
2494
|
-
}
|
|
2495
|
-
function entityNameOf(entity) {
|
|
2496
|
-
if (!entity || typeof entity !== "object")
|
|
2497
|
-
return;
|
|
2498
|
-
try {
|
|
2499
|
-
return toPascalEntityName(getTableName2(entity));
|
|
2500
|
-
} catch {
|
|
2501
|
-
return;
|
|
2502
|
-
}
|
|
2503
|
-
}
|
|
2504
|
-
function buildApis(meta, fullPrefix) {
|
|
2505
|
-
const apis = [];
|
|
2506
|
-
const seen = new Set;
|
|
2507
|
-
const push = (item) => {
|
|
2508
|
-
const key = `${item.method}:${item.path}`;
|
|
2509
|
-
if (seen.has(key))
|
|
2510
|
-
return;
|
|
2511
|
-
seen.add(key);
|
|
2512
|
-
apis.push(item);
|
|
2513
|
-
};
|
|
2514
|
-
for (const route of meta.routes) {
|
|
2515
|
-
const subPath = getRouteSubPath(route.path, meta.prefix);
|
|
2516
|
-
const path = subPath.startsWith("/") ? subPath : `/${subPath}`;
|
|
2517
|
-
const action = actionFromSubPath(path);
|
|
2518
|
-
push({
|
|
2519
|
-
method: route.method.toLowerCase(),
|
|
2520
|
-
path,
|
|
2521
|
-
summary: route.summary ?? "",
|
|
2522
|
-
dts: {},
|
|
2523
|
-
tag: "",
|
|
2524
|
-
prefix: fullPrefix,
|
|
2525
|
-
ignoreToken: Boolean(route.public),
|
|
2526
|
-
ignorePerms: Boolean(route.ignorePerms),
|
|
2527
|
-
perms: effectivePerms(route, meta, action) ?? []
|
|
2528
|
-
});
|
|
2529
|
-
}
|
|
2530
|
-
for (const name of meta.crud?.api ?? []) {
|
|
2531
|
-
const path = `/${name}`;
|
|
2532
|
-
push({
|
|
2533
|
-
method: name === "info" ? "get" : "post",
|
|
2534
|
-
path,
|
|
2535
|
-
summary: CRUD_SUMMARY[name] ?? name,
|
|
2536
|
-
dts: {},
|
|
2537
|
-
tag: "",
|
|
2538
|
-
prefix: fullPrefix,
|
|
2539
|
-
ignoreToken: false,
|
|
2540
|
-
ignorePerms: false,
|
|
2541
|
-
perms: effectivePerms({}, meta, name) ?? []
|
|
2542
|
-
});
|
|
2543
|
-
}
|
|
2544
|
-
for (const name of meta.crud?.serviceApis ?? []) {
|
|
2545
|
-
const path = `/${name}`;
|
|
2546
|
-
push({
|
|
2547
|
-
method: "post",
|
|
2548
|
-
path,
|
|
2549
|
-
summary: name,
|
|
2550
|
-
dts: {},
|
|
2551
|
-
tag: "",
|
|
2552
|
-
prefix: fullPrefix,
|
|
2553
|
-
ignoreToken: false,
|
|
2554
|
-
ignorePerms: false,
|
|
2555
|
-
perms: effectivePerms({}, meta, name) ?? []
|
|
2556
|
-
});
|
|
2557
|
-
}
|
|
2558
|
-
return apis;
|
|
2559
|
-
}
|
|
2560
|
-
function buildEntity(meta) {
|
|
2561
|
-
const fullPrefix = joinPrefix(getSidePrefix2(meta.side), meta.prefix);
|
|
2562
|
-
const typeName = lastSegment(meta.prefix);
|
|
2563
|
-
const entity = meta.crud?.entity;
|
|
2564
|
-
const columns = columnsFromEntity(entity);
|
|
2565
|
-
const pageQueryOp = normalizePageQueryOp(meta.crud?.pageQueryOp);
|
|
2566
|
-
applyFieldDictToColumns(columns, pageQueryOp.fieldEq);
|
|
2567
|
-
return {
|
|
2568
|
-
module: meta.module,
|
|
2569
|
-
side: meta.side,
|
|
2570
|
-
prefix: fullPrefix,
|
|
2571
|
-
name: entityNameOf(entity),
|
|
2572
|
-
info: {
|
|
2573
|
-
type: {
|
|
2574
|
-
name: typeName,
|
|
2575
|
-
description: meta.description ?? typeName
|
|
2576
|
-
}
|
|
2577
|
-
},
|
|
2578
|
-
api: buildApis(meta, fullPrefix),
|
|
2579
|
-
columns,
|
|
2580
|
-
pageQueryOp,
|
|
2581
|
-
pageColumns: columns
|
|
2582
|
-
};
|
|
2583
|
-
}
|
|
2584
|
-
function groupByModule(list) {
|
|
2585
|
-
const map = {};
|
|
2586
|
-
for (const item of list) {
|
|
2587
|
-
const arr = map[item.module] ?? [];
|
|
2588
|
-
arr.push(item);
|
|
2589
|
-
map[item.module] = arr;
|
|
2590
|
-
}
|
|
2591
|
-
return map;
|
|
2592
|
-
}
|
|
2593
|
-
function isEpsEnabled() {
|
|
2594
|
-
return Boolean(VomeConfig.vome?.eps);
|
|
2595
|
-
}
|
|
2596
|
-
function buildEps(side) {
|
|
2597
|
-
if (!isEpsEnabled())
|
|
2598
|
-
return {};
|
|
2599
|
-
return groupByModule(listControllers(side).map(buildEntity));
|
|
2600
|
-
}
|
|
2601
|
-
var Eps = {
|
|
2602
|
-
controllers: listControllers,
|
|
2603
|
-
admin: () => buildEps("admin"),
|
|
2604
|
-
app: () => buildEps("app"),
|
|
2605
|
-
enabled: isEpsEnabled
|
|
2606
|
-
};
|
|
2607
|
-
// src/routing/decorators.ts
|
|
2608
|
-
import"reflect-metadata";
|
|
2609
|
-
var ROUTES_PENDING_KEY = "vome:controller:routes-pending";
|
|
2610
|
-
function joinRoute(prefix, path) {
|
|
2611
|
-
return joinPrefix(prefix, path === "/" ? "" : path);
|
|
2612
|
-
}
|
|
2613
|
-
function asMiddlewareList(mw) {
|
|
2614
|
-
if (mw == null)
|
|
2615
|
-
return;
|
|
2616
|
-
return Array.isArray(mw) ? mw : [mw];
|
|
2617
|
-
}
|
|
2618
|
-
function appendPendingRoute(ctor, route) {
|
|
2619
|
-
const list = Reflect.getMetadata(ROUTES_PENDING_KEY, ctor) ?? [];
|
|
2620
|
-
list.push(route);
|
|
2621
|
-
Reflect.defineMetadata(ROUTES_PENDING_KEY, list, ctor);
|
|
2622
|
-
}
|
|
2623
|
-
function createParamDecorator(source) {
|
|
2624
|
-
const label = source === "params" ? "Param" : source === "body" ? "Body" : "Query";
|
|
2625
|
-
return (schema) => (target, propertyKey, parameterIndex) => {
|
|
2626
|
-
if (propertyKey === undefined) {
|
|
2627
|
-
throw new Error(`[Controller] @${label} \u53EA\u80FD\u7528\u4E8E\u65B9\u6CD5\u53C2\u6570`);
|
|
2628
|
-
}
|
|
2629
|
-
const ctor = target.constructor;
|
|
2630
|
-
appendRouteParam(ctor, String(propertyKey), {
|
|
2631
|
-
index: parameterIndex,
|
|
2632
|
-
source,
|
|
2633
|
-
schema
|
|
2634
|
-
});
|
|
2635
|
-
};
|
|
2636
|
-
}
|
|
2637
|
-
function pickCrudOptions(options) {
|
|
2638
|
-
const {
|
|
2639
|
-
api,
|
|
2640
|
-
entity,
|
|
2641
|
-
service,
|
|
2642
|
-
serviceApis,
|
|
2643
|
-
before,
|
|
2644
|
-
pageQueryOp,
|
|
2645
|
-
listQueryOp,
|
|
2646
|
-
insertParam,
|
|
2647
|
-
infoIgnoreProperty
|
|
2648
|
-
} = options;
|
|
2649
|
-
if (api == null && entity == null && service == null && serviceApis == null && before == null && pageQueryOp == null && listQueryOp == null && insertParam == null && infoIgnoreProperty == null) {
|
|
2650
|
-
return;
|
|
2651
|
-
}
|
|
2652
|
-
return {
|
|
2653
|
-
api,
|
|
2654
|
-
entity,
|
|
2655
|
-
service,
|
|
2656
|
-
serviceApis,
|
|
2657
|
-
before,
|
|
2658
|
-
pageQueryOp,
|
|
2659
|
-
listQueryOp,
|
|
2660
|
-
insertParam,
|
|
2661
|
-
infoIgnoreProperty
|
|
2662
|
-
};
|
|
2663
|
-
}
|
|
2664
|
-
function Controller(prefixOrOptions = "") {
|
|
2665
|
-
const fromString = typeof prefixOrOptions === "string";
|
|
2666
|
-
const options = fromString ? { prefix: prefixOrOptions } : prefixOrOptions;
|
|
2667
|
-
return (target) => {
|
|
2668
|
-
registerProvider({
|
|
2669
|
-
token: target,
|
|
2670
|
-
useClass: target,
|
|
2671
|
-
scope: "singleton" /* Singleton */
|
|
2672
|
-
});
|
|
2673
|
-
const ctx = getControllerScanContext();
|
|
2674
|
-
const useAuto = fromString && prefixOrOptions === "" || !fromString && (options.prefix == null || options.prefix === "");
|
|
2675
|
-
const prefix = normalizePrefix(useAuto && ctx?.file ? parseControllerAutoPrefix(ctx.file) : options.prefix ?? "");
|
|
2676
|
-
const pending = Reflect.getMetadata(ROUTES_PENDING_KEY, target) ?? [];
|
|
2677
|
-
const crud = pickCrudOptions(options);
|
|
2678
|
-
registerController({
|
|
2679
|
-
token: target,
|
|
2680
|
-
prefix,
|
|
2681
|
-
module: options.module ?? ctx?.module ?? "unknown",
|
|
2682
|
-
side: options.side ?? ctx?.side ?? "admin",
|
|
2683
|
-
description: options.description,
|
|
2684
|
-
file: ctx?.file,
|
|
2685
|
-
middleware: asMiddlewareList(options.middleware),
|
|
2686
|
-
crud,
|
|
2687
|
-
routes: pending.map((route) => {
|
|
2688
|
-
const params = getRouteParams(target, route.handler);
|
|
2689
|
-
const schema = schemaFromParams(params);
|
|
2690
|
-
const routeMw = [
|
|
2691
|
-
...route.middleware ?? [],
|
|
2692
|
-
...getRouteMiddleware(target, route.handler)
|
|
2693
|
-
];
|
|
2694
|
-
return {
|
|
2695
|
-
...route,
|
|
2696
|
-
path: joinRoute(prefix, route.path.startsWith("/") ? route.path.slice(1) : route.path),
|
|
2697
|
-
params,
|
|
2698
|
-
body: schema?.body,
|
|
2699
|
-
query: schema?.query,
|
|
2700
|
-
routeParams: schema?.params,
|
|
2701
|
-
public: isRoutePublic(target, route.handler),
|
|
2702
|
-
ignorePerms: isRouteIgnorePerms(target, route.handler),
|
|
2703
|
-
perms: getRoutePerms(target, route.handler),
|
|
2704
|
-
middleware: routeMw.length ? routeMw : undefined
|
|
2705
|
-
};
|
|
2706
|
-
})
|
|
2707
|
-
});
|
|
2708
|
-
Reflect.deleteMetadata(ROUTES_PENDING_KEY, target);
|
|
2709
|
-
clearRouteParams(target);
|
|
2710
|
-
clearRoutePublic(target);
|
|
2711
|
-
clearRouteMiddleware(target);
|
|
2712
|
-
clearRoutePerms(target);
|
|
2713
|
-
clearRouteIgnorePerms(target);
|
|
2714
|
-
};
|
|
2715
|
-
}
|
|
2716
|
-
function Use(...middleware) {
|
|
2717
|
-
return (target, propertyKey) => {
|
|
2718
|
-
const ctor = target.constructor;
|
|
2719
|
-
appendRouteMiddleware(ctor, String(propertyKey), middleware);
|
|
2720
|
-
};
|
|
2721
|
-
}
|
|
2722
|
-
function createMethodDecorator(method) {
|
|
2723
|
-
return (path = "", options) => (target, propertyKey) => {
|
|
2724
|
-
const ctor = target.constructor;
|
|
2725
|
-
appendPendingRoute(ctor, {
|
|
2726
|
-
method,
|
|
2727
|
-
path,
|
|
2728
|
-
handler: String(propertyKey),
|
|
2729
|
-
summary: options?.summary
|
|
2730
|
-
});
|
|
2731
|
-
};
|
|
2732
|
-
}
|
|
2733
|
-
function Public() {
|
|
2734
|
-
return (target, propertyKey) => {
|
|
2735
|
-
const ctor = target.constructor;
|
|
2736
|
-
markRoutePublic(ctor, String(propertyKey));
|
|
2737
|
-
};
|
|
2738
|
-
}
|
|
2739
|
-
function Perms(...codes) {
|
|
2740
|
-
return (target, propertyKey) => {
|
|
2741
|
-
const ctor = target.constructor;
|
|
2742
|
-
setRoutePerms(ctor, String(propertyKey), codes);
|
|
2743
|
-
};
|
|
2744
|
-
}
|
|
2745
|
-
function IgnorePerms() {
|
|
2746
|
-
return (target, propertyKey) => {
|
|
2747
|
-
const ctor = target.constructor;
|
|
2748
|
-
markRouteIgnorePerms(ctor, String(propertyKey));
|
|
2749
|
-
};
|
|
2750
|
-
}
|
|
2751
|
-
var Body = createParamDecorator("body");
|
|
2752
|
-
var Query = createParamDecorator("query");
|
|
2753
|
-
var Param = createParamDecorator("params");
|
|
2754
|
-
var Get = createMethodDecorator("GET");
|
|
2755
|
-
var Post = createMethodDecorator("POST");
|
|
2756
|
-
var Put = createMethodDecorator("PUT");
|
|
2757
|
-
var Delete = createMethodDecorator("DELETE");
|
|
2758
|
-
var Patch = createMethodDecorator("PATCH");
|
|
2759
|
-
// src/ext/base-plugin.ts
|
|
2760
|
-
class BasePlugin {
|
|
2761
|
-
pluginInfo;
|
|
2762
|
-
ctx;
|
|
2763
|
-
cache;
|
|
2764
|
-
pluginService;
|
|
2765
|
-
async init(pluginInfo, ctx, _app, services) {
|
|
2766
|
-
this.pluginInfo = pluginInfo;
|
|
2767
|
-
this.ctx = ctx;
|
|
2768
|
-
this.cache = services?.cache;
|
|
2769
|
-
this.pluginService = services?.pluginService;
|
|
2770
|
-
await this.ready();
|
|
2771
|
-
}
|
|
2772
|
-
async ready() {}
|
|
2773
|
-
}
|
|
2774
|
-
// src/ext/load-plugin.ts
|
|
2775
|
-
import { existsSync, readFileSync } from "fs";
|
|
2776
|
-
import { createRequire } from "module";
|
|
2777
|
-
import { join as join7 } from "path";
|
|
2778
|
-
|
|
2779
|
-
// src/ext/path.ts
|
|
2780
|
-
import { createHash } from "crypto";
|
|
2781
|
-
import { homedir } from "os";
|
|
2782
|
-
import { join as join6 } from "path";
|
|
2783
|
-
function pDataPath() {
|
|
2784
|
-
const hash = createHash("md5").update(String(VomeConfig.keys ?? "vome")).digest("hex");
|
|
2785
|
-
return join6(homedir(), ".vome", hash);
|
|
2786
|
-
}
|
|
2787
|
-
function pPluginPath() {
|
|
2788
|
-
return join6(pDataPath(), "plugin");
|
|
2789
|
-
}
|
|
2790
|
-
function pModulesPath() {
|
|
2791
|
-
return join6(pDataPath(), "modules");
|
|
2792
|
-
}
|
|
2793
|
-
function pModulePath(key) {
|
|
2794
|
-
return join6(pModulesPath(), key);
|
|
2795
|
-
}
|
|
2796
|
-
|
|
2797
|
-
// src/ext/load-plugin.ts
|
|
2798
|
-
var hostRequire = createRequire(import.meta.url);
|
|
2799
|
-
function pluginRequire(id) {
|
|
2800
|
-
if (id === "vome-plugin-runtime")
|
|
2801
|
-
return { BasePlugin };
|
|
2802
|
-
return hostRequire(id);
|
|
2803
|
-
}
|
|
2804
|
-
function loadPluginClass(content) {
|
|
2805
|
-
try {
|
|
2806
|
-
const normalized = content.replace(/export\s+const\s+Plugin\s*=/g, "var Plugin =").replace(/export\s+\{[^}]*\bPlugin\b[^}]*\};?/g, "").replace(/export\s+const\s+handlers\s*=/g, "var handlers =").replace(/export\s+\{[^}]*\bhandlers\b[^}]*\};?/g, "").replace(/export\s+class\s+(\w+)/g, "class $1").replace(/export\s+default\s+/g, "").replace(/import\s+\{?\s*BasePlugin\s*\}?\s*from\s*['"][^'"]+['"];?/g, "").replace(/import\s+BasePlugin\s+from\s*['"][^'"]+['"];?/g, "").replace(/require\(\s*['"]vome-plugin-runtime['"]\s*\)/g, "({ BasePlugin })");
|
|
2807
|
-
const fn = new Function("BasePlugin", "require", "module", "exports", `${normalized}
|
|
2808
|
-
var __Plugin = (typeof Plugin !== 'undefined')
|
|
2809
|
-
? Plugin
|
|
2810
|
-
: (module.exports && (module.exports.Plugin || module.exports.default || module.exports));
|
|
2811
|
-
if (typeof __Plugin === 'undefined' || __Plugin === null) {
|
|
2812
|
-
throw new Error('missing export Plugin');
|
|
2813
|
-
}
|
|
2814
|
-
return __Plugin;`);
|
|
2815
|
-
const mod = { exports: {} };
|
|
2816
|
-
return fn(BasePlugin, pluginRequire, mod, mod.exports);
|
|
2817
|
-
} catch (e) {
|
|
2818
|
-
throw new Error(`[Plugin] \u52A0\u8F7D\u5931\u8D25: ${e instanceof Error ? e.message : String(e)}`);
|
|
2819
|
-
}
|
|
2820
|
-
}
|
|
2821
|
-
function readPluginScript(keyName) {
|
|
2822
|
-
const moduleServer = join7(pModulePath(keyName), "server", "index.js");
|
|
2823
|
-
if (existsSync(moduleServer)) {
|
|
2824
|
-
return readFileSync(moduleServer, "utf8");
|
|
2825
|
-
}
|
|
2826
|
-
const legacy = join7(pPluginPath(), keyName);
|
|
2827
|
-
if (!existsSync(legacy))
|
|
2828
|
-
return;
|
|
2829
|
-
try {
|
|
2830
|
-
const payload = JSON.parse(readFileSync(legacy, "utf8"));
|
|
2831
|
-
return payload.content?.data;
|
|
2832
|
-
} catch {
|
|
2833
|
-
return;
|
|
2834
|
-
}
|
|
2835
|
-
}
|
|
2836
|
-
// src/ext/module-registry.ts
|
|
2837
|
-
import { existsSync as existsSync2, readFileSync as readFileSync2, readdirSync as readdirSync2, statSync } from "fs";
|
|
2838
|
-
import { createRequire as createRequire2 } from "module";
|
|
2839
|
-
import { join as join8 } from "path";
|
|
2840
|
-
var registry2 = new Map;
|
|
2841
|
-
var hostRequire2 = createRequire2(import.meta.url);
|
|
2842
|
-
function pluginRequire2(id) {
|
|
2843
|
-
if (id === "vome-plugin-runtime")
|
|
2844
|
-
return { BasePlugin };
|
|
2845
|
-
return hostRequire2(id);
|
|
2846
|
-
}
|
|
2847
|
-
function normalizePath(path) {
|
|
2848
|
-
const p = path.startsWith("/") ? path : `/${path}`;
|
|
2849
|
-
return p.replace(/\/+$/, "") || "/";
|
|
2850
|
-
}
|
|
2851
|
-
function normalizeMethod(method) {
|
|
2852
|
-
return method.toUpperCase();
|
|
2853
|
-
}
|
|
2854
|
-
function normalizeModuleScript(content) {
|
|
2855
|
-
return content.replace(/export\s+const\s+handlers\s*=/g, "var handlers =").replace(/export\s+\{[^}]*\bhandlers\b[^}]*\};?/g, "").replace(/export\s+default\s+\{/g, "var handlers = {").replace(/export\s+const\s+Plugin\s*=/g, "var Plugin =").replace(/export\s+\{[^}]*\bPlugin\b[^}]*\};?/g, "").replace(/export\s+class\s+(\w+)/g, "class $1").replace(/import\s+\{?\s*BasePlugin\s*\}?\s*from\s*['"][^'"]+['"];?/g, "").replace(/import\s+BasePlugin\s+from\s*['"][^'"]+['"];?/g, "").replace(/require\(\s*['"]vome-plugin-runtime['"]\s*\)/g, "({ BasePlugin })");
|
|
2856
|
-
}
|
|
2857
|
-
function loadModuleHandlers(content, required = true) {
|
|
2858
|
-
const normalized = normalizeModuleScript(content);
|
|
2859
|
-
const fn = new Function("BasePlugin", "require", "module", "exports", `${normalized}
|
|
2860
|
-
if (typeof handlers === 'undefined') return null;
|
|
2861
|
-
return handlers;`);
|
|
2862
|
-
const mod = { exports: {} };
|
|
2863
|
-
const handlers = fn(BasePlugin, pluginRequire2, mod, mod.exports);
|
|
2864
|
-
if (!handlers || typeof handlers !== "object") {
|
|
2865
|
-
if (required)
|
|
2866
|
-
throw new Error("missing export handlers");
|
|
2867
|
-
return {};
|
|
2868
|
-
}
|
|
2869
|
-
return handlers;
|
|
2870
|
-
}
|
|
2871
|
-
var ModuleRegistry = {
|
|
2872
|
-
get(key) {
|
|
2873
|
-
return registry2.get(key);
|
|
2874
|
-
},
|
|
2875
|
-
list() {
|
|
2876
|
-
return [...registry2.entries()].map(([key, mod]) => ({
|
|
2877
|
-
key,
|
|
2878
|
-
manifest: mod.manifest,
|
|
2879
|
-
routes: mod.routes
|
|
2880
|
-
}));
|
|
2881
|
-
},
|
|
2882
|
-
load(key) {
|
|
2883
|
-
if (!key || !/^[a-zA-Z0-9_-]+$/.test(key)) {
|
|
2884
|
-
throw new Error(`\u975E\u6CD5\u6A21\u5757 key: ${key}`);
|
|
2885
|
-
}
|
|
2886
|
-
const dir = pModulePath(key);
|
|
2887
|
-
const metaPath = join8(dir, "module.json");
|
|
2888
|
-
if (!existsSync2(metaPath)) {
|
|
2889
|
-
throw new Error(`\u7F3A\u5C11 module.json: ${key}`);
|
|
2890
|
-
}
|
|
2891
|
-
const manifest = JSON.parse(readFileSync2(metaPath, "utf8"));
|
|
2892
|
-
const routes = (manifest.routes ?? []).map((r) => ({
|
|
2893
|
-
...r,
|
|
2894
|
-
method: normalizeMethod(r.method),
|
|
2895
|
-
path: normalizePath(r.path)
|
|
2896
|
-
}));
|
|
2897
|
-
let handlers = {};
|
|
2898
|
-
const serverEntry = join8(dir, "server", "index.js");
|
|
2899
|
-
if (existsSync2(serverEntry)) {
|
|
2900
|
-
const content = readFileSync2(serverEntry, "utf8");
|
|
2901
|
-
handlers = loadModuleHandlers(content, routes.length > 0);
|
|
2902
|
-
for (const route of routes) {
|
|
2903
|
-
if (typeof handlers[route.handler] !== "function") {
|
|
2904
|
-
throw new Error(`\u6A21\u5757 ${key} \u7F3A\u5C11 handler: ${route.handler}`);
|
|
2905
|
-
}
|
|
2906
|
-
}
|
|
2907
|
-
} else if (routes.length) {
|
|
2908
|
-
throw new Error(`\u6A21\u5757 ${key} \u58F0\u660E\u4E86 routes \u4F46\u7F3A\u5C11 server/index.js`);
|
|
2909
|
-
}
|
|
2910
|
-
registry2.set(key, { manifest, handlers, routes });
|
|
2911
|
-
return registry2.get(key);
|
|
2912
|
-
},
|
|
2913
|
-
unload(key) {
|
|
2914
|
-
registry2.delete(key);
|
|
2915
|
-
},
|
|
2916
|
-
async dispatch(key, method, subPath, ctx) {
|
|
2917
|
-
const mod = registry2.get(key);
|
|
2918
|
-
if (!mod) {
|
|
2919
|
-
return { ok: false, status: 404, message: "\u6A21\u5757\u672A\u52A0\u8F7D" };
|
|
2920
|
-
}
|
|
2921
|
-
const m = normalizeMethod(method);
|
|
2922
|
-
const path = normalizePath(subPath);
|
|
2923
|
-
const route = mod.routes.find((r) => r.method === m && r.path === path);
|
|
2924
|
-
if (!route) {
|
|
2925
|
-
return { ok: false, status: 404, message: "\u8DEF\u7531\u4E0D\u5B58\u5728" };
|
|
2926
|
-
}
|
|
2927
|
-
const handler = mod.handlers[route.handler];
|
|
2928
|
-
if (typeof handler !== "function") {
|
|
2929
|
-
return { ok: false, status: 500, message: `handler \u7F3A\u5931: ${route.handler}` };
|
|
2930
|
-
}
|
|
2931
|
-
try {
|
|
2932
|
-
const data = await handler(ctx);
|
|
2933
|
-
return { ok: true, data, route };
|
|
2934
|
-
} catch (e) {
|
|
2935
|
-
const message = e instanceof Error ? e.message : String(e);
|
|
2936
|
-
return { ok: false, status: 500, message, route };
|
|
2937
|
-
}
|
|
2938
|
-
},
|
|
2939
|
-
bootstrap() {
|
|
2940
|
-
const root = pModulesPath();
|
|
2941
|
-
if (!existsSync2(root))
|
|
2942
|
-
return;
|
|
2943
|
-
for (const name of readdirSync2(root)) {
|
|
2944
|
-
const dir = join8(root, name);
|
|
2945
|
-
if (!statSync(dir).isDirectory())
|
|
2946
|
-
continue;
|
|
2947
|
-
if (!existsSync2(join8(dir, "module.json")))
|
|
2948
|
-
continue;
|
|
2949
|
-
try {
|
|
2950
|
-
this.load(name);
|
|
2951
|
-
console.log(`[Module] loaded ${name}`);
|
|
2952
|
-
} catch (e) {
|
|
2953
|
-
console.warn(`[Module] load failed ${name}:`, e instanceof Error ? e.message : e);
|
|
2954
|
-
}
|
|
2955
|
-
}
|
|
2956
|
-
}
|
|
2957
|
-
};
|
|
2958
|
-
// src/ext/micro-apps.ts
|
|
2959
|
-
import { existsSync as existsSync3, statSync as statSync2 } from "fs";
|
|
2960
|
-
import { join as join9, normalize, sep } from "path";
|
|
2961
|
-
import { Elysia as Elysia3 } from "elysia";
|
|
2962
|
-
var PREFIX = "/vome/apps";
|
|
2963
|
-
function contentType(filePath) {
|
|
2964
|
-
const lower = filePath.toLowerCase();
|
|
2965
|
-
if (lower.endsWith(".html"))
|
|
2966
|
-
return "text/html; charset=utf-8";
|
|
2967
|
-
if (lower.endsWith(".js") || lower.endsWith(".mjs"))
|
|
2968
|
-
return "application/javascript; charset=utf-8";
|
|
2969
|
-
if (lower.endsWith(".css"))
|
|
2970
|
-
return "text/css; charset=utf-8";
|
|
2971
|
-
if (lower.endsWith(".json"))
|
|
2972
|
-
return "application/json; charset=utf-8";
|
|
2973
|
-
if (lower.endsWith(".svg"))
|
|
2974
|
-
return "image/svg+xml";
|
|
2975
|
-
if (lower.endsWith(".png"))
|
|
2976
|
-
return "image/png";
|
|
2977
|
-
if (lower.endsWith(".jpg") || lower.endsWith(".jpeg"))
|
|
2978
|
-
return "image/jpeg";
|
|
2979
|
-
if (lower.endsWith(".woff2"))
|
|
2980
|
-
return "font/woff2";
|
|
2981
|
-
if (lower.endsWith(".woff"))
|
|
2982
|
-
return "font/woff";
|
|
2983
|
-
if (lower.endsWith(".map"))
|
|
2984
|
-
return "application/json";
|
|
2985
|
-
return "application/octet-stream";
|
|
2986
|
-
}
|
|
2987
|
-
var microApps = new Elysia3({ name: "micro-apps-static" }).get(`${PREFIX}/*`, ({ params, set: set2 }) => {
|
|
2988
|
-
const star = String(params["*"] || "");
|
|
2989
|
-
const parts = star.split("/").filter(Boolean);
|
|
2990
|
-
if (!parts.length) {
|
|
2991
|
-
set2.status = 404;
|
|
2992
|
-
return "Not Found";
|
|
2993
|
-
}
|
|
2994
|
-
const key = parts[0];
|
|
2995
|
-
if (!/^[a-zA-Z0-9_-]+$/.test(key)) {
|
|
2996
|
-
set2.status = 400;
|
|
2997
|
-
return "Invalid app key";
|
|
2998
|
-
}
|
|
2999
|
-
const root = join9(pModulePath(key), "web");
|
|
3000
|
-
if (!existsSync3(root) || !statSync2(root).isDirectory()) {
|
|
3001
|
-
set2.status = 404;
|
|
3002
|
-
return "App not found";
|
|
3003
|
-
}
|
|
3004
|
-
let sub = parts.slice(1).join("/") || "index.html";
|
|
3005
|
-
if (sub.endsWith("/"))
|
|
3006
|
-
sub += "index.html";
|
|
3007
|
-
const resolved = normalize(join9(root, sub));
|
|
3008
|
-
if (!resolved.startsWith(root + sep) && resolved !== root) {
|
|
3009
|
-
set2.status = 403;
|
|
3010
|
-
return "Forbidden";
|
|
3011
|
-
}
|
|
3012
|
-
let filePath = resolved;
|
|
3013
|
-
if (existsSync3(filePath) && statSync2(filePath).isDirectory()) {
|
|
3014
|
-
filePath = join9(filePath, "index.html");
|
|
3015
|
-
}
|
|
3016
|
-
if (!existsSync3(filePath) || !statSync2(filePath).isFile()) {
|
|
3017
|
-
set2.status = 404;
|
|
3018
|
-
return "Not Found";
|
|
3019
|
-
}
|
|
3020
|
-
set2.headers["content-type"] = contentType(filePath);
|
|
3021
|
-
set2.headers["cache-control"] = "no-cache";
|
|
3022
|
-
set2.headers["access-control-allow-origin"] = "*";
|
|
3023
|
-
return Bun.file(filePath);
|
|
3024
|
-
});
|
|
3025
|
-
// src/ext/module-gateway.ts
|
|
3026
|
-
import { Elysia as Elysia4 } from "elysia";
|
|
3027
|
-
function ok(data) {
|
|
3028
|
-
return { code: RES_CODE.SUCCESS, message: "success", data: data ?? null };
|
|
3029
|
-
}
|
|
3030
|
-
function fail(message, code = RES_CODE.ERROR) {
|
|
3031
|
-
return { code, message };
|
|
3032
|
-
}
|
|
3033
|
-
async function handleExt(ctx) {
|
|
3034
|
-
const key = ctx.params.key;
|
|
3035
|
-
if (!key || !/^[a-zA-Z0-9_-]+$/.test(key)) {
|
|
3036
|
-
ctx.set.status = 400;
|
|
3037
|
-
return fail("\u975E\u6CD5\u6A21\u5757 key");
|
|
3038
|
-
}
|
|
3039
|
-
const star = String(ctx.params["*"] || "");
|
|
3040
|
-
const subPath = `/${star}`.replace(/\/+/g, "/");
|
|
3041
|
-
const store = Context.get();
|
|
3042
|
-
const mod = ModuleRegistry.get(key);
|
|
3043
|
-
if (!mod) {
|
|
3044
|
-
ctx.set.status = 404;
|
|
3045
|
-
return fail("\u6A21\u5757\u672A\u5B89\u88C5\u6216\u672A\u52A0\u8F7D");
|
|
3046
|
-
}
|
|
3047
|
-
const method = ctx.request.method.toUpperCase();
|
|
3048
|
-
const pathNorm = subPath.replace(/\/+$/, "") || "/";
|
|
3049
|
-
const route = mod.routes.find((r) => r.method === method && r.path === pathNorm);
|
|
3050
|
-
if (!route) {
|
|
3051
|
-
ctx.set.status = 404;
|
|
3052
|
-
return fail("\u8DEF\u7531\u4E0D\u5B58\u5728");
|
|
3053
|
-
}
|
|
3054
|
-
if (route.perms && !store?.isSuper) {
|
|
3055
|
-
const held = store?.perms ?? [];
|
|
3056
|
-
if (!held.includes(route.perms)) {
|
|
3057
|
-
return ctx.status(403);
|
|
3058
|
-
}
|
|
3059
|
-
}
|
|
3060
|
-
const result = await ModuleRegistry.dispatch(key, method, subPath, {
|
|
3061
|
-
body: ctx.body,
|
|
3062
|
-
query: ctx.query ?? {},
|
|
3063
|
-
params: ctx.params,
|
|
3064
|
-
headers: ctx.request.headers,
|
|
3065
|
-
adminId: store?.adminId
|
|
3066
|
-
});
|
|
3067
|
-
if (!result.ok) {
|
|
3068
|
-
ctx.set.status = result.status;
|
|
3069
|
-
return fail(result.message);
|
|
3070
|
-
}
|
|
3071
|
-
return ok(result.data);
|
|
3072
|
-
}
|
|
3073
|
-
function createModuleGateway(options) {
|
|
3074
|
-
return new Elysia4({ name: "module-gateway" }).use(options.adminAuth).all("/admin/ext/:key/*", handleExt, { adminAuth: true }).all("/admin/ext/:key", handleExt, { adminAuth: true });
|
|
3075
|
-
}
|
|
3076
|
-
// src/auth/define-macro.ts
|
|
3077
|
-
import { Elysia as Elysia5 } from "elysia";
|
|
3078
|
-
function defineAuthMacro(name, resolve) {
|
|
3079
|
-
return new Elysia5({ name: `${name}-macro` }).macro({
|
|
3080
|
-
[name]: { resolve }
|
|
3081
|
-
}).as("scoped");
|
|
3082
|
-
}
|
|
3083
|
-
// package.json
|
|
3084
|
-
var package_default = {
|
|
3085
|
-
name: "vome-core",
|
|
3086
|
-
version: "0.0.8",
|
|
3087
|
-
description: "Vome framework \u2014 shared + Bun/Elysia server + Vue admin",
|
|
3088
|
-
license: "MIT",
|
|
3089
|
-
type: "module",
|
|
3090
|
-
files: [
|
|
3091
|
-
"dist",
|
|
3092
|
-
"src/admin",
|
|
3093
|
-
"src/shared",
|
|
3094
|
-
"typings/admin"
|
|
3095
|
-
],
|
|
3096
|
-
main: "./dist/index.js",
|
|
3097
|
-
types: "./dist/index.d.ts",
|
|
3098
|
-
exports: {
|
|
3099
|
-
".": {
|
|
3100
|
-
types: "./dist/index.d.ts",
|
|
3101
|
-
import: "./dist/index.js",
|
|
3102
|
-
default: "./dist/index.js"
|
|
3103
|
-
},
|
|
3104
|
-
"./server": {
|
|
3105
|
-
types: "./dist/server/index.d.ts",
|
|
3106
|
-
import: "./dist/server/index.js",
|
|
3107
|
-
default: "./dist/server/index.js"
|
|
3108
|
-
},
|
|
3109
|
-
"./admin": {
|
|
3110
|
-
types: "./src/admin/index.ts",
|
|
3111
|
-
import: "./src/admin/index.ts",
|
|
3112
|
-
default: "./src/admin/index.ts"
|
|
3113
|
-
},
|
|
3114
|
-
"./admin/*": "./src/admin/*",
|
|
3115
|
-
"./admin/styles/base.css": "./src/admin/styles/base.css",
|
|
3116
|
-
"./typings/*": "./typings/admin/*"
|
|
3117
|
-
},
|
|
3118
|
-
scripts: {
|
|
3119
|
-
build: `rm -rf dist && bun build ./src/index.ts ./src/server/index.ts --outdir ./dist --target bun --format esm --external elysia --external reflect-metadata --external drizzle-orm --external drizzle-zod --external @elysiajs/openapi --external @bogeychan/elysia-logger --external pino --external pino-pretty && tsc -p tsconfig.build.json && printf "%s\\n" "export * from '../src/index'" > dist/index.d.ts && mkdir -p dist/server && printf "%s\\n" "export * from '../../src/server/index'" > dist/server/index.d.ts`,
|
|
3120
|
-
"build:obfuscate": `rm -rf dist && bun build ./src/index.ts ./src/server/index.ts --outdir ./dist --target bun --format esm --minify --external elysia --external reflect-metadata --external drizzle-orm --external drizzle-zod --external @elysiajs/openapi --external @bogeychan/elysia-logger --external pino --external pino-pretty && tsc -p tsconfig.build.json && printf "%s\\n" "export * from '../src/index'" > dist/index.d.ts && mkdir -p dist/server && printf "%s\\n" "export * from '../../src/server/index'" > dist/server/index.d.ts && bun scripts/obfuscate.ts`,
|
|
3121
|
-
prepare: "bun run build"
|
|
3122
|
-
},
|
|
3123
|
-
peerDependencies: {
|
|
3124
|
-
elysia: ">=1.0.0",
|
|
3125
|
-
"reflect-metadata": ">=0.2.0",
|
|
3126
|
-
"drizzle-orm": ">=0.30.0",
|
|
3127
|
-
"drizzle-zod": ">=0.5.0",
|
|
3128
|
-
vue: ">=3.5.0",
|
|
3129
|
-
"vue-router": ">=4.0.0",
|
|
3130
|
-
pinia: ">=2.0.0",
|
|
3131
|
-
"vue-sonner": ">=2.0.0",
|
|
3132
|
-
"@vueuse/core": ">=10.0.0",
|
|
3133
|
-
clsx: ">=2.0.0",
|
|
3134
|
-
"tailwind-merge": ">=2.0.0",
|
|
3135
|
-
dompurify: ">=3.0.0",
|
|
3136
|
-
marked: ">=9.0.0"
|
|
3137
|
-
},
|
|
3138
|
-
peerDependenciesMeta: {
|
|
3139
|
-
"drizzle-orm": {
|
|
3140
|
-
optional: true
|
|
3141
|
-
},
|
|
3142
|
-
"drizzle-zod": {
|
|
3143
|
-
optional: true
|
|
3144
|
-
},
|
|
3145
|
-
vue: {
|
|
3146
|
-
optional: true
|
|
3147
|
-
},
|
|
3148
|
-
"vue-router": {
|
|
3149
|
-
optional: true
|
|
3150
|
-
},
|
|
3151
|
-
pinia: {
|
|
3152
|
-
optional: true
|
|
3153
|
-
},
|
|
3154
|
-
"vue-sonner": {
|
|
3155
|
-
optional: true
|
|
3156
|
-
},
|
|
3157
|
-
"@vueuse/core": {
|
|
3158
|
-
optional: true
|
|
3159
|
-
},
|
|
3160
|
-
clsx: {
|
|
3161
|
-
optional: true
|
|
3162
|
-
},
|
|
3163
|
-
"tailwind-merge": {
|
|
3164
|
-
optional: true
|
|
3165
|
-
},
|
|
3166
|
-
dompurify: {
|
|
3167
|
-
optional: true
|
|
3168
|
-
},
|
|
3169
|
-
marked: {
|
|
3170
|
-
optional: true
|
|
3171
|
-
}
|
|
3172
|
-
},
|
|
3173
|
-
devDependencies: {
|
|
3174
|
-
"bun-types": "latest",
|
|
3175
|
-
"drizzle-orm": "latest",
|
|
3176
|
-
"drizzle-zod": "^0.8.3",
|
|
3177
|
-
elysia: "latest",
|
|
3178
|
-
"javascript-obfuscator": "^5.4.7",
|
|
3179
|
-
"reflect-metadata": "^0.2.2",
|
|
3180
|
-
typescript: "latest"
|
|
3181
|
-
},
|
|
3182
|
-
dependencies: {
|
|
3183
|
-
"@bogeychan/elysia-logger": "^0.1.10",
|
|
3184
|
-
"@elysiajs/openapi": "^1.4.15",
|
|
3185
|
-
pino: "^10.3.1",
|
|
3186
|
-
"pino-pretty": "^13.1.3"
|
|
3187
|
-
}
|
|
3188
|
-
};
|
|
3189
|
-
|
|
3190
|
-
// src/server/index.ts
|
|
3191
|
-
var version = package_default.version;
|
|
3192
|
-
export {
|
|
3193
|
-
vome,
|
|
3194
|
-
version,
|
|
3195
|
-
tableHasDepartmentId,
|
|
3196
|
-
syncColumnCommentsToPg,
|
|
3197
|
-
scanFiles,
|
|
3198
|
-
resolveTenantScope,
|
|
3199
|
-
resolveDataScope,
|
|
3200
|
-
readPluginScript,
|
|
3201
|
-
q,
|
|
3202
|
-
pPluginPath,
|
|
3203
|
-
pModulesPath,
|
|
3204
|
-
pModulePath,
|
|
3205
|
-
pDataPath,
|
|
3206
|
-
normalizeHost,
|
|
3207
|
-
noTenant,
|
|
3208
|
-
noDataScope,
|
|
3209
|
-
microApps,
|
|
3210
|
-
loadPluginClass,
|
|
3211
|
-
loadModuleHandlers,
|
|
3212
|
-
listProviders,
|
|
3213
|
-
listControllers,
|
|
3214
|
-
isTenantEnabled,
|
|
3215
|
-
isEpsEnabled,
|
|
3216
|
-
isCommException,
|
|
3217
|
-
getRepository,
|
|
3218
|
-
getEnv,
|
|
3219
|
-
getColumnComments,
|
|
3220
|
-
entitySchemas,
|
|
3221
|
-
defineAuthMacro,
|
|
3222
|
-
createModuleGateway,
|
|
3223
|
-
columnComments,
|
|
3224
|
-
baseColumns,
|
|
3225
|
-
attachCrudRoutes,
|
|
3226
|
-
applyRowScopes,
|
|
3227
|
-
applyDataScopeWhere,
|
|
3228
|
-
appendInjectMeta,
|
|
3229
|
-
VomeConfig,
|
|
3230
|
-
Use,
|
|
3231
|
-
ScopeEnum,
|
|
3232
|
-
Repository,
|
|
3233
|
-
RES_CODE,
|
|
3234
|
-
Query,
|
|
3235
|
-
Put,
|
|
3236
|
-
Public,
|
|
3237
|
-
Provide,
|
|
3238
|
-
Post,
|
|
3239
|
-
Perms,
|
|
3240
|
-
Patch,
|
|
3241
|
-
Param,
|
|
3242
|
-
ModuleRegistry,
|
|
3243
|
-
Logger,
|
|
3244
|
-
Ioc,
|
|
3245
|
-
InjectRepository,
|
|
3246
|
-
Inject,
|
|
3247
|
-
IgnorePerms,
|
|
3248
|
-
Get,
|
|
3249
|
-
Eps,
|
|
3250
|
-
Delete,
|
|
3251
|
-
DbStore,
|
|
3252
|
-
Controller,
|
|
3253
|
-
Context,
|
|
3254
|
-
CommException,
|
|
3255
|
-
Body,
|
|
3256
|
-
BaseService,
|
|
3257
|
-
BasePlugin,
|
|
3258
|
-
BaseController,
|
|
3259
|
-
BASE_COLUMN_COMMENTS,
|
|
3260
|
-
App
|
|
3261
|
-
};
|
|
1
|
+
const _0x4727c2=_0x1a3d;(function(_0x1fa943,_0x5277dc){const _0x80a20e=_0x1a3d,_0x572732=_0x1fa943();while(!![]){try{const _0x54e8d2=parseInt(_0x80a20e(0x383))/0x1*(parseInt(_0x80a20e(0x326))/0x2)+-parseInt(_0x80a20e(0x259))/0x3*(-parseInt(_0x80a20e(0x2d0))/0x4)+-parseInt(_0x80a20e(0x26d))/0x5*(-parseInt(_0x80a20e(0x358))/0x6)+-parseInt(_0x80a20e(0x1e2))/0x7+-parseInt(_0x80a20e(0x390))/0x8*(parseInt(_0x80a20e(0x1ef))/0x9)+-parseInt(_0x80a20e(0x3a6))/0xa*(-parseInt(_0x80a20e(0x291))/0xb)+parseInt(_0x80a20e(0x347))/0xc*(-parseInt(_0x80a20e(0x348))/0xd);if(_0x54e8d2===_0x5277dc)break;else _0x572732['push'](_0x572732['shift']());}catch(_0x46b268){_0x572732['push'](_0x572732['shift']());}}}(_0x35d7,0xddcba));import{join}from'path';import{pathToFileURL}from'url';function getEnv(){const _0x4e8822=_0x1a3d;return Bun[_0x4e8822(0x2d1)][_0x4e8822(0x33f)]===_0x4e8822(0x3ac)?_0x4e8822(0x3ac):_0x4e8822(0x223);}function merge(_0x586c13,_0x17888b){const _0x4e66f0=_0x1a3d,_0x37e931={..._0x586c13};for(const _0x122223 of Object[_0x4e66f0(0x246)](_0x17888b)){const _0x3014d2=_0x37e931[_0x122223],_0x247dc3=_0x17888b[_0x122223];if(_0x3014d2&&_0x247dc3&&typeof _0x3014d2===_0x4e66f0(0x310)&&typeof _0x247dc3==='object'&&!Array[_0x4e66f0(0x327)](_0x3014d2)&&!Array[_0x4e66f0(0x327)](_0x247dc3)){_0x37e931[_0x122223]=merge(_0x3014d2,_0x247dc3);continue;}_0x37e931[_0x122223]=_0x247dc3;}return _0x37e931;}async function loadConfig(_0x4217c7=join(process[_0x4727c2(0x378)](),_0x4727c2(0x3b0))){const _0x2e18d5=_0x4727c2,_0x10cee3=getEnv()==='dev'?_0x2e18d5(0x288):_0x2e18d5(0x24c),_0xd878ce=await import(pathToFileURL(join(_0x4217c7,_0x2e18d5(0x278)))['href']),_0x13a541=await import(pathToFileURL(join(_0x4217c7,_0x10cee3))[_0x2e18d5(0x28c)]);return merge(_0xd878ce[_0x2e18d5(0x365)],_0x13a541[_0x2e18d5(0x365)]);}var VomeConfig=await loadConfig();import{Elysia as _0x59c491}from'elysia';import{Elysia}from'elysia';import{AsyncLocalStorage}from'async_hooks';var storage=new AsyncLocalStorage(),warnedOutsideRequest=![];function resolveClientIp(_0x547a56){const _0x5ee35f=_0x4727c2,_0x5374f5=_0x547a56[_0x5ee35f(0x23f)][_0x5ee35f(0x389)](_0x5ee35f(0x1fd));if(_0x5374f5){const _0x13bd9e=_0x5374f5[_0x5ee35f(0x22f)](',')[0x0]?.[_0x5ee35f(0x2fa)]();if(_0x13bd9e)return _0x13bd9e;}return _0x547a56['headers'][_0x5ee35f(0x389)](_0x5ee35f(0x31f))?.[_0x5ee35f(0x2fa)]()||_0x547a56[_0x5ee35f(0x23f)][_0x5ee35f(0x389)](_0x5ee35f(0x34b))?.[_0x5ee35f(0x2fa)]()||'';}function initContextFromRequest(_0x471a51){const _0x79e048=_0x4727c2,_0x572f45=new URL(_0x471a51[_0x79e048(0x2a6)]),_0x1160c1=_0x471a51[_0x79e048(0x23f)][_0x79e048(0x389)](_0x79e048(0x37d))?.[_0x79e048(0x22f)](',')[0x0]?.[_0x79e048(0x2fa)](),_0xb8205=_0x471a51['headers'][_0x79e048(0x389)]('host')?.['trim']();return{'requestId':crypto[_0x79e048(0x38d)](),'method':_0x471a51['method'],'path':_0x572f45[_0x79e048(0x2a1)],'ip':resolveClientIp(_0x471a51),'host':_0x1160c1||_0xb8205||_0x572f45[_0x79e048(0x360)],'startTime':Date[_0x79e048(0x322)]()};}function enterContextWith(_0x340432){const _0x5e72aa=_0x4727c2;storage[_0x5e72aa(0x20d)](_0x340432);}function getContext(){const _0x54d7c4=_0x4727c2;return storage[_0x54d7c4(0x286)]();}function assignContext(_0x3d6e5e){const _0x1ed9e0=_0x4727c2,_0x2f5e48=storage[_0x1ed9e0(0x286)]();if(!_0x2f5e48){getEnv()===_0x1ed9e0(0x3ac)&&!warnedOutsideRequest&&(warnedOutsideRequest=!![],console[_0x1ed9e0(0x1f8)](_0x1ed9e0(0x353)));return;}Object[_0x1ed9e0(0x39e)](_0x2f5e48,_0x3d6e5e);}function runContext(_0xb3e942,_0x2ecfcd){return storage['run'](_0xb3e942,_0x2ecfcd);}var Context=Object[_0x4727c2(0x39e)](assignContext,{'get':getContext,'run':runContext});import'reflect-metadata';var INJECT_METADATA_KEY=_0x4727c2(0x35a),providers=new Map();function registerProvider(_0xd5b541){const _0x38d9b7=_0x4727c2;providers[_0x38d9b7(0x2fc)](_0xd5b541[_0x38d9b7(0x341)],_0xd5b541);}function getProvider(_0x10bc10){const _0x4829bd=_0x4727c2;return providers[_0x4829bd(0x389)](_0x10bc10);}function listProviders(){const _0x5af665=_0x4727c2,_0x2f2932=new Set(),_0x585fb1=[];for(const _0x18c5d7 of providers[_0x5af665(0x319)]()){if(_0x2f2932['has'](_0x18c5d7[_0x5af665(0x2a7)]))continue;_0x2f2932[_0x5af665(0x213)](_0x18c5d7[_0x5af665(0x2a7)]),_0x585fb1['push'](_0x18c5d7);}return _0x585fb1;}function tokenLabel(_0x1d3471){const _0x2763ea=_0x4727c2;if(typeof _0x1d3471===_0x2763ea(0x256)||typeof _0x1d3471==='symbol')return String(_0x1d3471);return _0x1d3471[_0x2763ea(0x27e)]||_0x2763ea(0x23b);}function appendInjectMeta(_0x2b5288,_0x5a6566){const _0x4e09bf=_0x4727c2,_0x361447=Reflect[_0x4e09bf(0x2b7)](INJECT_METADATA_KEY,_0x2b5288)??[];_0x361447[_0x4e09bf(0x2dc)](_0x5a6566),Reflect[_0x4e09bf(0x328)](INJECT_METADATA_KEY,_0x361447,_0x2b5288);}function getInjectMetas(_0x2a3830){return Reflect['getMetadata'](INJECT_METADATA_KEY,_0x2a3830)??[];}function resetProviders(){providers['clear']();}var ScopeEnum;(_0x3e3217=>{const _0x1475f6=_0x4727c2;_0x3e3217[_0x1475f6(0x313)]=_0x1475f6(0x218),_0x3e3217[_0x1475f6(0x23a)]=_0x1475f6(0x34d),_0x3e3217[_0x1475f6(0x2a3)]=_0x1475f6(0x29b);})(ScopeEnum||={});var singletons=new Map(),creating=new Set(),requestCaches=new WeakMap();function injectProperties(_0x358f68,_0x5e6022){const _0x5deec1=_0x4727c2;for(const _0x1bb282 of getInjectMetas(_0x5e6022)){const {propertyKey:_0x4c8509,token:_0x292f3b,resolve:_0x165276}=_0x1bb282;if(!_0x165276&&_0x292f3b==null)throw new Error(_0x5deec1(0x30d)+String(_0x4c8509)+_0x5deec1(0x33d));const _0x43a01c=_0x165276?_0x165276():Ioc[_0x5deec1(0x389)](_0x292f3b);_0x358f68[_0x4c8509]=_0x43a01c;const _0x3dbde5=_0x358f68['bindEntity'];_0x165276&&typeof _0x3dbde5===_0x5deec1(0x305)&&_0x3dbde5[_0x5deec1(0x26b)](_0x358f68,_0x43a01c);}}function createInstance(_0x1c9229){const _0x3b014a=_0x4727c2;if(creating['has'](_0x1c9229))throw new Error('[Ioc]\x20检测到循环依赖:\x20'+_0x1c9229['name']);creating['add'](_0x1c9229);try{const _0x53cb78=new _0x1c9229();return injectProperties(_0x53cb78,_0x1c9229),_0x53cb78;}finally{creating[_0x3b014a(0x232)](_0x1c9229);}}function getSingleton(_0x5a7e61){const _0xcda6f2=singletons['get'](_0x5a7e61);if(_0xcda6f2)return _0xcda6f2;const _0xedc3d3=createInstance(_0x5a7e61);return singletons['set'](_0x5a7e61,_0xedc3d3),_0xedc3d3;}function getRequestCache(){const _0x6fd39c=_0x4727c2,_0x42a93a=Context[_0x6fd39c(0x389)]();if(!_0x42a93a)throw new Error(_0x6fd39c(0x361));let _0x227c8c=requestCaches[_0x6fd39c(0x389)](_0x42a93a);return!_0x227c8c&&(_0x227c8c=new Map(),requestCaches[_0x6fd39c(0x2fc)](_0x42a93a,_0x227c8c)),_0x227c8c;}function getRequestScoped(_0x4ab980){const _0x3cf10c=_0x4727c2,_0x48532b=getRequestCache(),_0x190b8f=_0x48532b[_0x3cf10c(0x389)](_0x4ab980);if(_0x190b8f)return _0x190b8f;const _0x539744=createInstance(_0x4ab980);return _0x48532b[_0x3cf10c(0x2fc)](_0x4ab980,_0x539744),_0x539744;}function resolveByScope(_0x158fe2,_0x4b4260){const _0x370166=_0x4727c2;switch(_0x4b4260){case _0x370166(0x218):return getSingleton(_0x158fe2);case'prototype':return createInstance(_0x158fe2);case _0x370166(0x34d):return getRequestScoped(_0x158fe2);default:throw new Error(_0x370166(0x2fe)+_0x4b4260);}}function resolveMeta(_0x553cd2){const _0x5a5b52=_0x4727c2,_0x204cc5=getProvider(_0x553cd2);if(!_0x204cc5)throw new Error(_0x5a5b52(0x2de)+tokenLabel(_0x553cd2));return _0x204cc5;}function bootstrapIoc(){const _0xf26266=_0x4727c2;for(const {useClass:_0x322df9,scope:_0x58f7c4}of listProviders()){_0x58f7c4===_0xf26266(0x218)&&getSingleton(_0x322df9);}console['log'](_0xf26266(0x1e3)+singletons[_0xf26266(0x2aa)]+'\x20singleton(s)');}function get(_0x510aa9){const _0x59982c=_0x4727c2,_0x5b0b85=resolveMeta(_0x510aa9);return resolveByScope(_0x5b0b85[_0x59982c(0x2a7)],_0x5b0b85['scope']);}function set(_0x3ad5b6,_0x580186){const _0x486f7f=_0x4727c2;if(typeof _0x3ad5b6===_0x486f7f(0x305)){registerProvider({'token':_0x3ad5b6,'useClass':_0x3ad5b6,'scope':_0x486f7f(0x218)}),singletons[_0x486f7f(0x2fc)](_0x3ad5b6,_0x580186);return;}const _0x268864=_0x580186?.[_0x486f7f(0x1e4)];if(!_0x268864||_0x268864===Object)throw new Error('[Ioc]\x20Ioc.set('+tokenLabel(_0x3ad5b6)+')\x20需要\x20class\x20实例,以便确定\x20useClass');registerProvider({'token':_0x3ad5b6,'useClass':_0x268864,'scope':_0x486f7f(0x218)}),registerProvider({'token':_0x268864,'useClass':_0x268864,'scope':_0x486f7f(0x218)}),singletons[_0x486f7f(0x2fc)](_0x268864,_0x580186);}function resetIoc(){const _0x42ce0d=_0x4727c2;singletons[_0x42ce0d(0x30f)](),creating[_0x42ce0d(0x30f)](),resetProviders();}var Ioc={'get':get,'set':set};import'reflect-metadata';var controllers=new Map();function registerController(_0x3c8905){const _0x4deef8=_0x4727c2;controllers[_0x4deef8(0x2fc)](_0x3c8905[_0x4deef8(0x341)],_0x3c8905);}function listControllers(_0x43c980){const _0x4d81b1=_0x4727c2,_0x286456=[...controllers['values']()];return _0x43c980?_0x286456[_0x4d81b1(0x2e3)](_0x17f969=>_0x17f969[_0x4d81b1(0x3b1)]===_0x43c980):_0x286456;}var ROUTE_PARAMS_KEY='vome:controller:route-params',ROUTE_PUBLIC_KEY=_0x4727c2(0x27b),ROUTE_MW_KEY='vome:controller:route-middleware',ROUTE_PERMS_KEY='vome:controller:route-perms',ROUTE_IGNORE_PERMS_KEY=_0x4727c2(0x1f2);function appendRouteParam(_0x4b5ef6,_0x342213,_0x133d05){const _0x5973c0=_0x4727c2,_0x2517f2=Reflect[_0x5973c0(0x2b7)](ROUTE_PARAMS_KEY,_0x4b5ef6)??{},_0x46aecd=_0x2517f2[_0x342213]??[];_0x46aecd[_0x5973c0(0x2dc)](_0x133d05),_0x2517f2[_0x342213]=_0x46aecd,Reflect[_0x5973c0(0x328)](ROUTE_PARAMS_KEY,_0x2517f2,_0x4b5ef6);}function getRouteParams(_0xea84a1,_0x361c63){const _0x55c128=_0x4727c2,_0xafca0e=Reflect[_0x55c128(0x2b7)](ROUTE_PARAMS_KEY,_0xea84a1);return _0xafca0e?.[_0x361c63]??[];}function clearRouteParams(_0x3996a0){const _0x8444e2=_0x4727c2;Reflect[_0x8444e2(0x352)](ROUTE_PARAMS_KEY,_0x3996a0);}function markRoutePublic(_0x5d8844,_0x23aeaa){const _0x3c7cc6=_0x4727c2,_0x15497a=Reflect['getMetadata'](ROUTE_PUBLIC_KEY,_0x5d8844)??{};_0x15497a[_0x23aeaa]=!![],Reflect[_0x3c7cc6(0x328)](ROUTE_PUBLIC_KEY,_0x15497a,_0x5d8844);}function isRoutePublic(_0x3b1450,_0xaf0d80){const _0x1f2d7a=_0x4727c2,_0x49d8b7=Reflect[_0x1f2d7a(0x2b7)](ROUTE_PUBLIC_KEY,_0x3b1450);return!!_0x49d8b7?.[_0xaf0d80];}function clearRoutePublic(_0x82fa73){Reflect['deleteMetadata'](ROUTE_PUBLIC_KEY,_0x82fa73);}function appendRouteMiddleware(_0x3a6322,_0x247f2b,_0x5245c8){const _0x2e39a5=_0x4727c2,_0x2e0050=Reflect[_0x2e39a5(0x2b7)](ROUTE_MW_KEY,_0x3a6322)??{};_0x2e0050[_0x247f2b]=[..._0x2e0050[_0x247f2b]??[],..._0x5245c8],Reflect[_0x2e39a5(0x328)](ROUTE_MW_KEY,_0x2e0050,_0x3a6322);}function getRouteMiddleware(_0x43b8b0,_0x1e881e){const _0x30982f=Reflect['getMetadata'](ROUTE_MW_KEY,_0x43b8b0);return _0x30982f?.[_0x1e881e]??[];}function clearRouteMiddleware(_0x1e429b){const _0x21629a=_0x4727c2;Reflect[_0x21629a(0x352)](ROUTE_MW_KEY,_0x1e429b);}function setRoutePerms(_0x1094cc,_0x576593,_0x136056){const _0x25e578=_0x4727c2,_0x2f9bba=Reflect[_0x25e578(0x2b7)](ROUTE_PERMS_KEY,_0x1094cc)??{};_0x2f9bba[_0x576593]=_0x136056,Reflect[_0x25e578(0x328)](ROUTE_PERMS_KEY,_0x2f9bba,_0x1094cc);}function getRoutePerms(_0xe0b5d,_0x3c6264){const _0xac768=Reflect['getMetadata'](ROUTE_PERMS_KEY,_0xe0b5d);return _0xac768?.[_0x3c6264];}function clearRoutePerms(_0x5a561b){const _0xf5c0ae=_0x4727c2;Reflect[_0xf5c0ae(0x352)](ROUTE_PERMS_KEY,_0x5a561b);}function markRouteIgnorePerms(_0x3dd2e7,_0xe01e85){const _0x4f2ea4=_0x4727c2,_0xe55d4d=Reflect[_0x4f2ea4(0x2b7)](ROUTE_IGNORE_PERMS_KEY,_0x3dd2e7)??{};_0xe55d4d[_0xe01e85]=!![],Reflect[_0x4f2ea4(0x328)](ROUTE_IGNORE_PERMS_KEY,_0xe55d4d,_0x3dd2e7);}function isRouteIgnorePerms(_0x2b7a99,_0x542aa0){const _0x14b25e=_0x4727c2,_0x494793=Reflect[_0x14b25e(0x2b7)](ROUTE_IGNORE_PERMS_KEY,_0x2b7a99);return!!_0x494793?.[_0x542aa0];}function clearRouteIgnorePerms(_0x2f8105){Reflect['deleteMetadata'](ROUTE_IGNORE_PERMS_KEY,_0x2f8105);}function schemaFromParams(_0xa4a0af){const _0x1a455f=_0x4727c2,_0x49ece9={};for(const _0x8f0565 of _0xa4a0af){if(_0x8f0565[_0x1a455f(0x20f)]===_0x1a455f(0x3ba)&&_0x8f0565[_0x1a455f(0x250)]!==undefined)_0x49ece9[_0x1a455f(0x3ba)]=_0x8f0565[_0x1a455f(0x250)];if(_0x8f0565[_0x1a455f(0x20f)]==='query'&&_0x8f0565['schema']!==undefined)_0x49ece9['query']=_0x8f0565[_0x1a455f(0x250)];if(_0x8f0565[_0x1a455f(0x20f)]===_0x1a455f(0x3aa)&&_0x8f0565[_0x1a455f(0x250)]!==undefined)_0x49ece9[_0x1a455f(0x3aa)]=_0x8f0565['schema'];}return Object[_0x1a455f(0x246)](_0x49ece9)[_0x1a455f(0x202)]>0x0?_0x49ece9:undefined;}function openApiTag(_0x1edca5,_0x1d3b42){return _0x1edca5+'.'+_0x1d3b42;}function sideOrder(_0x18a03e){const _0x4b5206=_0x4727c2;if(_0x18a03e===_0x4b5206(0x32b))return 0x0;if(_0x18a03e===_0x4b5206(0x343))return 0x1;return 0x2;}function parseTag(_0x260a83){const _0x1f3721=_0x4727c2,_0x42d9d1=_0x260a83[_0x1f3721(0x297)]('.');if(_0x42d9d1<0x0)return{'module':_0x260a83,'side':''};return{'module':_0x260a83[_0x1f3721(0x1fb)](0x0,_0x42d9d1),'side':_0x260a83['slice'](_0x42d9d1+0x1)};}function buildOpenApiTagDocs(){const _0x9e8f6f=_0x4727c2,_0x5946db=listControllers(),_0x14190a=new Map(),_0x4e88da=new Map();for(const _0x431452 of _0x5946db){const _0x2e34e2=openApiTag(_0x431452[_0x9e8f6f(0x265)],_0x431452['side']);!_0x14190a['has'](_0x2e34e2)&&_0x14190a[_0x9e8f6f(0x2fc)](_0x2e34e2,{'name':_0x2e34e2,'description':_0x431452[_0x9e8f6f(0x265)]+'\x20'+_0x431452[_0x9e8f6f(0x3b1)],'x-displayName':_0x431452[_0x9e8f6f(0x3b1)]});let _0x5644d8=_0x4e88da[_0x9e8f6f(0x389)](_0x431452[_0x9e8f6f(0x265)]);!_0x5644d8&&(_0x5644d8=new Set(),_0x4e88da['set'](_0x431452[_0x9e8f6f(0x265)],_0x5644d8)),_0x5644d8[_0x9e8f6f(0x213)](_0x2e34e2);}const _0x703e23=[..._0x14190a[_0x9e8f6f(0x319)]()][_0x9e8f6f(0x25e)]((_0x4ce466,_0x957ccc)=>{const _0x59643a=_0x9e8f6f,_0x27808d=parseTag(_0x4ce466[_0x59643a(0x27e)]),_0xb3435f=parseTag(_0x957ccc[_0x59643a(0x27e)]);return _0x27808d[_0x59643a(0x265)]['localeCompare'](_0xb3435f['module'])||sideOrder(_0x27808d[_0x59643a(0x3b1)])-sideOrder(_0xb3435f[_0x59643a(0x3b1)]);}),_0x1ff89b=[..._0x4e88da[_0x9e8f6f(0x3b8)]()]['sort'](([_0x1904b0],[_0x12e1fe])=>_0x1904b0[_0x9e8f6f(0x220)](_0x12e1fe))[_0x9e8f6f(0x38c)](([_0x2f2c34,_0x5d57a8])=>({'name':_0x2f2c34,'tags':[..._0x5d57a8][_0x9e8f6f(0x25e)]((_0x23290d,_0x4c9ccc)=>{const _0xe19fde=_0x9e8f6f,_0x21c50c=parseTag(_0x23290d)[_0xe19fde(0x3b1)],_0x46c9eb=parseTag(_0x4c9ccc)[_0xe19fde(0x3b1)];return sideOrder(_0x21c50c)-sideOrder(_0x46c9eb);})}));return{'tags':_0x703e23,'tagGroups':_0x1ff89b};}function normalizePrefix(_0x4b7cb2){const _0x3bd833=_0x4727c2;if(!_0x4b7cb2)return'';return _0x4b7cb2[_0x3bd833(0x2ed)]('/')?_0x4b7cb2:'/'+_0x4b7cb2;}function joinPrefix(..._0x2336e6){const _0x596bde=_0x4727c2,_0x23c7d5=_0x2336e6[_0x596bde(0x38c)](_0x26882e=>normalizePrefix(_0x26882e)[_0x596bde(0x244)](/^\/+|\/+$/g,''))[_0x596bde(0x2e3)](Boolean);return _0x23c7d5[_0x596bde(0x202)]?'/'+_0x23c7d5['join']('/'):'/';}function getRouteSubPath(_0x25ef30,_0x4eaca9){const _0x2ace9f=_0x4727c2,_0x3df412=normalizePrefix(_0x4eaca9)[_0x2ace9f(0x244)](/\/$/,''),_0x3f75e4=normalizePrefix(_0x25ef30);if(!_0x3df412)return _0x3f75e4||'/';if(_0x3f75e4===_0x3df412)return'/';if(_0x3f75e4[_0x2ace9f(0x2ed)](_0x3df412+'/'))return _0x3f75e4[_0x2ace9f(0x1fb)](_0x3df412[_0x2ace9f(0x202)])||'/';const _0x43b6b2=_0x25ef30['startsWith']('/')?_0x25ef30:'/'+_0x25ef30;return _0x43b6b2||'/';}function resolveRoutePerm(_0x2eb657,_0x8ad59d,_0x284e6f){const _0x453e42=_0x4727c2;let _0x396cbc=_0x8ad59d[_0x453e42(0x244)](/^\//,'')[_0x453e42(0x244)](/\/+/g,':');if(_0x396cbc===_0x2eb657)_0x396cbc=_0x2eb657;else _0x396cbc['startsWith'](_0x2eb657+':')&&(_0x396cbc=_0x396cbc['slice'](_0x2eb657['length']+0x1));const _0x1e4f0e=_0x2eb657+'-';_0x396cbc[_0x453e42(0x2ed)](_0x1e4f0e)&&(_0x396cbc=_0x396cbc['slice'](_0x1e4f0e[_0x453e42(0x202)]));_0x396cbc=_0x396cbc[_0x453e42(0x244)](/-/g,':');if(!_0x396cbc)_0x396cbc=_0x2eb657;return _0x2eb657+':'+_0x396cbc+':'+_0x284e6f;}function actionFromSubPath(_0x5a487f){const _0x1abcc1=_0x4727c2,_0x21e8d7=_0x5a487f[_0x1abcc1(0x244)](/^\/+|\/+$/g,'');if(!_0x21e8d7)return _0x1abcc1(0x380);const _0x21a9d1=_0x21e8d7[_0x1abcc1(0x22f)]('/');return _0x21a9d1[_0x21a9d1['length']-0x1]||_0x1abcc1(0x380);}function effectivePerms(_0x1f8617,_0x2d5b8b,_0x120dac){const _0x198e9e=_0x4727c2;if(_0x2d5b8b[_0x198e9e(0x3b1)]!=='admin'||_0x1f8617[_0x198e9e(0x200)]||_0x1f8617[_0x198e9e(0x3b2)])return;if(_0x1f8617[_0x198e9e(0x2b6)]?.['length'])return _0x1f8617[_0x198e9e(0x2b6)];const _0xbf1a83=_0x120dac??actionFromSubPath(getRouteSubPath(_0x1f8617[_0x198e9e(0x2b5)]??'/',_0x2d5b8b['prefix']));return[resolveRoutePerm(_0x2d5b8b[_0x198e9e(0x265)],_0x2d5b8b['prefix'],_0xbf1a83)];}var crudRegistrar;function setCrudRegistrar(_0x2e51ac){crudRegistrar=_0x2e51ac;}var SIDE_PREFIX={'admin':_0x4727c2(0x307),'app':'/app'},ADMIN_GUARD='adminAuth',APP_GUARD=_0x4727c2(0x2da),ELYSIA_METHODS={'GET':_0x4727c2(0x389),'POST':_0x4727c2(0x21a),'PUT':_0x4727c2(0x20e),'DELETE':'delete','PATCH':_0x4727c2(0x29a)};function getSidePrefix(_0x32b71a){return normalizePrefix(SIDE_PREFIX[_0x32b71a]);}function buildRouteSchema(_0x40223e){const _0x3626b6=_0x4727c2;if(_0x40223e[_0x3626b6(0x3aa)]?.[_0x3626b6(0x202)])return schemaFromParams(_0x40223e[_0x3626b6(0x3aa)]);const _0x5d3c8a={};if(_0x40223e[_0x3626b6(0x3ba)]!==undefined)_0x5d3c8a[_0x3626b6(0x3ba)]=_0x40223e[_0x3626b6(0x3ba)];if(_0x40223e[_0x3626b6(0x1ed)]!==undefined)_0x5d3c8a[_0x3626b6(0x1ed)]=_0x40223e[_0x3626b6(0x1ed)];if(_0x40223e['routeParams']!==undefined)_0x5d3c8a[_0x3626b6(0x3aa)]=_0x40223e[_0x3626b6(0x359)];return Object[_0x3626b6(0x246)](_0x5d3c8a)[_0x3626b6(0x202)]>0x0?_0x5d3c8a:undefined;}function assertRouteParams(_0x23071e,_0x212de4,_0x2de32a){const _0xfa3d61=_0x4727c2,_0x1a4355=new Set();for(const _0x358bba of _0x23071e){if(_0x1a4355[_0xfa3d61(0x211)](_0x358bba['source'])){const _0x533362=_0x358bba[_0xfa3d61(0x20f)]===_0xfa3d61(0x3ba)?_0xfa3d61(0x303):_0x358bba[_0xfa3d61(0x20f)]===_0xfa3d61(0x1ed)?'Query':_0xfa3d61(0x38e);throw new Error('[Router]\x20'+_0x2de32a+'.'+_0x212de4+'\x20重复\x20@'+_0x533362);}_0x1a4355['add'](_0x358bba[_0xfa3d61(0x20f)]);}}function createParamHandler(_0x5581cf,_0x3e0982,_0x3f1782){const _0x34b6b1=_0x4727c2,_0x3495c5=_0x5581cf[_0x3e0982],_0x5eb1aa=_0x3495c5[_0x34b6b1(0x37c)](_0x5581cf);if(!_0x3f1782?.[_0x34b6b1(0x202)])return _0x5eb1aa;const _0x392d62=[..._0x3f1782][_0x34b6b1(0x25e)]((_0x40ce52,_0x4ad60d)=>_0x40ce52['index']-_0x4ad60d[_0x34b6b1(0x380)]);return _0x44485f=>{const _0xb7b526=_0x34b6b1,_0x17d653=_0x392d62[_0xb7b526(0x38c)](_0x328c57=>{const _0x1f39f1=_0xb7b526;if(_0x328c57[_0x1f39f1(0x20f)]==='body')return _0x44485f[_0x1f39f1(0x3ba)];if(_0x328c57['source']===_0x1f39f1(0x1ed))return _0x44485f['query'];if(_0x328c57[_0x1f39f1(0x20f)]===_0x1f39f1(0x3aa))return _0x44485f[_0x1f39f1(0x3aa)];throw new Error(_0x1f39f1(0x316)+_0x328c57[_0x1f39f1(0x20f)]);});return _0x5eb1aa(..._0x17d653,_0x44485f);};}function createPermsGuard(_0x242dba){return _0xfe15e1=>{const _0x4c730a=_0x1a3d,_0x1bde9c=_0xfe15e1[_0x4c730a(0x2d7)],_0x4e39a9=Context[_0x4c730a(0x389)]();if(_0x4e39a9?.['isSuper'])return;const _0x601aff=_0x4e39a9?.[_0x4c730a(0x2b6)]??[];if(_0x242dba['some'](_0x131f31=>_0x601aff[_0x4c730a(0x395)](_0x131f31)))return;return _0x1bde9c(0x193);};}function openApiSummary(_0x40abd7,_0x14928b){const _0x1effbf=_0x4727c2,_0x24347d=_0x40abd7[_0x1effbf(0x244)](/^\/+|\/+$/g,'')[_0x1effbf(0x22f)]('/')[_0x1effbf(0x27d)]()||_0x40abd7;return _0x14928b?_0x24347d+'\x20'+_0x14928b:_0x24347d;}function buildRouteOptions(_0x48e224,_0x4e8335){const _0x3a255e=_0x4727c2,_0x241969=buildRouteSchema(_0x48e224)??{},_0x110e3e={..._0x241969,'detail':{'tags':[openApiTag(_0x4e8335['module'],_0x4e8335[_0x3a255e(0x3b1)])],'summary':openApiSummary(_0x48e224[_0x3a255e(0x1e6)],_0x48e224[_0x3a255e(0x1f4)])}};_0x4e8335['side']===_0x3a255e(0x32b)&&!_0x48e224['public']&&(_0x110e3e[ADMIN_GUARD]=!![]);_0x4e8335['side']==='app'&&!_0x48e224['public']&&(_0x110e3e[APP_GUARD]=!![]);const _0x3dba89=[],_0x1343a4=effectivePerms(_0x48e224,_0x4e8335);if(_0x1343a4?.[_0x3a255e(0x202)])_0x3dba89[_0x3a255e(0x2dc)](createPermsGuard(_0x1343a4));if(_0x48e224[_0x3a255e(0x274)]?.[_0x3a255e(0x202)])_0x3dba89['push'](..._0x48e224[_0x3a255e(0x274)]);if(_0x3dba89['length'])_0x110e3e[_0x3a255e(0x21d)]=_0x3dba89;return _0x110e3e;}function normalizeCrudRouteOpts(_0xc61ecf){const _0x1b501e=_0x4727c2;if(_0xc61ecf==null)return{};if(typeof _0xc61ecf===_0x1b501e(0x237))return{'public':_0xc61ecf};return _0xc61ecf;}function registerControllerPlugin(_0x1a9d49,_0x57492b){const _0x425c32=_0x4727c2,_0x307538=getSidePrefix(_0x1a9d49['side']),_0x1bd247=joinPrefix(_0x307538,_0x1a9d49['prefix']),_0x10a125=Ioc[_0x425c32(0x389)](_0x1a9d49[_0x425c32(0x341)]);let _0x9c6540=new Elysia({'prefix':_0x1bd247,'name':_0x1a9d49['token'][_0x425c32(0x27e)],'tags':[openApiTag(_0x1a9d49[_0x425c32(0x265)],_0x1a9d49['side'])]});for(const _0x16e11a of _0x1a9d49['middleware']??[]){_0x9c6540=_0x9c6540[_0x425c32(0x285)](_0x16e11a);}const _0x5a8b74=[];for(const _0x4618f8 of _0x1a9d49[_0x425c32(0x1e0)]){const _0x907477=_0x10a125[_0x4618f8[_0x425c32(0x1e6)]];if(typeof _0x907477!==_0x425c32(0x305))throw new Error(_0x425c32(0x37f)+_0x1a9d49['token']['name']+'.'+_0x4618f8['handler']+_0x425c32(0x21b));assertRouteParams(_0x4618f8[_0x425c32(0x3aa)]??[],_0x4618f8[_0x425c32(0x1e6)],_0x1a9d49[_0x425c32(0x341)][_0x425c32(0x27e)]);const _0x45348a=createParamHandler(_0x10a125,_0x4618f8[_0x425c32(0x1e6)],_0x4618f8[_0x425c32(0x3aa)]),_0x16e2ec=getRouteSubPath(_0x4618f8['path'],_0x1a9d49[_0x425c32(0x388)]),_0x4c020a=buildRouteOptions(_0x4618f8,_0x1a9d49),_0x523c85=ELYSIA_METHODS[_0x4618f8[_0x425c32(0x269)]];_0x9c6540=_0x9c6540[_0x523c85](_0x16e2ec,_0x45348a,_0x4c020a);}if(_0x1a9d49[_0x425c32(0x391)]?.['api']?.[_0x425c32(0x202)]||_0x1a9d49[_0x425c32(0x391)]?.[_0x425c32(0x30b)]?.[_0x425c32(0x202)]){if(!crudRegistrar)throw new Error(_0x425c32(0x37f)+_0x1a9d49['token'][_0x425c32(0x27e)]+_0x425c32(0x1df));_0x9c6540=crudRegistrar(_0x9c6540,_0x1a9d49,{'controller':_0x10a125,'routeOptions':_0x59de55=>{const _0x16783e=_0x425c32,{public:_0x11a218,action:_0x270801,summary:_0x357a6c}=normalizeCrudRouteOpts(_0x59de55),_0x19f775={'detail':{'tags':[openApiTag(_0x1a9d49[_0x16783e(0x265)],_0x1a9d49['side'])],'summary':openApiSummary(_0x270801??_0x16783e(0x294),_0x357a6c)}};if(_0x1a9d49['side']===_0x16783e(0x32b)&&!_0x11a218){_0x19f775[ADMIN_GUARD]=!![];if(_0x270801){const _0x24855a=resolveRoutePerm(_0x1a9d49[_0x16783e(0x265)],_0x1a9d49[_0x16783e(0x388)],_0x270801);_0x19f775[_0x16783e(0x21d)]=[createPermsGuard([_0x24855a])];}}return _0x19f775;}});for(const _0x2376e9 of _0x1a9d49[_0x425c32(0x391)]?.[_0x425c32(0x22b)]??[]){const _0x33ef63=_0x2376e9==='info'?_0x425c32(0x2c0):_0x425c32(0x3bc);_0x5a8b74[_0x425c32(0x2dc)]({'method':_0x33ef63,'path':joinPrefix(_0x1a9d49[_0x425c32(0x388)],_0x2376e9),'handler':_0x2376e9,'autoCrud':!![]});}for(const _0x3e3b53 of _0x1a9d49[_0x425c32(0x391)]?.[_0x425c32(0x30b)]??[]){_0x5a8b74[_0x425c32(0x2dc)]({'method':_0x425c32(0x3bc),'path':joinPrefix(_0x1a9d49[_0x425c32(0x388)],_0x3e3b53),'handler':_0x3e3b53,'autoCrud':!![]});}}return{'plugin':_0x9c6540,'pluginPrefix':_0x1bd247,'autoRoutes':_0x5a8b74};}function registerControllers(_0x533a1c,_0x3a4741){const _0x5d4a5d=_0x4727c2;let _0x1f2dc8=_0x533a1c,_0x5905b8=0x0;const _0x1ad42a=[];for(const _0x43e8cc of listControllers()){const {plugin:_0x555f65,pluginPrefix:_0x560e02,autoRoutes:_0x27b92d}=registerControllerPlugin(_0x43e8cc,_0x3a4741);_0x1f2dc8=_0x1f2dc8[_0x5d4a5d(0x262)](_0x555f65);for(const _0x7d0c94 of[..._0x43e8cc[_0x5d4a5d(0x1e0)],..._0x27b92d]){_0x5905b8+=0x1;const _0x1a95cd=getRouteSubPath(_0x7d0c94['path'],_0x43e8cc['prefix']),_0x55fac8=_0x1a95cd==='/'?_0x560e02:joinPrefix(_0x560e02,_0x1a95cd[_0x5d4a5d(0x244)](/^\//,'')),_0x29a54a=_0x7d0c94[_0x5d4a5d(0x200)]?_0x5d4a5d(0x356):_0x7d0c94['autoCrud']?_0x5d4a5d(0x2d4):'';_0x1ad42a[_0x5d4a5d(0x2dc)](_0x7d0c94['method']+'\x20'+_0x55fac8+_0x29a54a);}}if(_0x5905b8>0x0){console[_0x5d4a5d(0x2e2)](_0x5d4a5d(0x33a)+_0x5905b8+_0x5d4a5d(0x2a0));for(const _0x286386 of _0x1ad42a)console['log']('\x20\x20'+_0x286386);}return _0x1f2dc8;}var {Glob}=globalThis[_0x4727c2(0x2ac)],DEFAULT_EXT=/\.tsx?$/;async function scanFiles(_0x5ccac8,_0x44fdd8={}){const _0x18fc5f=_0x4727c2,{cwd:cwd=process[_0x18fc5f(0x378)](),ext:ext=DEFAULT_EXT}=_0x44fdd8,_0x3579c6=Array[_0x18fc5f(0x327)](_0x5ccac8)?_0x5ccac8:[_0x5ccac8],_0x125d50=[];for(const _0x2ba066 of _0x3579c6){const _0x42bbb4=new Glob(_0x2ba066);for await(const _0xc76403 of _0x42bbb4[_0x18fc5f(0x1ec)]({'cwd':cwd,'onlyFiles':!![]})){if(ext['test'](_0xc76403))_0x125d50['push'](_0xc76403);}}return[...new Set(_0x125d50)][_0x18fc5f(0x25e)]();}var context=null;function setControllerScanContext(_0x3ede49){context=_0x3ede49;}function getControllerScanContext(){return context;}function parseModuleFromPath(_0x5b4b0c){const _0xb54ecc=_0x4727c2,_0x1f471f=_0x5b4b0c[_0xb54ecc(0x393)](/modules\/([^/]+)\/controller\//);if(!_0x1f471f)return _0xb54ecc(0x330);return _0x1f471f[0x1];}function parseControllerAutoPrefix(_0x30e949){const _0xc56201=_0x4727c2,_0x4d5a77=_0x30e949[_0xc56201(0x244)](/\\/g,'/')['match'](/modules\/([^/]+)\/controller\/(?:admin|app)\/(.+)\.tsx?$/);if(!_0x4d5a77)return'';const _0x17bf60=_0x4d5a77[0x1],_0x35a979=_0x4d5a77[0x2][_0xc56201(0x244)](/\/+/g,'/')['replace'](/^\/|\/$/g,'');if(!_0x35a979)return'/'+_0x17bf60;return'/'+_0x17bf60+'/'+_0x35a979;}var TIME_KEY_RE=/(?:Time|Date|At)$/,ISO_RE=/^\d{4}-\d{2}-\d{2}[T ]\d{2}:\d{2}:\d{2}(?:\.\d+)?(?:Z|[+-]\d{2}:?\d{2})?$/;function formatDateTime(_0x1b4b67){const _0x4454ed=_0x4727c2,_0x1acedb=_0x1b4b67 instanceof Date?_0x1b4b67:new Date(_0x1b4b67);if(Number[_0x4454ed(0x342)](_0x1acedb['getTime']()))return String(_0x1b4b67);return new Intl[(_0x4454ed(0x302))](_0x4454ed(0x290),{'timeZone':_0x4454ed(0x399),'year':_0x4454ed(0x321),'month':'2-digit','day':_0x4454ed(0x35e),'hour':_0x4454ed(0x35e),'minute':'2-digit','second':_0x4454ed(0x35e),'hour12':![]})['format'](_0x1acedb)[_0x4454ed(0x244)]('T','\x20');}function isTimeKey(_0x38e371){const _0x332a5b=_0x4727c2;return TIME_KEY_RE[_0x332a5b(0x298)](_0x38e371);}function formatApiDates(_0x4b5775){return walk(_0x4b5775);}function walk(_0x382f09,_0x2219bc){const _0x42b851=_0x4727c2;if(_0x382f09==null)return _0x382f09;if(_0x382f09 instanceof Date)return formatDateTime(_0x382f09);if(typeof _0x382f09===_0x42b851(0x256)&&_0x2219bc&&isTimeKey(_0x2219bc)&&ISO_RE[_0x42b851(0x298)](_0x382f09))return formatDateTime(_0x382f09);if(Array['isArray'](_0x382f09))return _0x382f09[_0x42b851(0x38c)](_0x14d443=>walk(_0x14d443));if(typeof _0x382f09===_0x42b851(0x310)){if(Object[_0x42b851(0x29b)][_0x42b851(0x252)][_0x42b851(0x26b)](_0x382f09)!==_0x42b851(0x1f5))return _0x382f09;const _0x27d834={};for(const [_0x2cbd45,_0x4ec971]of Object['entries'](_0x382f09)){_0x27d834[_0x2cbd45]=walk(_0x4ec971,_0x2cbd45);}return _0x27d834;}return _0x382f09;}var RES_CODE={'SUCCESS':0x3e8,'ERROR':0x3e9};class BaseController{['ok'](_0x3d1b72){const _0x118ac9=_0x4727c2,_0x5536a1=_0x3d1b72===undefined?null:_0x3d1b72;return{'code':RES_CODE[_0x118ac9(0x2f8)],'message':_0x118ac9(0x26f),'data':_0x5536a1==null?_0x5536a1:formatApiDates(_0x5536a1)};}['fail'](_0x35c6cd='error',_0x4619ae=RES_CODE[_0x4727c2(0x34c)]){return{'code':_0x4619ae,'message':_0x35c6cd};}}import'reflect-metadata';function normalizeProvideArgs(_0x388eae){const _0x3ec046=_0x4727c2;if(_0x388eae==null)return{};if(typeof _0x388eae===_0x3ec046(0x256)||typeof _0x388eae==='symbol')return{'id':_0x388eae};return _0x388eae;}function Provide(_0x32f9eb){return _0x522fc7=>{const _0x1cbcf8=_0x1a3d,_0x2e1740=normalizeProvideArgs(_0x32f9eb),_0x153f05=_0x2e1740[_0x1cbcf8(0x279)]??_0x1cbcf8(0x218);registerProvider({'token':_0x522fc7,'useClass':_0x522fc7,'scope':_0x153f05}),_0x2e1740['id']!=null&®isterProvider({'token':_0x2e1740['id'],'useClass':_0x522fc7,'scope':_0x153f05});};}function Inject(_0xfa267d){return(_0x298201,_0x3a6e81)=>{const _0x12bf68=_0x1a3d,_0x28a23d=Reflect[_0x12bf68(0x2b7)](_0x12bf68(0x39f),_0x298201,_0x3a6e81),_0x1df7cd=_0xfa267d??_0x28a23d;if(_0x1df7cd==null)throw new Error(_0x12bf68(0x2ce)+String(_0x3a6e81)+'\x20的类型,请显式传入\x20token');appendInjectMeta(_0x298201['constructor'],{'propertyKey':_0x3a6e81,'token':_0x1df7cd});};}import{and,arrayContains,arrayOverlaps,asc,desc,eq,gte,inArray,like,lte,or,sql}from'drizzle-orm';function colName(_0x4cf464){const _0x1b9618=_0x4727c2;if(typeof _0x4cf464==='string'){const _0x322ed0=_0x4cf464[_0x1b9618(0x395)]('.')?_0x4cf464[_0x1b9618(0x22f)]('.')[_0x1b9618(0x27d)]():_0x4cf464;return{'column':_0x322ed0,'param':_0x322ed0,'none':![]};}const _0x2b7185=_0x4cf464[_0x1b9618(0x3b5)][_0x1b9618(0x395)]('.')?_0x4cf464[_0x1b9618(0x3b5)][_0x1b9618(0x22f)]('.')[_0x1b9618(0x27d)]():_0x4cf464[_0x1b9618(0x3b5)];return{'column':_0x2b7185,'param':_0x4cf464[_0x1b9618(0x2af)]??_0x2b7185,'none':Boolean(_0x4cf464['none'])};}function rangeColumn(_0x563d99){const _0x3dbae1=_0x4727c2;return _0x563d99[_0x3dbae1(0x3b5)]['includes']('.')?_0x563d99[_0x3dbae1(0x3b5)]['split']('.')[_0x3dbae1(0x27d)]():_0x563d99[_0x3dbae1(0x3b5)];}function tableCol(_0x315fde,_0x3f0082){const _0x24d39e=_0x4727c2,_0x4fcbe6=_0x315fde[_0x3f0082];if(_0x4fcbe6==null)throw new Error(_0x24d39e(0x201)+_0x3f0082);return _0x4fcbe6;}function isBlank(_0x1db959){return _0x1db959===undefined||_0x1db959===null||_0x1db959==='';}function compactWhere(_0x38d4bf){const _0x4c1837=_0x4727c2;if(_0x38d4bf==null||_0x38d4bf===![])return[];const _0x3bc55c=Array[_0x4c1837(0x327)](_0x38d4bf)?_0x38d4bf:[_0x38d4bf];return _0x3bc55c[_0x4c1837(0x2e3)](_0xe44271=>_0xe44271!=null&&_0xe44271!==![]);}var q={'between'(_0x514b38,_0x284d68,_0x42648e){if(isBlank(_0x284d68)||isBlank(_0x42648e))return;return sql`${_0x514b38} between ${_0x284d68} and ${_0x42648e}`;},'range'(_0x11a32c,_0x44a5bb,_0x1ef1d1){const _0x4c238e=_0x4727c2,_0x5cc8bc=[];if(!isBlank(_0x44a5bb))_0x5cc8bc[_0x4c238e(0x2dc)](gte(_0x11a32c,_0x44a5bb));if(!isBlank(_0x1ef1d1))_0x5cc8bc[_0x4c238e(0x2dc)](lte(_0x11a32c,_0x1ef1d1));if(!_0x5cc8bc[_0x4c238e(0x202)])return;return _0x5cc8bc[_0x4c238e(0x202)]===0x1?_0x5cc8bc[0x0]:and(..._0x5cc8bc);},'eqRest'(_0x26e927,_0x572bc9,_0x574e0c){const _0x301825=_0x4727c2,_0x28e0f3=[];for(const [_0x6d2a32,_0x5492f5]of Object[_0x301825(0x3b8)](_0x26e927)){if(isBlank(_0x5492f5))continue;const _0x23246d=_0x574e0c?.[_0x6d2a32]??_0x572bc9[_0x6d2a32];if(_0x23246d==null)continue;_0x28e0f3['push'](eq(_0x23246d,_0x5492f5));}return _0x28e0f3;},'contains'(_0x17a7db,_0x23e9e9){const _0x2f8242=_0x4727c2;if(isBlank(_0x23e9e9))return;const _0x16b7cd=Array['isArray'](_0x23e9e9)?_0x23e9e9:[_0x23e9e9];if(!_0x16b7cd[_0x2f8242(0x202)])return;return _0x16b7cd[_0x2f8242(0x202)]===0x1?arrayContains(_0x17a7db,_0x16b7cd):arrayOverlaps(_0x17a7db,_0x16b7cd);}};function _0x35d7(){const _0x3aed69=['DMfYigHHBMrSzxjZid0GEW','AgfZrw50Axr5','C2nVCgvKv2HLCMu','w1jVDxrLCL0GCMvNAxn0zxjLzcdIHPaG','pJ00lJaUma','CM91DgvpChrPB25Z','ioE8UUwWKsb0B2TLBIdMIjyGCMvZB2X2zq','w1bSDwDPBL0G5yQG6l295AsX6lsLoIa','tK9erv9ftLy','CMvZDg9YzsbMywLSzwq','Dg9Rzw4','Axnoyu4','yxbW','BwLU','Aw1Hz2uVC3zNk3HTBa','DgfNCW','ntaWnfHlqMPgEa','odG1ndnyChzZuwi','yMvMB3jL','AwrZihjLCxvPCMvK','y2yTy29UBMvJDgLUzY1PCa','rvjst1i','CMvXDwvZDa','BNvTyMvY','5y2v5lIQ5l+H5OgV','C3rHDhvZq29Kzq','Aw5Zzxj0','zgvSzxrLtwv0ywrHDge','w0nVBNrLEhrDiow9K+wjJEAxOoIVT+AXGUs4IUs4I+AwH++8JowgMEwfPEIIQ+w/VEEvPE+8IoIVT+EHRUIUPcbHC3LUy0nVBNrLEhrnyw5Hz2vYiow3SUwqR+EuQo+8Iq','zxHPDa','ywrKt3jKzxjcEq','icHWDwjSAwmP','CMvHzhK','mtq4nte5ogLgAfHwDa','CM91DgvqyxjHBxm','DM9TztPPBMPLy3q','B25szxf1zxn0','Bw9KDwXLlMPZB24','uxvLCNK','mI1KAwDPDa','AwrZ','Ag9ZDa','w0LVy10GuMvXDwvZDcdKVzZNLkJLN5/POBVLNkJOR7FMSylKUiRKUiVMLOFKUk3OP6pMNPdVViJOR7FNOA7ORQqGyxn5BMndB250zxH0twfUywDLCI5LBMfIBgxVViK','yxbWBgLJyxrPB24VANnVBJSGy2HHCNnLDd11DgyToa','C2f2zq','z2v0u1fm','zgvMyxvSDa','Aw1Hz2uVCg5N','yNvUigj1AwXKic4VC3jJl2LUzgv4lNrZic4VC3jJl3nLCNzLCI9PBMrLEc50CYaTlw91DgrPCIaUl2rPC3qGls10yxjNzxqGyNvUic0TzM9YBwf0igvZBsaTlwv4DgvYBMfSigvSExnPysaTlwv4DgvYBMfSihjLzMXLy3qTBwv0ywrHDgeGls1LEhrLCM5HBcbKCML6EMXLlw9YBsaTlwv4DgvYBMfSigrYAxP6BguTEM9Kic0TzxH0zxjUywWGqgvSExnPywPZl29Wzw5HCgKGls1LEhrLCM5HBcbayM9NzxLJAgfUl2vSExnPys1SB2DNzxiGls1LEhrLCM5HBcbWAw5Vic0TzxH0zxjUywWGCgLUBY1WCMv0DhKGjIyGDhnJic1WihrZy29UzMLNlMj1AwXKlMPZB24GjIyGChjPBNrMiciLC1XUiIaIzxHWB3j0icOGzNjVBsaNlI9ZCMmVAw5KzxGNiIa+igrPC3qVAw5KzxGUzc50CYaMjIbTA2rPCIaTCcbKAxn0l3nLCNzLCIaMjIbWCMLUDgyGiIvZxg4IicjLEhbVCNqGkIbMCM9TicCUlI9ZCMmVC2vYDMvYl2LUzgv4jYiGpIbKAxn0l3nLCNzLCI9PBMrLEc5KlNrZ','Dw5ZywzL','zgf0yvnJB3bLrgvWDeLKCW','5yIG6zMK5PE26zE0','Aw5KzxGUANm','yxnJ','CMfUz2u','6z2E5Rov5QIH5z2xigTLEq','zgf0yvr5Cgu','57Y65Bcrig1VzhvSzs5QC29UoIa','lI9KAxn0l2LUzgv4lMqUDhm','zgLNzxn0','D2vI','B25fCNjVCG','BwfUAwzLC3q','CMvXDwvZDeXVzW','Bgf0zxn0','y3DK','y29TBwvUDa','zM9UDc93B2zMmG','BgLZDff1zxj5t3a','yMLUza','Ec1MB3j3yxjKzwqTAg9ZDa','zgvZy3jPChrPB24','w1jVDxrLCL0G','Aw5KzxG','DhLWzq','yM9VDhn0CMfW','nJaWotjIqwXgDee','Aw50zxjUywWGC2vYDMvYigvYCM9Y','BM90igzVDw5K','yxbWBgLJyxrPB24VAMf2yxnJCMLWDdSGy2HHCNnLDd11DgyToa','zM9Yy2u','ChjLzML4','z2v0','BgvMDePVAw4','lI9KAxn0l3nLCNzLCI9PBMrLEc5QCW','BwfW','CMfUzg9Tvvvjra','ugfYyw0','l2LUzM8','ohf5DLLRsa','y3j1za','B3jKzxjcEvnXBa','Bwf0y2G','l2XPC3q','Aw5JBhvKzxm','6lEV55sX5lIn5A2y5zYO','cMLMicH0ExbLB2yGAgfUzgXLCNmGpt09icD1BMrLzMLUzwqNksbYzxr1CM4GBNvSBdSkCMv0DxjUigHHBMrSzxjZoW','CM0GlxjMigrPC3qGjIyGyNvUihj1BIbIDwLSzdPZzxj2zxiGjIyGyNvUihj1BIbIDwLSzdPHzg1PBG','qxnPys9tAgfUz2HHAq','C2nVCgvK','pJ0Xmc4WlJa','Aw5KzxGUAhrTBa','B2zMC2v0','yxnZAwDU','zgvZAwDUoNr5Cgu','C3vWCg9YDhntB2z0rgvSzxrL','D2L0AfrYyxnOzwq','vM9TzsbMCMfTzxDVCMSG4OcuihnOyxjLzcaRiej1BI9fBhLZAweGC2vYDMvYicSGvNvLigfKBwLU','y3jLyxrLvgLTzq','zgvZyW','CgfNzvf1zxj5t3a','nJmWndbzChrXtKK','Bw9KAwz5qwz0zxi','zgf0yvnJB3bL','zw5KC1DPDgG','CgfYyw1Z','l3jLC3rVCMu','zgv2','DMfYifbSDwDPBIa9','l3bHz2u','CgfNzq','C3jJl2nVBMzPzW','C2LKzq','AwDUB3jLugvYBxm','Bw9KAwz5qMvMB3jL','Aw5PDa','y29SDw1U','BgLZDgvU','zgvSzxrLigzHAwXLza','zw50CMLLCW','lNDVzMyY','yM9KEq','y3r4','ue9tva','y2XHC3nPyW','z2v0tw9UDgG','kIOVBw9KDwXLCY8Ql3nLCNzPy2uVkIOVkI50CW','BM8Ty2fJAgu','y291BNq','y3jLyxrL','qxbWig5VDcbMB3vUza','Aw5MBYbMywLSzwq','pJ0ZlJaUma','5yIB5BU65PE26zE0','ioMfJEE9RUs6HIbHCgKVC2vYDMLJzufWAxpVViZKVyBMNkRMIB7LIlaGq1jvrcdLRP7NJRdVViHaDM9Tzs1JB3jLigf0DgfJAenYDwrsB3v0zxmG5PYQ5OYc6l2977Yj','CM91DgvZ','BwLJCM9bChbZ','otaXotm0nMHlwhnTrG','w0LVy10GyM9VDhn0CMfWiokgKca','y29UC3rYDwn0B3i','zMLLBgrsyw5Nzq','AgfUzgXLCG','xJeZlJeUmW','AxneAxjLy3rVCNK','ChjVCgvYDhLoyw1L','C2v0rw50Axr5','pJ0YlJaUma','C2nHBG','CxvLCNK','l2fKza','otG2odq5mwH5zM9NqG','lM1QCW','y29UDhjVBgXLCG','DM9TztPJB250CM9SBgvYoNjVDxrLlwLNBM9Yzs1WzxjTCW','D3jPDgu','C3vTBwfYEq','w29IAMvJDcbpyMPLy3rD','zw5K','lNbUzW','D2fYBG','B3jKzxjcEq','kIOVBw9KDwXLCY8Ql2nVBNrYB2XSzxiVywrTAw4VkIOVkI50CW','C2XPy2u','CgX1z2LU','Ec1MB3j3yxjKzwqTzM9Y','zMLUzej5swq','DxbKyxrLvgLTzq','ChvIBgLJ','w1f1zxj5t3bDioIHQoAxOowTL+AUTtOG','BgvUz3rO','AxngAw5PDgu','w01VzhvSzv0GBg9HzcbMywLSzwqG','mc4WlJeX','CMv0DxjUAw5N','y29UDgvUDa','xJeUnc4Xnq','y29SDw1UvhLWzq','DM9Tzq','zw5HyMXL','l3zVBwuVyxbWCW','zw50zxjxAxrO','Chv0','C291CMnL','C3rHCNq','AgfZ','AgfUzgXLCNm','ywrK','lI9KAxn0l3nLCNzLCI9PBMrLEc5KlNrZ','ywrKigzHAwXLza','pJ05lJaUma','zMLUza','C2LUz2XLDg9U','C2vYDMLJzq','Cg9ZDa','ios4JEAyR+ACIEAvIcbOyw5KBgvY','AxntDxbLCG','yMvMB3jLsgfUzgXL','Dgv4Dc9JC3m7ignOyxjZzxq9DxrMltG','BgLTAxq','Bg9JywXLq29TCgfYzq','w1jLCg9ZAxrVCNLDioIHQoAxOcbKzwXLDgvKqxtVViZML6dMS5xOVA/LIkdPMAq','ufvu','ChjVza','Bwf4rgf5CW','yNvUihnJCMLWDhmVyNvPBgqTywrTAw4UDhm','yNvUihj1BIbIDwLSzdPVyMz1C2nHDgu','ioIHQoAxOcbPzcdLIjC','xJeWlJmUmq','zMLUze9Uzq','ChjPBwfYEuTLEq','yxbP','zgLZDa','CgfKu3rHCNq','lw1Hy3jV','C3bSAxq','w2nVBhvTBKnVBw1LBNrZxsdPNz7MS5xMOiFOR4BNRky6ia','DMvYC2LVBG','zgvSzxrL','zxjYB3i','DM9Tzs1JB3jL','lMPZB24','zgvIDwC','yM9VBgvHBG','zMLUzfbHz2u','ios4JEAyR+ACIEAvIoAwUEAZLq','uMvXDwvZDa','kgfUB255Bw91CYK','w0HVC3rDihnJyw4G4OAqia','B25Jzq','zMLLBgrbCNjHEq','AgvHzgvYCW','y2XVC2u','w01VzhvSzv0GBg9HzgvKia','DMfSAwrHDgLVBIbMywLSzwq','w0HVC3rDignYDwqG4OAqieb2B21LlwnVCMuVB3jT','CMvWBgfJzq','z2v0rgf0zq','A2v5CW','ywrTAw5bDxrO','yMLUzevUDgL0Eq','AM9PBG','B3jKzxi','ignVBNrYB2XSzxiGzMLSzsHZkq','ChjVzc50CW','C3jJl21PzgrSzxDHCMuVAw5KzxGUDhm','CgLKlgHVC3rUyw1L','8j+tMIbbueNMLOFMOAm6ia','C2nOzw1H','uefuq0G','Dg9tDhjPBMC','y29SDw1Ux25HBwu','zw50Axr5','yxbWBgLJyxrPB24VANnVBG','C3rYAw5N','DxbKyxrLigzHAwXLza','y29Kzq','mJaXDNHyA0np','Bg9Nz2LUzW','y29UDgvUDc10ExbL','rw50Axr5','lNDVzMy','C29YDa','lI9KAxn0l2fKBwLUl2LUzgv4lMPZ','khSGqMfZzvbSDwDPBIb9kq','DMfSDwu','DxnL','DM9TztPJB250CM9SBgvYoNjVDxrLCY1Wzw5KAw5N','pJ0WlJiUma','Bw9KDwXL','Bwq1','y2fJAgu','CgX1z2LUu2vYDMLJzq','Bwv0Ag9K','lI90ExbPBMDZl2fKBwLUlYO','y2fSBa','CMvZDg9Yzq','mZvHr1bev1y','C3jJl2XPyI9JywnOzs9PBMrLEc50CW','C3vJy2vZCW','zMLLBgrfCq','BwLJCM8TyxbWCY1ZDgf0Awm','Bwf4','5QIH5z2x5PYQ5yQG6l29','BwLKzgXLD2fYzq','B3bLCMf0Aw9UvgL0BgvtB3vYy2u','Bgf5B3v0','Ahr0CdOVl2XVy2fS','zgvMyxvSDc50CW','C2nVCgu','zNjVBq','DM9TztPJB250CM9SBgvYoNjVDxrLlxb1yMXPyW','w0jHC2vtzxj2AwnLxsdMNkRNU5hLRPRLRP7KVzpVViZOR7FKVB/NLkGGqeLUAMvJDfjLCg9ZAxrVCNKG5OIwihnLDevUDgL0Eq','Cg9W','BMfTzq','B2zM','BM90tNvSBa','DxbKyxrLqNLsB3DZ','DxbKyxrL','Cg9YDa','DxbZzxj0','B25czwzVCMviyw5KBgu','z2v0u3rVCMu','6z2E5Rov5QIH5z2xigTLEtOG','zgv2lNrZ','Dg9mB3DLCKnHC2u','lMPZ','x19ZA2LWrgf0yvnJB3bL','AhjLzG','DhjHC2G','vKfmsurbveLptG','C3rKB3v0','C3yTu0u','mJC2mu50vvbqAG','zMLSzq','Bw9KDwXLr2f0zxDHEq','ywn0Aw9U','q09ntuvovcbptIbdt0Xvtu4G','zgvMyxvSDe5VDW','BgfZDeLUzgv4t2y','DgvZDa','lI9KAxn0l2fKBwLUl3n0EwXLCY9IyxnLlMnZCW','Cgf0y2G','ChjVDg90ExbL','C3jJl2XPyI90yxnRl2LUzgv4lNrZ','5yIx6kgO5P+L6k+I','lMH0BwW','C3fS','ihjVDxrLkhmP','Cgf0Ag5HBwu','AwqGCMvXDwLYzwq','uhjVDg90ExbL','yxbWBgLJyxrPB24VB2n0zxqTC3rYzwfT','C3jJl3nOyxjLza','DxjS','DxnLq2XHC3m','Ahr0CdOVl2XVy2fSAg9ZDdO','zgvWyxj0BwvUDeLK','C2L6zq','w0HVC3rDihnRAxaG4OAqig1PC3nPBMCG','qNvU','ywnJzxnZlwnVBNrYB2WTywXSB3CTB3jPz2LU','A2v5v29YzeXPA2vgAwvSzhm','CMvXDwvZDfbHCMfT','u0Lhvevstq','zM9Yy2vezwXLDgu','lI9KAxn0l2fKBwLUlYO','tM90iezVDw5K','Aw5UzxjkB2LU','Cgf0Aa','CgvYBxm','z2v0twv0ywrHDge','BM9Uzq','revmrvrf','zgf0yq','C3jJl2XPyI9HDxrOl2LUzgv4lNrZ','zM9UDc93B2zM','Dg9vChbLCKnHC2u','w0nsvurDia','vgfZAW','r0vu','C3rVCa','jg9UvxbKyxrL','y2XHC3mGjde','DMfYigHHBMrSzxjZid0','5QIH5z2x5PYQ5A6j6kof5OIw5PYQ5yQG6l29','C29MDerLBgv0zq','ioMCGoMfJEE9RIbLBNrPDhKG5OIwihnLCNzPy2u','zxHWB3j0CW','w1jLCg9ZAxrVCNLDioAjUEMhJ+ABToAwSoAVJ+ADOEMCGow4PIbPza','AxnfCNjVCG','C3jJl2XPyI9WBhvNAw4VAw5KzxGUDhm','zgLJDa','zg9JDw1LBNrHDgLVBG','w0LVy10GqeLUAMvJDcdML6dMS5xMJQJMLQ0G','yNvUihnJCMLWDhmVB2jMDxnJyxrLlNrZ','odKZndH1s2vTtMO','zw52','x19ZA2LWvgvUyw50','A2v5','icHJCNvKkq','DxrMoa','D2HLCMu','C3rHDhvZ','zxH0zw5K','DgfIBgu','yxv0Aa','l2rLBgv0zq','ChvZAa','g1SYsHTBsa','w0LVy10G5PYQ5RoO5yAm55QeifbYB3zPzgvYoIa','Aw1Hz2uVANbLzW','pJ0ZlJuUma','kqOGia','Bg9N','zMLSDgvY','iowJSoAyJUs6HIbYB3v0zxmG5l2g57Y65BcrihnLCNzLCI9PBMrLEc5QCW','cUkwIokwIokvLYaGiokwIokwIokvLYaGiokwIokwIokwIokwIokwIokwIokvLYaGiokwIokwIokwIokvLYaGiokwIokwIokwIokvLYaG4PAi4PAi4PAi4PAi4PAi4PAi4PAi4PwxcUkwIokwIokvKsaGiokwIokwIokvKsaG4PAi4PAi4Pwu4Pwq4Pwq4Pwq4PAi4PAi4PwxicdILOJILOJILOJILOJILzCG4PAi4PAi4PAi4PAi4PwricdILOJILOJILztILzdILzdILzdILzdILz0k4PAi4PAi4PwricaG4PAi4PAi4PwricdILOJILOJILzeGicdILOJILOJILzeGiokwIokwIokvLokwIokwIokwIokwIokvLokwIokwIokvKsaG4PAi4PAi4PAi4PAi4PAi4PwxcIdILOJILOJILzCG4PAi4PAi4Pwu4PwDicdILOJILOJILzeGicdILOJILOJILzeGiokwIokwIokvKEkvMUkwIokwIokvLokvNEkwIokwIokvKsaG4PAi4PAi4Pwu4Pwq4Pwq4PwDcIaG4PwA4PAi4PAi4PAi4Pwu4PwDicaG4PwA4PAi4PAi4PAi4PAi4PAi4PAi4Pwu4PwDicdILOJILOJILzeG4PwA4Pwq4PwDiokwIokwIokvKsaG4PAi4PAi4PAi4PAi4PAi4PAi4PAi4PwxcIaGiokvMUkvKokvKokvNsaGicaG4PwA4Pwq4Pwq4Pwq4Pwq4Pwq4PwDicaG4PwA4Pwq4PwDicaGicdILzRILzdILz0GiokvMUkvKokvKokvKokvKokvKokvKokvNqO','DgfIBgvFBMfTzq','AgfUzgXLCIdNVlRLPle6ia','C2v0rgf0zq','CgfYC2u','AxngAwXL','C2vYDMvY','rM9YyMLKzgvU','C3rHCNrZv2L0Aa','z2v0uMvWBW','ugX1z2LU','lMnZCW','A2v5v29Yza','cIaGicbtruXfq1qkicaGicaGyY5YzwXUyw1LieftihrHyMXLx25HBwuScIaGicaGigeUyxr0BMfTzsbbuYbJB2X1Bw5FBMfTzsWkicaGicaGy29Sx2rLC2nYAxb0Aw9UkgeUyxr0CMvSAwqSigeUyxr0BNvTksbbuYbJB21Tzw50cIaGicbguK9nihbNx2nHDgfSB2CUCgDFy2XHC3mGyWOGicaGsK9jtIbWz19JyxrHBg9NlNbNx25HBwvZCgfJzsbUie9oig4UB2LKid0GyY5YzwXUyw1LC3bHy2ukicaGiePpsu4GCgDFy2f0ywXVzY5Wz19HDhrYAwj1DguGysbptIbHlMf0DhjLBgLKid0GyY5VAwqkicaGifDirvjfigmUCMvSA2LUzca9icDYjWOGicaGicbbtKqGBI5UC3bUyw1Lid0Gy3vYCMvUDf9Zy2HLBweOkqOGicaGicbbtKqGys5HDhrUDw0GpIaWcIaGicaGieforcbot1qGys5HDhrPC2rYB3bWzwqkicaGicaGqu5eigmUCMvSBMfTzsbjtIaO','lI9KAxn0l2LUzgv4lMPZ','Bw9KDwXLCW','ywXS','y2XPzw50','Bgv2zwW','u1vdq0vtuW','zhjPENPSzq','DhjPBq','ywrTAw5jza','C2v0','DhLWAw5NCY9Hzg1PBG','w0LVy10G5PYQ55+L5l2C55sO5z+FoIa','q29TBuv4y2vWDgLVBG','C3jJl2XPyI9KyI9PBMrLEc50CW','CMvXDwLYzuvUDgL0Eq','rgf0zvrPBwvgB3jTyxq','qM9KEq','Aw5MBW','zNvUy3rPB24','CMvZB2X2zuLKv2HLCMu','l2fKBwLU','C2nHBgfY','tw9KDwXL','CgfNzsbMywLSzwq','C2vYDMLJzufWAxm','l2rVy3m','w0LVy10G','w1jLCg9ZAxrVCNLDioIHQoAxOcbKzwXLDgvKqxtVViZML6dMS5xMGAlLPi0','y2XLyxi','B2jQzwn0','Bw9Kzq','B25SEvrYyxnOzwq','u2LUz2XLDg9U','l2fKBwLUl2v4Dc86A2v5','q2fJAgu','w1jVDxrLCL0G5PYQ55+L5y+c5PwW5P2L5RQqoIa','C3LZDgvT','BwvZC2fNzq','DMfSDwvZ','5PU05PAW5PE26zE0','DgvUyw50swq','y29UDgfPBNm','C2vSzwn0','BgLZDcbMywLSzwq','Ec1YzwfSlwLW','zgvSzxrLzef0','BNvTzxjPyW','BM93','igzHAwXLza','BgLZDa','zMfPBa','ndrOu2vNyxG','AxnbCNjHEq','zgvMAw5Ltwv0ywrHDge','5yIg6Ag15P+L6k+I','DhjHBNnWB3j0','ywrTAw4','D2vIqxv0Aa','u0Lhsu5u','zgLY','Aw5MB0LNBM9YzvbYB3bLCNr5','Dw5RBM93BG','Aw5Zzxj0ugfYyw0','DgvUyw50','l3vWzgf0zq','yNvUihj1BIbIDwLSzcaMjIbIDw4GCNvUig9IzNvZy2f0zq','CgX1z2LUsw5MBW','CgfYC2vjBNnLCNq'];_0x35d7=function(){return _0x3aed69;};return _0x35d7();}function buildFieldClauses(_0x35794f,_0x2e4fcc,_0x182fc7){const _0x1c0fc7=_0x4727c2,_0x56dc14=[];if(_0x182fc7[_0x1c0fc7(0x2ae)]?.['length']&&!isBlank(_0x2e4fcc[_0x1c0fc7(0x2f1)])){const _0x1bc7c2='%'+String(_0x2e4fcc[_0x1c0fc7(0x2f1)])+'%',_0x5bb9a5=_0x182fc7[_0x1c0fc7(0x2ae)][_0x1c0fc7(0x38c)](_0x2cc91b=>{const _0x5ee6df=_0x1c0fc7,_0x1fc618=_0x2cc91b[_0x5ee6df(0x395)]('.')?_0x2cc91b[_0x5ee6df(0x22f)]('.')['pop']():_0x2cc91b;return like(tableCol(_0x35794f,_0x1fc618),_0x1bc7c2);});if(_0x5bb9a5[_0x1c0fc7(0x202)]===0x1)_0x56dc14[_0x1c0fc7(0x2dc)](_0x5bb9a5[0x0]);else{if(_0x5bb9a5['length']>0x1)_0x56dc14['push'](or(..._0x5bb9a5));}}for(const _0x269d3f of _0x182fc7[_0x1c0fc7(0x270)]??[]){const {column:_0x32b875,param:_0x7cec0a}=colName(_0x269d3f),_0x11a9a7=_0x2e4fcc[_0x7cec0a];if(isBlank(_0x11a9a7))continue;if(Array[_0x1c0fc7(0x327)](_0x11a9a7)){if(!_0x11a9a7[_0x1c0fc7(0x202)])continue;_0x56dc14[_0x1c0fc7(0x2dc)](inArray(tableCol(_0x35794f,_0x32b875),_0x11a9a7));}else _0x56dc14[_0x1c0fc7(0x2dc)](eq(tableCol(_0x35794f,_0x32b875),_0x11a9a7));}for(const _0x346792 of _0x182fc7['fieldLike']??[]){const {column:_0x513467,param:_0x65583}=colName(_0x346792),_0x396d7f=_0x2e4fcc[_0x65583];if(isBlank(_0x396d7f))continue;_0x56dc14['push'](like(tableCol(_0x35794f,_0x513467),'%'+String(_0x396d7f)+'%'));}for(const _0x29a2af of _0x182fc7[_0x1c0fc7(0x23e)]??[]){const {column:_0x3d0996,param:_0x35fe89}=colName(_0x29a2af),_0x2fe9cf=q[_0x1c0fc7(0x31c)](tableCol(_0x35794f,_0x3d0996),_0x2e4fcc[_0x35fe89]);if(_0x2fe9cf)_0x56dc14[_0x1c0fc7(0x2dc)](_0x2fe9cf);}for(const _0x857400 of _0x182fc7[_0x1c0fc7(0x1e5)]??[]){const _0x1ded6d=tableCol(_0x35794f,rangeColumn(_0x857400)),_0x5b2aa4=q[_0x1c0fc7(0x36d)](_0x1ded6d,_0x2e4fcc[_0x857400['min']],_0x2e4fcc[_0x857400['max']]);if(_0x5b2aa4)_0x56dc14[_0x1c0fc7(0x2dc)](_0x5b2aa4);}return _0x56dc14;}function buildOrderBy(_0x4cf3a0,_0xcd01ef,_0x998e88){const _0x5f1987=_0x4727c2,_0x2acb6a=[],_0xf37616=_0xcd01ef[_0x5f1987(0x24a)]!=null?String(_0xcd01ef[_0x5f1987(0x24a)]):undefined,_0x1c69f0=_0xcd01ef['sort']==='asc'||_0xcd01ef[_0x5f1987(0x25e)]===_0x5f1987(0x3a4)?_0xcd01ef[_0x5f1987(0x25e)]:undefined;if(_0xf37616){const _0x5a75dc=tableCol(_0x4cf3a0,_0xf37616);_0x2acb6a[_0x5f1987(0x2dc)](_0x1c69f0==='asc'?asc(_0x5a75dc):desc(_0x5a75dc));}else{if(_0x998e88[_0x5f1987(0x355)])for(const [_0x48cda1,_0x12b4bd]of Object[_0x5f1987(0x3b8)](_0x998e88[_0x5f1987(0x355)])){const _0x2a89c6=_0x48cda1[_0x5f1987(0x395)]('.')?_0x48cda1[_0x5f1987(0x22f)]('.')[_0x5f1987(0x27d)]():_0x48cda1,_0x2ab074=tableCol(_0x4cf3a0,_0x2a89c6);_0x2acb6a['push'](_0x12b4bd===_0x5f1987(0x36c)?asc(_0x2ab074):desc(_0x2ab074));}}return _0x2acb6a;}function needsAdvancedQuery(_0x4260f9){const _0x1c54cd=_0x4727c2;return!!(_0x4260f9?.['join']?.['length']||_0x4260f9?.[_0x1c54cd(0x31d)]);}async function buildQueryOp(_0x5373c3,_0x2837b5,_0x1c81e5={},_0x51a092){const _0x1c2e1a=_0x4727c2,_0x447ce1=buildFieldClauses(_0x5373c3,_0x2837b5,_0x1c81e5),_0x1c2dc4=buildOrderBy(_0x5373c3,_0x2837b5,_0x1c81e5),_0x216cbe={'body':_0x2837b5,'request':_0x51a092??new Request(_0x1c2e1a(0x277))};_0x1c81e5[_0x1c2e1a(0x2d6)]&&_0x447ce1[_0x1c2e1a(0x2dc)](...compactWhere(await _0x1c81e5[_0x1c2e1a(0x2d6)](_0x216cbe)));if(_0x1c81e5[_0x1c2e1a(0x2d8)]){const _0x40afc9={'andWhere'(_0x39cac3){const _0x5122fd=_0x1c2e1a;if(_0x39cac3!=null&&_0x39cac3!==![])_0x447ce1[_0x5122fd(0x2dc)](_0x39cac3);},'orderBy'(..._0x498b8b){for(const _0x4eff05 of _0x498b8b){if(_0x4eff05!=null)_0x1c2dc4['push'](_0x4eff05);}}};await _0x1c81e5[_0x1c2e1a(0x2d8)](_0x40afc9,_0x216cbe);}const _0x57f84d=_0x447ce1[_0x1c2e1a(0x202)]===0x0?undefined:_0x447ce1[_0x1c2e1a(0x202)]===0x1?_0x447ce1[0x0]:and(..._0x447ce1);return{'where':_0x57f84d,'orderBySql':_0x1c2dc4};}import{and as _0x124388,count,countDistinct,getTableColumns,isNotNull,isNull,sql as _0x2cd2ac}from'drizzle-orm';function readCrudConfig(){const _0x35df3c=_0x4727c2;return VomeConfig[_0x35df3c(0x20a)]?.['crud']??{};}function resolveUpsert(_0x1308a6){const _0x4f2c71=_0x4727c2;return _0x1308a6??readCrudConfig()[_0x4f2c71(0x284)]??_0x4f2c71(0x351);}function resolveSoftDelete(_0x685ed7){const _0x5691cb=_0x4727c2;if(_0x685ed7!=null)return _0x685ed7;return readCrudConfig()[_0x5691cb(0x2c6)]===!![];}class DbStore{[_0x4727c2(0x2f9)];[_0x4727c2(0x2f6)];[_0x4727c2(0x250)];[_0x4727c2(0x29f)];constructor(_0x2b70b0,_0x1183a9,_0x60a850,_0x672620){const _0x53649f=_0x4727c2;this[_0x53649f(0x2f9)]=_0x2b70b0,this[_0x53649f(0x2f6)]=_0x1183a9,this['schema']=_0x60a850,this[_0x53649f(0x29f)]=_0x672620;}}import{and as _0x1b9a45,inArray as _0x3c367f,sql as _0x426b38}from'drizzle-orm';import{and as _0x25f2a8,eq as _0x20c6cf,sql as _0x21c614}from'drizzle-orm';var SKIP_KEY=_0x4727c2(0x2d2);function isTenantEnabled(){const _0x417ac5=_0x4727c2;return VomeConfig[_0x417ac5(0x20a)]?.[_0x417ac5(0x332)]===!![];}function tableHasTenantId(_0x5bf0ba){const _0x5b77ea=_0x4727c2;return _0x5bf0ba[_0x5b77ea(0x31b)]!=null;}function resolveTenantScope(){const _0x14d1fc=_0x4727c2;if(!isTenantEnabled())return _0x14d1fc(0x27f);const _0x497988=Context[_0x14d1fc(0x389)]();if(_0x497988?.[SKIP_KEY])return'off';if(_0x497988?.[_0x14d1fc(0x21c)])return'all';const _0x248e04=_0x497988?.[_0x14d1fc(0x31b)],_0x98f005=typeof _0x248e04===_0x14d1fc(0x34e)?_0x248e04:Number(_0x248e04);if(!Number[_0x14d1fc(0x203)](_0x98f005)||_0x98f005<=0x0)return'none';return _0x98f005;}function applyTenantWhere(_0x3e258a,_0x2de813){const _0x3381ec=_0x4727c2;if(!tableHasTenantId(_0x3e258a))return _0x2de813;const _0x41ffdc=resolveTenantScope();if(_0x41ffdc===_0x3381ec(0x27f)||_0x41ffdc==='all')return _0x2de813;const _0x33abc3=_0x3e258a[_0x3381ec(0x31b)],_0x1a7ae5=_0x41ffdc===_0x3381ec(0x2b8)?_0x21c614`false`:_0x20c6cf(_0x33abc3,_0x41ffdc);if(_0x2de813&&_0x1a7ae5)return _0x25f2a8(_0x2de813,_0x1a7ae5);return _0x2de813??_0x1a7ae5;}function stampTenantId(_0x4a6b18,_0x5202b8){if(!tableHasTenantId(_0x4a6b18))return _0x5202b8;const _0x59a660=resolveTenantScope();if(typeof _0x59a660!=='number')return _0x5202b8;if(_0x5202b8['tenantId']!=null)return _0x5202b8;return{..._0x5202b8,'tenantId':_0x59a660};}async function noTenant(_0x113908){const _0x5dfa4d=_0x4727c2,_0x23bea6=Context[_0x5dfa4d(0x389)]();if(!_0x23bea6)return _0x113908();const _0xb815e0=_0x23bea6[SKIP_KEY];_0x23bea6[SKIP_KEY]=!![];try{return await _0x113908();}finally{if(_0xb815e0===undefined)delete _0x23bea6[SKIP_KEY];else _0x23bea6[SKIP_KEY]=_0xb815e0;}}function normalizeHost(_0x2a0b05){const _0x464ec9=_0x4727c2;if(!_0x2a0b05)return'';return _0x2a0b05['trim']()[_0x464ec9(0x289)]()['replace'](/:\d+$/,'');}var SKIP_KEY2=_0x4727c2(0x28b);function tableHasDepartmentId(_0x38882f){const _0xa10722=_0x4727c2;return _0x38882f[_0xa10722(0x2a9)]!=null;}function resolveDataScope(){const _0x124ca8=_0x4727c2,_0x3039e7=Context['get']();if(!_0x3039e7)return _0x124ca8(0x27f);if(_0x3039e7[SKIP_KEY2])return _0x124ca8(0x27f);if(_0x3039e7['isSuper'])return _0x124ca8(0x2f5);const _0x3d4533=_0x3039e7[_0x124ca8(0x3a8)];if(_0x3d4533==null||_0x3d4533==='')return _0x124ca8(0x27f);if(_0x3d4533==='all')return _0x124ca8(0x2f5);if(_0x3d4533==='none')return'none';const _0xc9a0f7=_0x3039e7[_0x124ca8(0x369)],_0x48ad64=Array['isArray'](_0xc9a0f7)?_0xc9a0f7[_0x124ca8(0x38c)](_0x1af096=>Number(_0x1af096))['filter'](_0x18084f=>Number['isFinite'](_0x18084f)&&_0x18084f>0x0):[];if(!_0x48ad64[_0x124ca8(0x202)])return'none';return[...new Set(_0x48ad64)];}function applyDataScopeWhere(_0x21987e,_0x44950b){const _0x8f93b1=_0x4727c2;if(!tableHasDepartmentId(_0x21987e))return _0x44950b;const _0x264432=resolveDataScope();if(_0x264432==='off'||_0x264432===_0x8f93b1(0x2f5))return _0x44950b;const _0x5dce3d=_0x21987e['departmentId'],_0x4c9f33=_0x264432===_0x8f93b1(0x2b8)?_0x426b38`false`:_0x3c367f(_0x5dce3d,_0x264432);if(_0x44950b)return _0x1b9a45(_0x44950b,_0x4c9f33);return _0x4c9f33;}function applyRowScopes(_0x2bf40c,_0x237582){return applyDataScopeWhere(_0x2bf40c,applyTenantWhere(_0x2bf40c,_0x237582));}async function noDataScope(_0x32da19){const _0x111a40=_0x4727c2,_0x321be4=Context[_0x111a40(0x389)]();if(!_0x321be4)return _0x32da19();const _0x383cf9=_0x321be4[SKIP_KEY2];_0x321be4[SKIP_KEY2]=!![];try{return await _0x32da19();}finally{if(_0x383cf9===undefined)delete _0x321be4[SKIP_KEY2];else _0x321be4[SKIP_KEY2]=_0x383cf9;}}function deletedAtColumn(_0x115a56){return _0x115a56['deletedAt'];}function trashClause(_0x160319,_0x468e31){const _0x35d9f2=_0x4727c2;if(!resolveSoftDelete(_0x468e31?.[_0x35d9f2(0x2c6)]))return;const _0x349396=deletedAtColumn(_0x160319);if(_0x349396==null)return;if(_0x468e31?.[_0x35d9f2(0x312)])return isNotNull(_0x349396);if(_0x468e31?.[_0x35d9f2(0x3a1)])return;return isNull(_0x349396);}function mergeWhere(_0x599b91,_0x296b65){if(_0x599b91&&_0x296b65)return _0x124388(_0x296b65,_0x599b91);return _0x599b91??_0x296b65;}function applyJoins(_0x5eb718,_0x2e1781,_0x4d24fd){const _0xb2620f=_0x4727c2;let _0x58d6aa=_0x5eb718;for(const _0x4e52b1 of _0x4d24fd['join']??[]){const _0x4add93=_0x4e52b1[_0xb2620f(0x2d9)],_0x2c9e84=_0x4e52b1['on'](_0x2e1781),_0x3942d0=_0x4e52b1[_0xb2620f(0x381)]??_0xb2620f(0x38a);_0x3942d0===_0xb2620f(0x2b4)||_0x3942d0==='join'?_0x58d6aa=_0x58d6aa[_0xb2620f(0x2b4)](_0x4add93,_0x2c9e84):_0x58d6aa=_0x58d6aa[_0xb2620f(0x38a)](_0x4add93,_0x2c9e84);}return _0x58d6aa;}function resolveSelect(_0x2e8f37,_0x2e3310){const _0xb8c31d=_0x4727c2;if(_0x2e3310['select'])return _0x2e3310[_0xb8c31d(0x31d)];return getTableColumns(_0x2e8f37);}function countExpr(_0x586e6b,_0x13388e){const _0x73bb5d=_0x586e6b['id'];if(_0x73bb5d!=null&&_0x13388e)return countDistinct(_0x73bb5d);if(_0x73bb5d!=null)return count(_0x73bb5d);return count(_0x2cd2ac`*`);}async function queryWithOp(_0x317a19,_0x37532b,_0x59b05d,_0x5638a4){const _0x47b07e=_0x4727c2,_0x512b13=await buildQueryOp(_0x317a19,_0x37532b,_0x59b05d,_0x5638a4['request']),_0x201c70=trashClause(_0x317a19,_0x5638a4[_0x47b07e(0x28d)]),_0x407515=applyRowScopes(_0x317a19,mergeWhere(_0x512b13['where'],_0x201c70)),_0x55bb13=resolveSelect(_0x317a19,_0x59b05d),_0x5bfd8b=!!_0x59b05d[_0x47b07e(0x249)]?.[_0x47b07e(0x202)],_0x16e87f=Ioc[_0x47b07e(0x389)](DbStore)['drizzle'];let _0x379687=applyJoins(_0x16e87f[_0x47b07e(0x31d)](_0x55bb13)[_0x47b07e(0x27a)](_0x317a19),_0x317a19,_0x59b05d);if(_0x407515)_0x379687=_0x379687[_0x47b07e(0x2d6)](_0x407515);if(_0x512b13[_0x47b07e(0x392)][_0x47b07e(0x202)])_0x379687=_0x379687[_0x47b07e(0x1f9)](..._0x512b13['orderBySql']);if(_0x5638a4[_0x47b07e(0x311)]===_0x47b07e(0x324))return await _0x379687;const _0x22a3a7=Math[_0x47b07e(0x272)](0x1,Number(_0x37532b['page']??0x1)),_0x42806f=Math[_0x47b07e(0x344)](0x64,Math[_0x47b07e(0x272)](0x1,Number(_0x37532b['size']??0x14))),_0x31490f=(_0x22a3a7-0x1)*_0x42806f,_0x1c6db0=await _0x379687[_0x47b07e(0x21f)](_0x42806f)[_0x47b07e(0x39d)](_0x31490f);let _0x33b81e=applyJoins(_0x16e87f['select']({'value':countExpr(_0x317a19,_0x5bfd8b)})[_0x47b07e(0x27a)](_0x317a19),_0x317a19,_0x59b05d);if(_0x407515)_0x33b81e=_0x33b81e['where'](_0x407515);const _0x5bd108=await _0x33b81e,_0x28b960=Number(_0x5bd108[0x0]?.['value']??0x0);return{'list':_0x1c6db0,'pagination':{'page':_0x22a3a7,'size':_0x42806f,'total':_0x28b960}};}import{and as _0x2d4390,count as _0x562431,eq as _0xbb5626,inArray as _0x25d194,isNotNull as _0x238ed1,isNull as _0x202255}from'drizzle-orm';import{createInsertSchema,createSelectSchema,createUpdateSchema}from'drizzle-zod';function entitySchemas(_0x29706b){return{'select':createSelectSchema(_0x29706b),'insert':createInsertSchema(_0x29706b),'update':createUpdateSchema(_0x29706b)};}var WRITE_META_KEYS=['createTime',_0x4727c2(0x1ff),_0x4727c2(0x320)];function sanitizeWritePayload(_0x380096){const _0x4c9175=_0x4727c2,_0x3123be=_0x380096&&typeof _0x380096===_0x4c9175(0x310)&&!Array[_0x4c9175(0x327)](_0x380096)?{..._0x380096}:{};for(const _0x24ac74 of WRITE_META_KEYS)delete _0x3123be[_0x24ac74];for(const [_0x5b099e,_0x479ff6]of Object[_0x4c9175(0x3b8)](_0x3123be)){if(typeof _0x479ff6!==_0x4c9175(0x256))continue;if(!/^\d{4}-\d{2}-\d{2}/[_0x4c9175(0x298)](_0x479ff6))continue;const _0xcbf8ec=new Date(_0x479ff6);if(!Number[_0x4c9175(0x342)](_0xcbf8ec['getTime']()))_0x3123be[_0x5b099e]=_0xcbf8ec;}return _0x3123be;}function isSqlLike(_0x5d6d66){const _0x1cd5cd=_0x4727c2;return!!_0x5d6d66&&typeof _0x5d6d66===_0x1cd5cd(0x310)&&_0x5d6d66[_0x1cd5cd(0x364)]!=null;}function db(){const _0xa26695=_0x4727c2;return Ioc[_0xa26695(0x389)](DbStore)[_0xa26695(0x2f9)];}function tableId(_0x5975d7){const _0x1e9987=_0x5975d7['id'];if(!_0x1e9987)throw new Error('[Repository]\x20\u8868\u65E0\x20id\x20\u5217\uFF0C\u8BF7\u6539\u7528\x20find(where)\x20/\x20findOne(where)');return _0x1e9987;}function deletedAtColumn2(_0x348ea6){const _0x21e606=_0x4727c2;return _0x348ea6[_0x21e606(0x320)];}function mergeWhere2(_0xfcfb8d,_0x32a169){if(_0xfcfb8d&&_0x32a169)return _0x2d4390(_0x32a169,_0xfcfb8d);return _0xfcfb8d??_0x32a169;}function trashClause2(_0x5e4007,_0x1e9657){const _0x350865=_0x4727c2;if(!resolveSoftDelete(_0x1e9657?.[_0x350865(0x2c6)]))return;const _0x359373=deletedAtColumn2(_0x5e4007);if(_0x359373==null)return;if(_0x1e9657?.[_0x350865(0x312)])return _0x238ed1(_0x359373);if(_0x1e9657?.[_0x350865(0x3a1)])return;return _0x202255(_0x359373);}class Repository{[_0x4727c2(0x2d9)];[_0x4727c2(0x250)];constructor(_0x319507,_0x4f6e4b){const _0x223783=_0x4727c2;this['table']=_0x319507,this[_0x223783(0x250)]=_0x4f6e4b??entitySchemas(_0x319507);}[_0x4727c2(0x3a0)](){const _0x5ca444=_0x4727c2;return deletedAtColumn2(this[_0x5ca444(0x2d9)])!=null;}[_0x4727c2(0x339)](_0x4820cc,_0x2c8d9d){const _0x450ae0=_0x4727c2;return applyRowScopes(this[_0x450ae0(0x2d9)],mergeWhere2(_0x4820cc,trashClause2(this[_0x450ae0(0x2d9)],_0x2c8d9d)));}async[_0x4727c2(0x217)](_0x159998,_0x5679f0){const _0x54be0f=_0x4727c2,_0x11b867=this['scopedWhere'](_0x159998,_0x5679f0);let _0x6eea8c=db()[_0x54be0f(0x31d)]()[_0x54be0f(0x27a)](this['table']);if(_0x11b867)_0x6eea8c=_0x6eea8c[_0x54be0f(0x2d6)](_0x11b867);if(_0x5679f0?.[_0x54be0f(0x1f9)]?.[_0x54be0f(0x202)])_0x6eea8c=_0x6eea8c[_0x54be0f(0x1f9)](..._0x5679f0[_0x54be0f(0x1f9)]);return await _0x6eea8c;}async[_0x4727c2(0x229)](_0x3166b3,_0x373598){const _0x5b3b3f=_0x4727c2,[_0x495b50]=await this[_0x5b3b3f(0x217)](_0x3166b3,_0x373598);return _0x495b50;}async['findById'](_0x1d591e,_0x360e0c){const _0x21470c=_0x4727c2;return this['findOne'](_0xbb5626(tableId(this[_0x21470c(0x2d9)]),_0x1d591e),_0x360e0c);}async[_0x4727c2(0x3c1)](_0x412709,_0x4e806d){const _0x3e6950=_0x4727c2,_0xc432a3=this[_0x3e6950(0x339)](_0x412709,_0x4e806d),_0x12e059=db()['select']({'value':_0x562431()})[_0x3e6950(0x27a)](this[_0x3e6950(0x2d9)]),_0x17bed7=_0xc432a3?await _0x12e059[_0x3e6950(0x2d6)](_0xc432a3):await _0x12e059;return Number(_0x17bed7[0x0]?.[_0x3e6950(0x261)]??0x0);}async[_0x4727c2(0x238)](_0x2cfa39){const _0x4a1cfb=_0x4727c2,{page:_0x294ecc,size:_0x52922e,where:_0x2fb275,orderBy:_0x54c299,withTrashed:_0xa6bb3d,onlyTrashed:_0x3b3c1d,softDelete:_0x17c2bf}=_0x2cfa39,_0x2255a9={'withTrashed':_0xa6bb3d,'onlyTrashed':_0x3b3c1d,'softDelete':_0x17c2bf},_0x31d6a6=this[_0x4a1cfb(0x339)](_0x2fb275,_0x2255a9),_0x7c1235=(_0x294ecc-0x1)*_0x52922e;let _0x322647=db()['select']()['from'](this['table']);if(_0x31d6a6)_0x322647=_0x322647['where'](_0x31d6a6);if(_0x54c299?.[_0x4a1cfb(0x202)])_0x322647=_0x322647[_0x4a1cfb(0x1f9)](..._0x54c299);const _0x1f1395=await _0x322647[_0x4a1cfb(0x21f)](_0x52922e)['offset'](_0x7c1235),_0x1e0fd4=await this[_0x4a1cfb(0x3c1)](_0x2fb275,_0x2255a9);return{'list':_0x1f1395,'pagination':{'page':_0x294ecc,'size':_0x52922e,'total':_0x1e0fd4}};}[_0x4727c2(0x336)](_0x1b0e6b){const _0x1c760d=_0x4727c2,_0x225fb0=stampTenantId(this[_0x1c760d(0x2d9)],sanitizeWritePayload(_0x1b0e6b));return this[_0x1c760d(0x250)][_0x1c760d(0x351)][_0x1c760d(0x2e9)](_0x225fb0);}async['create'](_0x415bc5){const _0xe1ab74=_0x4727c2;if(Array[_0xe1ab74(0x327)](_0x415bc5)){if(!_0x415bc5[_0xe1ab74(0x202)])return[];const _0x39278a=_0x415bc5[_0xe1ab74(0x38c)](_0x251978=>this[_0xe1ab74(0x336)](_0x251978));return await db()[_0xe1ab74(0x351)](this[_0xe1ab74(0x2d9)])['values'](_0x39278a)['returning']();}const [_0x29b0ed]=await db()[_0xe1ab74(0x351)](this[_0xe1ab74(0x2d9)])['values'](this['parseInsert'](_0x415bc5))[_0xe1ab74(0x206)]();return _0x29b0ed;}async[_0x4727c2(0x363)](_0x16a10e){const _0x2bc93a=_0x4727c2;if(Array[_0x2bc93a(0x327)](_0x16a10e)){if(!_0x16a10e[_0x2bc93a(0x202)])return[];const _0x512a06=_0x16a10e,_0x1e279e=tableId(this[_0x2bc93a(0x2d9)]),_0x5e6ea1=_0x512a06['filter'](_0x33191f=>_0x33191f?.['id']!=null&&_0x33191f['id']!==''),_0x4458b3=_0x512a06[_0x2bc93a(0x2e3)](_0x1637ca=>_0x1637ca?.['id']==null||_0x1637ca['id']==='');let _0x5c1459=new Set();if(_0x5e6ea1[_0x2bc93a(0x202)]){const _0x3be584=await this[_0x2bc93a(0x217)](_0x25d194(_0x1e279e,_0x5e6ea1[_0x2bc93a(0x38c)](_0x2fb258=>_0x2fb258['id'])));_0x5c1459=new Set(_0x3be584['map'](_0x4a9321=>_0x4a9321['id']));}const _0x142404=[],_0x4ab105=[..._0x4458b3];for(const _0x1bdfce of _0x5e6ea1){if(_0x5c1459[_0x2bc93a(0x211)](_0x1bdfce['id']))_0x142404['push'](_0x1bdfce);else _0x4ab105[_0x2bc93a(0x2dc)](_0x1bdfce);}const _0x26cad8=_0x142404[_0x2bc93a(0x202)]?await this['update'](_0x142404):[],_0x330467=_0x4ab105[_0x2bc93a(0x202)]?await this[_0x2bc93a(0x1da)](_0x4ab105):[];return[...Array['isArray'](_0x26cad8)?_0x26cad8:_0x26cad8?[_0x26cad8]:[],...Array[_0x2bc93a(0x327)](_0x330467)?_0x330467:_0x330467?[_0x330467]:[]];}const _0x59b286=_0x16a10e,_0x447e6a=_0x59b286?.['id'];if(_0x447e6a!=null&&_0x447e6a!==''){const _0x3b79a7=await this[_0x2bc93a(0x1fe)](_0x447e6a);if(_0x3b79a7){const {id:_0x12d041,..._0xa55fa}=_0x59b286,_0x3b7784=await this[_0x2bc93a(0x282)](_0xbb5626(tableId(this[_0x2bc93a(0x2d9)]),_0x447e6a),_0xa55fa);return _0x3b7784??_0x3b79a7;}}return await this[_0x2bc93a(0x1da)](_0x16a10e);}async[_0x4727c2(0x282)](_0xfa45d9,_0x5aac08){const _0x22a7ad=_0x4727c2;if(Array[_0x22a7ad(0x327)](_0xfa45d9))return this[_0x22a7ad(0x281)](_0xfa45d9);const _0x21fe48=this[_0x22a7ad(0x250)][_0x22a7ad(0x282)]['parse'](sanitizeWritePayload(_0x5aac08)),_0x2800da=applyRowScopes(this['table'],_0xfa45d9);if(!_0x2800da)return;const [_0x3f2e9f]=await db()[_0x22a7ad(0x282)](this[_0x22a7ad(0x2d9)])[_0x22a7ad(0x2fc)](_0x21fe48)['where'](_0x2800da)['returning']();return _0x3f2e9f;}async[_0x4727c2(0x281)](_0x1fa29f){const _0x27e5d3=_0x4727c2;if(!_0x1fa29f[_0x27e5d3(0x202)])return[];const _0x2fc165=tableId(this[_0x27e5d3(0x2d9)]),_0x50d621=new Map();for(const _0x28b713 of _0x1fa29f){const _0xc1b763=_0x28b713['id'];if(_0xc1b763==null||_0xc1b763==='')throw new Error(_0x27e5d3(0x2c9));const {id:_0x125c02,..._0x19f8a3}=_0x28b713,_0x25871c=this[_0x27e5d3(0x250)][_0x27e5d3(0x282)][_0x27e5d3(0x2e9)](sanitizeWritePayload(_0x19f8a3)),_0x5c4982=JSON['stringify'](_0x25871c),_0x3bdeba=_0x50d621['get'](_0x5c4982);if(_0x3bdeba)_0x3bdeba[_0x27e5d3(0x35f)]['push'](_0xc1b763);else _0x50d621['set'](_0x5c4982,{'ids':[_0xc1b763],'patch':_0x25871c});}const _0x3292a1=[];for(const {ids:_0x587ca3,patch:_0x47f920}of _0x50d621[_0x27e5d3(0x319)]()){const _0x33e3fe=applyRowScopes(this[_0x27e5d3(0x2d9)],_0x25d194(_0x2fc165,_0x587ca3));if(!_0x33e3fe)continue;const _0x47374c=await db()[_0x27e5d3(0x282)](this['table'])[_0x27e5d3(0x2fc)](_0x47f920)[_0x27e5d3(0x2d6)](_0x33e3fe)[_0x27e5d3(0x206)]();_0x3292a1[_0x27e5d3(0x2dc)](..._0x47374c);}return _0x3292a1;}[_0x4727c2(0x306)](_0x1e1933){const _0x3224df=_0x4727c2;if(isSqlLike(_0x1e1933))return applyRowScopes(this['table'],_0x1e1933);const _0x5659b8=Array[_0x3224df(0x327)](_0x1e1933)?_0x1e1933:[_0x1e1933];if(!_0x5659b8[_0x3224df(0x202)])return;return applyRowScopes(this[_0x3224df(0x2d9)],_0x25d194(tableId(this[_0x3224df(0x2d9)]),_0x5659b8));}async[_0x4727c2(0x2c6)](_0x5bcbac){const _0x16b189=_0x4727c2;if(!this[_0x16b189(0x3a0)]())throw new Error(_0x16b189(0x221));const _0x489e9d=this[_0x16b189(0x306)](_0x5bcbac);if(!_0x489e9d)return;await db()[_0x16b189(0x282)](this[_0x16b189(0x2d9)])[_0x16b189(0x2fc)]({'deletedAt':new Date()})[_0x16b189(0x2d6)](_0x489e9d);}async[_0x4727c2(0x26c)](_0xfc1083){const _0x5e0d50=_0x4727c2;if(!this[_0x5e0d50(0x3a0)]())throw new Error(_0x5e0d50(0x30e));const _0x568abe=this[_0x5e0d50(0x306)](_0xfc1083);if(!_0x568abe)return;await db()[_0x5e0d50(0x282)](this[_0x5e0d50(0x2d9)])[_0x5e0d50(0x2fc)]({'deletedAt':null})[_0x5e0d50(0x2d6)](_0x568abe);}async[_0x4727c2(0x2b1)](_0xdbf919){const _0x20ff4c=_0x4727c2,_0x4488d0=this['resolveIdWhere'](_0xdbf919);if(!_0x4488d0)return;await db()[_0x20ff4c(0x232)](this[_0x20ff4c(0x2d9)])['where'](_0x4488d0);}}var repoCache=new WeakMap();function getRepository(_0x49c2b5){const _0x29153f=_0x4727c2,_0x19c413=repoCache[_0x29153f(0x389)](_0x49c2b5);if(_0x19c413)return _0x19c413;const _0xf4beca=new Repository(_0x49c2b5);return repoCache['set'](_0x49c2b5,_0xf4beca),_0xf4beca;}function InjectRepository(_0x246e66){return(_0x5e7214,_0xcdc27d)=>{const _0x3cc9a3=_0x1a3d;appendInjectMeta(_0x5e7214[_0x3cc9a3(0x1e4)],{'propertyKey':_0xcdc27d,'resolve':()=>getRepository(_0x246e66)});};}function isSql(_0x367c63){const _0x20a782=_0x4727c2;return!!_0x367c63&&typeof _0x367c63==='object'&&_0x367c63[_0x20a782(0x364)]!=null;}class BaseService{['entity'];[_0x4727c2(0x248)](_0x4a1fbd){const _0x142255=_0x4727c2;if(!this[_0x142255(0x254)])this[_0x142255(0x254)]=_0x4a1fbd;}[_0x4727c2(0x1ea)](_0x140ab0){this['entity']=_0x140ab0;}[_0x4727c2(0x338)](){return!!this['entity'];}[_0x4727c2(0x2ee)](){const _0x24eb1c=_0x4727c2;return this[_0x24eb1c(0x301)]();}[_0x4727c2(0x301)](){const _0x378460=_0x4727c2;if(!this['entity'])throw new Error(_0x378460(0x27c));return this[_0x378460(0x254)];}async[_0x4727c2(0x3b3)](_0x1e5343,_0x55d7aa){}async['modifyAfter'](_0x3c1116,_0x14ce02){}async[_0x4727c2(0x213)](_0xef1894,_0x50d847){const _0x2b5efa=_0x4727c2,_0x45d24a=resolveUpsert(_0x50d847?.[_0x2b5efa(0x284)]),_0x5a80a0=Array['isArray'](_0xef1894)?_0xef1894[_0x2b5efa(0x38c)](_0x518d3e=>_0x518d3e!=null&&typeof _0x518d3e==='object'?{..._0x518d3e}:_0x518d3e):_0xef1894!=null&&typeof _0xef1894===_0x2b5efa(0x310)?{..._0xef1894}:_0xef1894;await this[_0x2b5efa(0x3b3)](_0x5a80a0,_0x2b5efa(0x213));const _0x83946a=_0x45d24a===_0x2b5efa(0x363)?await this[_0x2b5efa(0x301)]()[_0x2b5efa(0x363)](_0x5a80a0):await this[_0x2b5efa(0x301)]()[_0x2b5efa(0x1da)](_0x5a80a0);return await this[_0x2b5efa(0x3a7)](_0x83946a??_0x5a80a0,_0x2b5efa(0x213)),_0x83946a;}async[_0x4727c2(0x282)](_0x492cb0,_0x3f3fe0){const _0x52a985=_0x4727c2;if(Array[_0x52a985(0x327)](_0x492cb0)){const _0x11550a=_0x492cb0['map'](_0x183d72=>({..._0x183d72}));await this[_0x52a985(0x3b3)](_0x11550a,'update');const _0x4358b8=await this[_0x52a985(0x301)]()[_0x52a985(0x282)](_0x11550a);return await this['modifyAfter'](_0x4358b8??_0x11550a,_0x52a985(0x282)),_0x4358b8;}if(isSql(_0x492cb0)){const _0x3b3efe=_0x3f3fe0!=null&&typeof _0x3f3fe0==='object'?{..._0x3f3fe0}:_0x3f3fe0;await this[_0x52a985(0x3b3)](_0x3b3efe,'update');const _0x411c86=await this['requireEntity']()[_0x52a985(0x282)](_0x492cb0,_0x3b3efe);return await this[_0x52a985(0x3a7)](_0x411c86??_0x3b3efe,_0x52a985(0x282)),_0x411c86;}const _0x4a04c3={..._0x492cb0};await this[_0x52a985(0x3b3)](_0x4a04c3,'update');const _0x2489aa=await this[_0x52a985(0x301)]()[_0x52a985(0x282)]([_0x4a04c3]);return await this['modifyAfter'](_0x2489aa??_0x4a04c3,_0x52a985(0x282)),Array[_0x52a985(0x327)](_0x2489aa)?_0x2489aa[0x0]:_0x2489aa;}async['delete'](_0x1e6860,_0x2922e){const _0x304432=_0x4727c2,_0x2bad7e=this['requireEntity']();await this[_0x304432(0x3b3)](_0x1e6860,'delete');const _0x5e9a63=resolveSoftDelete(_0x2922e?.[_0x304432(0x2c6)]);_0x2922e?.[_0x304432(0x387)]||!_0x5e9a63||!_0x2bad7e[_0x304432(0x3a0)]()?await _0x2bad7e['forceDelete'](_0x1e6860):await _0x2bad7e[_0x304432(0x2c6)](_0x1e6860),await this[_0x304432(0x3a7)](_0x1e6860,_0x304432(0x232));}[_0x4727c2(0x26c)](_0x2c5b7a){return this['requireEntity']()['restore'](_0x2c5b7a);}[_0x4727c2(0x324)](_0x31dd37,_0x335e1e){const _0x2a755f=_0x4727c2;return this[_0x2a755f(0x301)]()[_0x2a755f(0x217)](_0x31dd37,_0x335e1e);}[_0x4727c2(0x304)](_0x10cb96,_0x522d48){const _0x3dc9ac=_0x4727c2,_0x4a1e1e=this[_0x3dc9ac(0x301)]();if(typeof _0x10cb96===_0x3dc9ac(0x310))return _0x4a1e1e[_0x3dc9ac(0x229)](_0x10cb96,_0x522d48);return _0x4a1e1e[_0x3dc9ac(0x1fe)](_0x10cb96,_0x522d48);}[_0x4727c2(0x3af)](_0xdd6a34={}){const _0x3ccc0c=_0x4727c2,_0x5d66a9=Math['max'](0x1,_0xdd6a34[_0x3ccc0c(0x3af)]??0x1),_0x21a4ee=Math[_0x3ccc0c(0x344)](0x64,Math['max'](0x1,_0xdd6a34[_0x3ccc0c(0x2aa)]??0x14));return this[_0x3ccc0c(0x301)]()[_0x3ccc0c(0x238)]({'page':_0x5d66a9,'size':_0x21a4ee,'where':_0xdd6a34[_0x3ccc0c(0x2d6)],'orderBy':_0xdd6a34[_0x3ccc0c(0x1f9)],'withTrashed':_0xdd6a34['withTrashed'],'onlyTrashed':_0xdd6a34[_0x3ccc0c(0x312)],'softDelete':_0xdd6a34[_0x3ccc0c(0x2c6)]});}}var CRUD_SUMMARY={'add':'\u65B0\u589E','delete':'\u5220\u9664','update':'\u4FEE\u6539','info':_0x4727c2(0x34f),'list':_0x4727c2(0x29d),'page':_0x4727c2(0x329),'restore':'\u6062\u590D'},CRUD_APIS=['add',_0x4727c2(0x232),_0x4727c2(0x282),_0x4727c2(0x304),_0x4727c2(0x324),_0x4727c2(0x3af),_0x4727c2(0x26c)],BEFORE_APIS=new Set([_0x4727c2(0x213),_0x4727c2(0x282),_0x4727c2(0x232),_0x4727c2(0x26c)]);function omitProps(_0x396026,_0x225886){const _0x2cf16d=_0x4727c2;if(!_0x396026||!_0x225886?.[_0x2cf16d(0x202)])return _0x396026;const _0x343674={..._0x396026};for(const _0x5972b8 of _0x225886)delete _0x343674[_0x5972b8];return _0x343674;}function resolveIds(_0x5c1ec5){const _0xa7aafe=_0x4727c2;if(Array[_0xa7aafe(0x327)](_0x5c1ec5))return _0x5c1ec5[_0xa7aafe(0x38c)](_0x3a9298=>{if(_0x3a9298!=null&&typeof _0x3a9298==='object'&&'id'in _0x3a9298)return _0x3a9298['id'];return _0x3a9298;});if(_0x5c1ec5&&typeof _0x5c1ec5===_0xa7aafe(0x310)){const _0x44fff7=_0x5c1ec5;if(Array['isArray'](_0x44fff7['ids']))return _0x44fff7[_0xa7aafe(0x35f)];if(_0x44fff7['id']!=null)return[_0x44fff7['id']];}return[];}function resolveService(_0x325700){const _0x5d9d73=_0x4727c2,_0x25cf4b=_0x325700[_0x5d9d73(0x391)],_0x2ee69e=_0x25cf4b['entity'];if(_0x25cf4b[_0x5d9d73(0x219)]){const _0x559010=Ioc[_0x5d9d73(0x389)](_0x25cf4b['service']);if(_0x2ee69e&&!_0x559010['hasEntity']())_0x559010[_0x5d9d73(0x1ea)](getRepository(_0x2ee69e));return _0x559010;}if(!_0x2ee69e)throw new Error(_0x5d9d73(0x2be)+_0x325700[_0x5d9d73(0x341)]['name']+_0x5d9d73(0x2c7));const _0x83a19=new class extends BaseService{}();return _0x83a19[_0x5d9d73(0x1ea)](getRepository(_0x2ee69e)),_0x83a19;}function tableOf(_0x324e74,_0x2999b9){const _0x2d5b59=_0x4727c2,_0x52f6ed=_0x2999b9[_0x2d5b59(0x391)]?.[_0x2d5b59(0x254)];if(_0x52f6ed)return _0x52f6ed;return _0x324e74['getRepo']()['table'];}var attachCrudRoutes=(_0x4866be,_0x209ca6,_0x21839a)=>{const _0x2eb502=_0x4727c2,_0x2d3c0a=_0x209ca6[_0x2eb502(0x391)];if(!_0x2d3c0a)return _0x4866be;const _0xc78748=(_0x2d3c0a[_0x2eb502(0x22b)]??[])['filter'](_0x56c3df=>CRUD_APIS['includes'](_0x56c3df)),_0x1437f5=_0x2d3c0a[_0x2eb502(0x30b)]??[];if(!_0xc78748['length']&&!_0x1437f5['length'])return _0x4866be;const _0xf428a2=_0x21839a[_0x2eb502(0x1f1)]instanceof BaseController?_0x21839a[_0x2eb502(0x1f1)]:new BaseController(),_0x3de5a8=_0xc78748[_0x2eb502(0x202)]>0x0,_0x5b57d2=_0x3de5a8||_0x2d3c0a[_0x2eb502(0x219)]?resolveService(_0x209ca6):undefined,_0x116510=_0x3de5a8&&_0x5b57d2?tableOf(_0x5b57d2,_0x209ca6):undefined,_0x3e2af3=_0x116510?_0x116510['id']:undefined;if(_0x3de5a8&&_0x3e2af3==null)throw new Error(_0x2eb502(0x2be)+_0x209ca6[_0x2eb502(0x341)][_0x2eb502(0x27e)]+_0x2eb502(0x227));let _0x46b8cd=_0x4866be;const _0x5842ef=(_0xcbe487,_0x1f1ccf,_0x3209e6,_0x520625)=>{const _0x4092c6=_0x2eb502;_0x46b8cd=_0x46b8cd[_0xcbe487](_0x1f1ccf,_0x520625,_0x21839a[_0x4092c6(0x33c)]({'action':_0x3209e6,'summary':CRUD_SUMMARY[_0x3209e6]}));},_0x55cdb5=async(_0x34d575,_0x2173be,_0x31935c)=>{const _0x175876=_0x2eb502;if(!_0x2d3c0a[_0x175876(0x349)]||!BEFORE_APIS['has'](_0x34d575))return _0x2173be;return await _0x2d3c0a['before']({'body':_0x2173be,'request':_0x31935c,'api':_0x34d575}),_0x2173be;};_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x213))&&_0x5b57d2&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x1ee),_0x2eb502(0x213),async({body:_0x28e97c,request:_0x45931d})=>{const _0xebe65f=_0x2eb502;try{const _0x310e02=_0x28e97c;if(Array[_0xebe65f(0x327)](_0x310e02)){let _0x46411a=_0x310e02;if(_0x2d3c0a[_0xebe65f(0x349)]&&BEFORE_APIS[_0xebe65f(0x211)](_0xebe65f(0x213)))for(let _0x4b3b22=0x0;_0x4b3b22<_0x46411a[_0xebe65f(0x202)];_0x4b3b22++){_0x46411a[_0x4b3b22]=await _0x55cdb5('add',{..._0x46411a[_0x4b3b22]??{}},_0x45931d);}if(_0x2d3c0a['insertParam']){const _0x5ab1d4=await _0x2d3c0a[_0xebe65f(0x331)]({'body':_0x46411a[0x0]??{},'request':_0x45931d});_0x46411a=_0x46411a[_0xebe65f(0x38c)](_0x224810=>({..._0x224810,..._0x5ab1d4}));}const _0x2f91df=await _0x5b57d2['add'](_0x46411a);return _0xf428a2['ok'](_0x2f91df);}let _0x393e8e={..._0x310e02??{}};_0x393e8e=await _0x55cdb5(_0xebe65f(0x213),_0x393e8e,_0x45931d);_0x2d3c0a['insertParam']&&Object[_0xebe65f(0x39e)](_0x393e8e,await _0x2d3c0a[_0xebe65f(0x331)]({'body':_0x393e8e,'request':_0x45931d}));const _0x2e92bb=await _0x5b57d2[_0xebe65f(0x213)](_0x393e8e);return _0xf428a2['ok'](_0x2e92bb);}catch(_0x50253f){return _0xf428a2[_0xebe65f(0x325)](_0x50253f instanceof Error?_0x50253f[_0xebe65f(0x318)]:_0xebe65f(0x215));}});_0xc78748[_0x2eb502(0x395)]('delete')&&_0x5b57d2&&_0x3e2af3&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x2db),_0x2eb502(0x232),async({body:_0x159934,request:_0x2ae207})=>{const _0x182340=_0x2eb502;try{const _0x2109f1=_0x159934,_0x2923dc=Array[_0x182340(0x327)](_0x2109f1)?_0x2109f1:await _0x55cdb5(_0x182340(0x232),{..._0x2109f1??{}},_0x2ae207),_0x2f409d=resolveIds(_0x2923dc);if(!_0x2f409d[_0x182340(0x202)])return _0xf428a2[_0x182340(0x325)](_0x182340(0x34a));const _0x1bee41=!Array['isArray'](_0x2923dc)&&!!_0x2923dc[_0x182340(0x387)];return await _0x5b57d2['delete'](_0x2f409d,{'force':_0x1bee41}),_0xf428a2['ok']();}catch(_0x10e028){return _0xf428a2['fail'](_0x10e028 instanceof Error?_0x10e028[_0x182340(0x318)]:_0x182340(0x3b7));}});_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x282))&&_0x5b57d2&&_0x3e2af3&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x333),_0x2eb502(0x282),async({body:_0x2ef9a9,request:_0x4df1be})=>{const _0x5a00aa=_0x2eb502;try{const _0x3074bd=_0x2ef9a9;if(Array[_0x5a00aa(0x327)](_0x3074bd)){let _0x568a04=_0x3074bd;if(_0x2d3c0a[_0x5a00aa(0x349)]&&BEFORE_APIS['has'](_0x5a00aa(0x282)))for(let _0x5b13d0=0x0;_0x5b13d0<_0x568a04['length'];_0x5b13d0++){_0x568a04[_0x5b13d0]=await _0x55cdb5(_0x5a00aa(0x282),{..._0x568a04[_0x5b13d0]??{}},_0x4df1be);}const _0x113728=await _0x5b57d2[_0x5a00aa(0x282)](_0x568a04);return _0xf428a2['ok'](_0x113728);}const _0x773808=await _0x55cdb5('update',{..._0x3074bd??{}},_0x4df1be),_0x145411=_0x773808['id'];if(_0x145411==null)return _0xf428a2[_0x5a00aa(0x325)](_0x5a00aa(0x2a2));const _0x144acd=await _0x5b57d2[_0x5a00aa(0x282)](_0x773808);return _0xf428a2['ok'](_0x144acd);}catch(_0x330268){return _0xf428a2[_0x5a00aa(0x325)](_0x330268 instanceof Error?_0x330268[_0x5a00aa(0x318)]:_0x5a00aa(0x257));}});_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x304))&&_0x5b57d2&&_0x5842ef(_0x2eb502(0x389),_0x2eb502(0x38f),'info',async({query:_0x26a736})=>{const _0x188102=_0x2eb502;try{const _0x303803=_0x26a736?.['id'];if(_0x303803==null||_0x303803==='')return _0xf428a2[_0x188102(0x325)](_0x188102(0x2a2));const _0x208640=await _0x5b57d2[_0x188102(0x304)](_0x303803);return _0xf428a2['ok'](omitProps(_0x208640,_0x2d3c0a[_0x188102(0x32f)]));}catch(_0x59433e){return _0xf428a2[_0x188102(0x325)](_0x59433e instanceof Error?_0x59433e[_0x188102(0x318)]:_0x188102(0x1dc));}});_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x324))&&_0x5b57d2&&_0x116510&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x394),_0x2eb502(0x324),async({body:_0x463754,request:_0x45c469})=>{const _0x1569ff=_0x2eb502;try{const _0x27a15e=_0x463754??{},_0x5aeccf=_0x2d3c0a[_0x1569ff(0x37b)]??{},_0x4eae20={'onlyTrashed':_0x27a15e[_0x1569ff(0x312)]===!![],'withTrashed':_0x27a15e[_0x1569ff(0x3a1)]===!![]};if(needsAdvancedQuery(_0x5aeccf)){const _0x579541=await queryWithOp(_0x116510,_0x27a15e,_0x5aeccf,{'request':_0x45c469,'mode':'list','trash':_0x4eae20});return _0xf428a2['ok'](_0x579541);}const {where:_0x314cb3,orderBySql:_0x22494b}=await buildQueryOp(_0x116510,_0x27a15e,_0x5aeccf,_0x45c469),_0x1e7fa9=await _0x5b57d2['list'](_0x314cb3,{'orderBy':_0x22494b,..._0x4eae20});return _0xf428a2['ok'](_0x1e7fa9);}catch(_0x26e62c){return _0xf428a2[_0x1569ff(0x325)](_0x26e62c instanceof Error?_0x26e62c[_0x1569ff(0x318)]:_0x1569ff(0x31e));}});_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x3af))&&_0x5b57d2&&_0x116510&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x3ae),_0x2eb502(0x3af),async({body:_0x483eae,request:_0x3a7f96})=>{const _0x44b58d=_0x2eb502;try{const _0x58107a=_0x483eae??{},_0x297bc4=_0x2d3c0a[_0x44b58d(0x3a5)]??{},_0x509947={'onlyTrashed':_0x58107a[_0x44b58d(0x312)]===!![],'withTrashed':_0x58107a[_0x44b58d(0x3a1)]===!![]};if(needsAdvancedQuery(_0x297bc4)){const _0x4ce82e=await queryWithOp(_0x116510,_0x58107a,_0x297bc4,{'request':_0x3a7f96,'mode':_0x44b58d(0x3af),'trash':_0x509947});return _0xf428a2['ok'](_0x4ce82e);}const {where:_0x3447dc,orderBySql:_0xdb0670}=await buildQueryOp(_0x116510,_0x58107a,_0x297bc4,_0x3a7f96),_0x5b40c3=await _0x5b57d2[_0x44b58d(0x3af)]({'page':Number(_0x58107a[_0x44b58d(0x3af)]??0x1),'size':Number(_0x58107a[_0x44b58d(0x2aa)]??0x14),'where':_0x3447dc,'orderBy':_0xdb0670,..._0x509947});return _0xf428a2['ok'](_0x5b40c3);}catch(_0x2525a5){return _0xf428a2[_0x44b58d(0x325)](_0x2525a5 instanceof Error?_0x2525a5[_0x44b58d(0x318)]:_0x44b58d(0x30a));}});_0xc78748[_0x2eb502(0x395)](_0x2eb502(0x26c))&&_0x5b57d2&&_0x3e2af3&&_0x5842ef(_0x2eb502(0x21a),_0x2eb502(0x3ab),_0x2eb502(0x26c),async({body:_0x1b747b,request:_0x335451})=>{const _0x3bb9a2=_0x2eb502;try{const _0x23a99b=_0x1b747b,_0x2e5629=Array[_0x3bb9a2(0x327)](_0x23a99b)?_0x23a99b:await _0x55cdb5(_0x3bb9a2(0x26c),{..._0x23a99b??{}},_0x335451),_0xe3460c=resolveIds(_0x2e5629);if(!_0xe3460c[_0x3bb9a2(0x202)])return _0xf428a2[_0x3bb9a2(0x325)](_0x3bb9a2(0x34a));return await _0x5b57d2[_0x3bb9a2(0x26c)](_0xe3460c),_0xf428a2['ok']();}catch(_0x528710){return _0xf428a2[_0x3bb9a2(0x325)](_0x528710 instanceof Error?_0x528710[_0x3bb9a2(0x318)]:_0x3bb9a2(0x340));}});if(_0x1437f5[_0x2eb502(0x202)]){if(!_0x2d3c0a[_0x2eb502(0x219)])throw new Error(_0x2eb502(0x2be)+_0x209ca6[_0x2eb502(0x341)]['name']+'\x20配置了\x20serviceApis,需同时配置\x20service');const _0x4c4e5a=Ioc[_0x2eb502(0x389)](_0x2d3c0a[_0x2eb502(0x219)]);for(const _0x4f0d42 of _0x1437f5){const _0x14d342=_0x4c4e5a[_0x4f0d42];if(typeof _0x14d342!==_0x2eb502(0x305))throw new Error(_0x2eb502(0x2be)+_0x2d3c0a[_0x2eb502(0x219)][_0x2eb502(0x27e)]+'.'+_0x4f0d42+_0x2eb502(0x239));const _0x1cab9d=_0x14d342[_0x2eb502(0x37c)](_0x4c4e5a);_0x5842ef('post','/'+_0x4f0d42,_0x4f0d42,async({body:_0x4e0902})=>{const _0x36ce50=_0x2eb502;try{const _0x183245=await _0x1cab9d(_0x4e0902);return _0xf428a2['ok'](_0x183245);}catch(_0x170c6a){return _0xf428a2[_0x36ce50(0x325)](_0x170c6a instanceof Error?_0x170c6a[_0x36ce50(0x318)]:_0x4f0d42+_0x36ce50(0x323));}});}}return _0x46b8cd;};import{join as _0x3b53a1}from'path';import{pathToFileURL as _0x402a87}from'url';var SERVICE_PATTERN=_0x4727c2(0x3bf),CONTROLLER_SCANS=[{'pattern':_0x4727c2(0x1fa),'side':'admin'},{'pattern':'**/modules/*/controller/app/**/*.ts','side':'app'}];async function importWithContext(_0x367b0d,_0x10d8ca,_0x207577){setControllerScanContext({'module':parseModuleFromPath(_0x10d8ca),'side':_0x207577,'file':_0x10d8ca});try{const _0x3629de=_0x402a87(_0x3b53a1(_0x367b0d,_0x10d8ca))['href'];await import(_0x3629de);}finally{setControllerScanContext(null);}}async function scanHost(){const _0x4b5f69=_0x4727c2,_0x25ea5b=process[_0x4b5f69(0x378)](),_0x32397a=await scanFiles(SERVICE_PATTERN,{'cwd':_0x25ea5b});for(const _0x50fe4c of _0x32397a){const _0x20101a=_0x402a87(_0x3b53a1(_0x25ea5b,_0x50fe4c))[_0x4b5f69(0x28c)];await import(_0x20101a);}let _0x537a15=0x0;for(const {pattern:_0x58a1e9,side:_0x382c5b}of CONTROLLER_SCANS){const _0x26d199=await scanFiles(_0x58a1e9,{'cwd':_0x25ea5b});_0x537a15+=_0x26d199[_0x4b5f69(0x202)];for(const _0x42b224 of _0x26d199){await importWithContext(_0x25ea5b,_0x42b224,_0x382c5b);}}setCrudRegistrar(attachCrudRoutes),console[_0x4b5f69(0x2e2)](_0x4b5f69(0x243)),console[_0x4b5f69(0x2e2)](_0x4b5f69(0x23c)+_0x32397a[_0x4b5f69(0x202)]+'\x20service,\x20'+_0x537a15+_0x4b5f69(0x24b));}import{join as _0x347a49}from'path';import{createPinoLogger}from'@bogeychan/elysia-logger';import _0x2b939e from'pino-pretty';import{createWriteStream,mkdirSync,readdirSync,unlinkSync}from'fs';import{join as _0x13f264}from'path';import{Writable}from'stream';var FILE_PATTERN=/^(\d{4}-\d{2}-\d{2})\.log$/;function formatLocalDate(_0x2eb670=new Date()){const _0x382bbd=_0x4727c2,_0x4d110f=_0x2eb670['getFullYear'](),_0x45fd3b=String(_0x2eb670[_0x382bbd(0x3be)]()+0x1)[_0x382bbd(0x22d)](0x2,'0'),_0x44f8f8=String(_0x2eb670[_0x382bbd(0x245)]())[_0x382bbd(0x22d)](0x2,'0');return _0x4d110f+'-'+_0x45fd3b+'-'+_0x44f8f8;}function purgeOldLogs(_0x33351d,_0x1fc90d){const _0x59ab58=_0x4727c2,_0xb915dc=new Date();_0xb915dc[_0x59ab58(0x2e8)](_0xb915dc[_0x59ab58(0x245)]()-_0x1fc90d);const _0x44972a=formatLocalDate(_0xb915dc);for(const _0x313c46 of readdirSync(_0x33351d)){const _0x58aac2=_0x313c46[_0x59ab58(0x393)](FILE_PATTERN);if(!_0x58aac2||_0x58aac2[0x1]>=_0x44972a)continue;unlinkSync(_0x13f264(_0x33351d,_0x313c46));}}function openDailyStream(_0xf761f8,_0x5a49a1){return createWriteStream(_0x13f264(_0xf761f8,_0x5a49a1+'.log'),{'flags':'a'});}function createDailyLogStream(_0x2d516d,_0x5b4a0b=0x1e){mkdirSync(_0x2d516d,{'recursive':!![]}),purgeOldLogs(_0x2d516d,_0x5b4a0b);let _0x442e47=formatLocalDate(),_0x47201c=openDailyStream(_0x2d516d,_0x442e47);return new Writable({'write'(_0x156c3a,_0x44fa72,_0x537ee4){const _0x21fb8e=_0x1a3d,_0x24fb3a=formatLocalDate();_0x24fb3a!==_0x442e47&&(_0x47201c[_0x21fb8e(0x1f6)](),_0x442e47=_0x24fb3a,_0x47201c=openDailyStream(_0x2d516d,_0x442e47),purgeOldLogs(_0x2d516d,_0x5b4a0b)),_0x47201c[_0x21fb8e(0x1f3)](_0x156c3a,_0x537ee4);},'final'(_0x23b3ef){const _0x34b799=_0x1a3d;_0x47201c[_0x34b799(0x1f6)](_0x23b3ef);}});}var pinoInstance;function buildPino(){const _0x290fb6=_0x4727c2,_0x56fc90=VomeConfig[_0x290fb6(0x25a)]??{},_0x253ebb=_0x56fc90[_0x290fb6(0x2f7)]??'info';if(_0x56fc90[_0x290fb6(0x32a)]===_0x290fb6(0x292)){const _0x491a84=_0x347a49(process[_0x290fb6(0x378)](),_0x56fc90[_0x290fb6(0x32e)]??'logging'),_0x170013=_0x56fc90[_0x290fb6(0x224)]??0x1e;return createPinoLogger({'level':_0x253ebb,'stream':createDailyLogStream(_0x491a84,_0x170013)});}return createPinoLogger({'level':_0x253ebb,'stream':_0x2b939e({'colorize':!![],'translateTime':'SYS:standard','ignore':_0x290fb6(0x24e)})});}function getPinoLogger(){if(!pinoInstance)pinoInstance=buildPino();return pinoInstance;}function resetPinoLogger(){pinoInstance=undefined;}class Logger{['info'](_0x27cd0b,..._0x7f29c1){const _0x31c9f5=_0x4727c2,_0x2416e2=getPinoLogger();if(_0x7f29c1[_0x31c9f5(0x202)])_0x2416e2[_0x31c9f5(0x304)]({'args':_0x7f29c1},_0x27cd0b);else _0x2416e2[_0x31c9f5(0x304)](_0x27cd0b);}[_0x4727c2(0x1f8)](_0x2fc7f0,..._0x4113fc){const _0xc135ea=_0x4727c2,_0x4a7dd7=getPinoLogger();if(_0x4113fc['length'])_0x4a7dd7[_0xc135ea(0x1f8)]({'args':_0x4113fc},_0x2fc7f0);else _0x4a7dd7[_0xc135ea(0x1f8)](_0x2fc7f0);}[_0x4727c2(0x236)](_0xdce0df,..._0x2e968d){const _0x3e9b00=_0x4727c2,_0x582695=getPinoLogger();if(_0x2e968d[_0x3e9b00(0x202)])_0x582695[_0x3e9b00(0x236)]({'args':_0x2e968d},_0xdce0df);else _0x582695[_0x3e9b00(0x236)](_0xdce0df);}[_0x4727c2(0x233)](_0x1be81f,..._0x5113d8){const _0x27c437=_0x4727c2,_0x28176a=getPinoLogger();if(_0x1be81f instanceof Error){_0x28176a[_0x27c437(0x233)](_0x1be81f);return;}if(_0x5113d8[0x0]instanceof Error){_0x28176a[_0x27c437(0x233)](_0x5113d8[0x0],_0x1be81f);return;}if(_0x5113d8[_0x27c437(0x202)])_0x28176a[_0x27c437(0x233)]({'args':_0x5113d8},_0x1be81f);else _0x28176a[_0x27c437(0x233)](_0x1be81f);}}class CommException extends Error{[_0x4727c2(0x350)];['code'];constructor(_0x5e8298,_0x2b4be3){const _0xe5afdf=_0x4727c2;super(_0x5e8298),this[_0xe5afdf(0x27e)]=_0xe5afdf(0x2ff),this['statusCode']=_0x2b4be3?.[_0xe5afdf(0x350)]??0xc8,this[_0xe5afdf(0x258)]=_0x2b4be3?.[_0xe5afdf(0x258)]??RES_CODE[_0xe5afdf(0x34c)];}}function isCommException(_0x1c80ca){return _0x1c80ca instanceof CommException;}function bootstrapLogger(){const _0xc08a92=_0x4727c2;getPinoLogger(),Ioc[_0xc08a92(0x2fc)](Logger,new Logger());}var VOME_BANNER=_0x4727c2(0x2e5);function resetViewport(){const _0x457ff5=_0x4727c2;if(!process[_0x457ff5(0x28f)]['isTTY'])return;process[_0x457ff5(0x28f)][_0x457ff5(0x1f3)](_0x457ff5(0x2dd));}function printStartupBanner(){const _0xe205b9=_0x4727c2;resetViewport();const _0x4e4030=getEnv(),_0xc93e53=VomeConfig[_0xe205b9(0x317)]?.[_0xe205b9(0x283)]??0xbb9,_0x3832ba=VomeConfig['openapi']?.['path']??'/docs',_0x349fa1=_0xe205b9(0x2a8)+_0xc93e53;console[_0xe205b9(0x2e2)](VOME_BANNER),console[_0xe205b9(0x2e2)]('🌍\x20运行环境:\x20'+_0x4e4030),_0x4e4030==='dev'&&(console[_0xe205b9(0x2e2)]('📡\x20服务地址:\x20'+_0x349fa1),console[_0xe205b9(0x2e2)](_0xe205b9(0x24f)+_0x349fa1+(_0x3832ba['startsWith']('/')?_0x3832ba:'/'+_0x3832ba)));}import{access}from'fs/promises';import{join as _0x9a0e10}from'path';import{pathToFileURL as _0x5afdc8}from'url';async function exists(_0x5b3690){try{return await access(_0x5b3690),!![];}catch{return![];}}async function importHostModule(_0x24b227){const _0x4995ba=_0x4727c2,_0x433d9d=_0x9a0e10(process[_0x4995ba(0x378)](),_0x24b227);if(!await exists(_0x433d9d)){console[_0x4995ba(0x1f8)](_0x4995ba(0x2ab)+_0x24b227);return;}return await import(_0x5afdc8(_0x433d9d)['href']);}async function bootstrapHostInfra(){const _0x3bdcc5=_0x4727c2,_0x4d864a=await importHostModule(_0x3bdcc5(0x300));if(_0x4d864a?.['Db']?.['bootstrap'])await _0x4d864a['Db']['bootstrap']();const _0x4790d5=await importHostModule(_0x3bdcc5(0x26e));if(_0x4790d5?.[_0x3bdcc5(0x315)]?.[_0x3bdcc5(0x382)])await _0x4790d5[_0x3bdcc5(0x315)][_0x3bdcc5(0x382)]();const _0x444c68=await importHostModule(_0x3bdcc5(0x2bb));if(_0x444c68?.['Auth']?.['bootstrap'])await _0x444c68['Auth'][_0x3bdcc5(0x382)]();}async function bootstrapHostTasks(){const _0x35a81d=_0x4727c2,_0x12c021=await importHostModule(_0x35a81d(0x29c));if(_0x12c021?.[_0x35a81d(0x2bf)]?.[_0x35a81d(0x382)])await _0x12c021[_0x35a81d(0x2bf)][_0x35a81d(0x382)]();}async function bootstrapHostPlugins(){const _0x4e108a=_0x4727c2,_0x2a9c09=await importHostModule(_0x4e108a(0x2cb));if(_0x2a9c09?.[_0x4e108a(0x2ef)]?.[_0x4e108a(0x382)])await _0x2a9c09[_0x4e108a(0x2ef)][_0x4e108a(0x382)]();}async function bootstrapHostModules(){const _0xf26bda=_0x4727c2,_0x4418ce=await importHostModule('src/lib/module/index.ts');if(_0x4418ce?.[_0xf26bda(0x309)]?.[_0xf26bda(0x382)])await _0x4418ce[_0xf26bda(0x309)][_0xf26bda(0x382)]();}async function shutdownHostTasks(){const _0x24fc8e=_0x4727c2,_0x1c3392=await importHostModule('src/lib/task/index.ts');if(_0x1c3392?.[_0x24fc8e(0x2bf)]?.['close'])await _0x1c3392[_0x24fc8e(0x2bf)][_0x24fc8e(0x240)]();}async function shutdownHostInfra(){const _0x2052c1=_0x4727c2,_0x5c4b3e=await importHostModule(_0x2052c1(0x26e));if(_0x5c4b3e?.[_0x2052c1(0x315)]?.[_0x2052c1(0x240)])await _0x5c4b3e[_0x2052c1(0x315)][_0x2052c1(0x240)]();const _0xc37e89=await importHostModule(_0x2052c1(0x300));if(_0xc37e89?.['Db']?.[_0x2052c1(0x240)])await _0xc37e89['Db'][_0x2052c1(0x240)]();}async function applyHostAuthMiddleware(_0x2bcad4){const _0x562f3f=_0x4727c2,_0x2ed935=await importHostModule(_0x562f3f(0x24d));if(!_0x2ed935)return _0x2bcad4;let _0x32faa2=_0x2bcad4;if(_0x2ed935[_0x562f3f(0x32c)])_0x32faa2=_0x32faa2['use'](_0x2ed935[_0x562f3f(0x32c)]);if(_0x2ed935[_0x562f3f(0x247)])_0x32faa2=_0x32faa2[_0x562f3f(0x262)](_0x2ed935[_0x562f3f(0x247)]);if(_0x2ed935[_0x562f3f(0x376)])_0x32faa2=_0x32faa2[_0x562f3f(0x262)](_0x2ed935[_0x562f3f(0x376)]);if(_0x2ed935['microApps'])_0x32faa2=_0x32faa2[_0x562f3f(0x262)](_0x2ed935[_0x562f3f(0x1e1)]);if(_0x2ed935[_0x562f3f(0x293)])_0x32faa2=_0x32faa2[_0x562f3f(0x262)](_0x2ed935[_0x562f3f(0x293)]);return _0x32faa2;}function applyAsyncContext(_0x5f31e9){const _0x1909ef=_0x4727c2,_0x57c5ca=VomeConfig['asyncContextManager']??{};if(!_0x57c5ca[_0x1909ef(0x20b)])return _0x5f31e9;return _0x5f31e9[_0x1909ef(0x35b)](({request:_0x406c0d})=>{enterContextWith(initContextFromRequest(_0x406c0d));});}function applyErrorHandler(_0x375a11){const _0x6752d4=_0x4727c2;return _0x375a11[_0x6752d4(0x374)](({error:_0x2e68e4,set:_0x6314ad,code:_0x56ac13})=>{const _0x28e881=_0x6752d4,_0x4f3fa1=getPinoLogger();if(isCommException(_0x2e68e4))return _0x4f3fa1['error']({'code':_0x2e68e4[_0x28e881(0x258)]},_0x2e68e4[_0x28e881(0x318)]),_0x6314ad['status']=_0x2e68e4[_0x28e881(0x350)],{'code':_0x2e68e4[_0x28e881(0x258)],'message':_0x2e68e4[_0x28e881(0x318)]};if(_0x56ac13===_0x28e881(0x28e)){const _0x465875=_0x2e68e4 instanceof Error?_0x2e68e4[_0x28e881(0x318)]:_0x28e881(0x242);return _0x4f3fa1[_0x28e881(0x233)]({'code':_0x56ac13},_0x465875),_0x6314ad['status']=0x1a6,{'code':RES_CODE['ERROR'],'message':_0x465875};}if(_0x56ac13==='NOT_FOUND')return _0x6314ad[_0x28e881(0x2d7)]=0x194,{'code':RES_CODE[_0x28e881(0x34c)],'message':_0x28e881(0x385)};const _0x41ba17=_0x2e68e4 instanceof Error?_0x2e68e4:new Error(String(_0x2e68e4));return _0x4f3fa1[_0x28e881(0x233)](_0x41ba17),_0x6314ad[_0x28e881(0x2d7)]=0x1f4,{'code':RES_CODE[_0x28e881(0x34c)],'message':getEnv()===_0x28e881(0x3ac)?_0x41ba17['message']:_0x28e881(0x384)};});}function applyLogging(_0x497069){const _0x397d0a=_0x4727c2,_0x23cc36=getPinoLogger();return _0x497069[_0x397d0a(0x262)](_0x23cc36['into']({'autoLogging':{'ignore':_0x5a851c=>Boolean(_0x5a851c[_0x397d0a(0x2ca)])}}));}import{openapi}from'@elysiajs/openapi';function applyOpenapi(_0x46205a){const _0x52bb9d=_0x4727c2,_0x201fa0=VomeConfig['openapi']??{'enable':![]};if(_0x201fa0[_0x52bb9d(0x20b)]===![])return _0x46205a;const _0x36decd=_0x201fa0['path']??_0x52bb9d(0x30c),{tags:_0x42224b,tagGroups:_0xd10665}=buildOpenApiTagDocs(),_0x3328c9=_0x201fa0[_0x52bb9d(0x2cd)]??{},_0x4717d0=_0x201fa0[_0x52bb9d(0x308)]??{};return _0x46205a[_0x52bb9d(0x262)](openapi({'path':_0x36decd,'documentation':{..._0x3328c9,'tags':[..._0x3328c9[_0x52bb9d(0x346)]??[],..._0x42224b],'x-tagGroups':_0xd10665},'scalar':{..._0x4717d0,'layout':_0x4717d0[_0x52bb9d(0x276)]??_0x52bb9d(0x3bd),'operationTitleSource':_0x4717d0[_0x52bb9d(0x275)]??'summary'}}));}var app,started=![],signalsRegistered=![],hostScanned=![],bootstrapHooks=[],shutdownHooks=[],usePlugins=[];async function ensureHostScanned(){if(hostScanned)return;hostScanned=!![],await scanHost();}function createApp(){return applyAsyncContext(applyErrorHandler(applyLogging(new _0x59c491())));}function bootstrap(_0x7506b4){const _0xbd7b73=_0x4727c2;bootstrapHooks[_0xbd7b73(0x2dc)](_0x7506b4);}function shutdown(_0x517813){shutdownHooks['push'](_0x517813);}function use(_0x5ed7fb){usePlugins['push'](_0x5ed7fb);}async function start(){const _0x37c370=_0x4727c2;if(started)throw new Error('[App]\x20\u5DF2\u542F\u52A8\uFF0C\u8BF7\u5148\x20App.stop()\x20\u518D\x20start');let _0x49d250=createApp();_0x49d250=await applyHostAuthMiddleware(_0x49d250);for(const _0x393d33 of usePlugins){_0x49d250=_0x393d33(_0x49d250);}await ensureHostScanned(),_0x49d250=applyOpenapi(_0x49d250),await bootstrapHostInfra();for(const _0x464bb1 of bootstrapHooks)await _0x464bb1();bootstrapLogger(),bootstrapIoc(),await bootstrapHostPlugins(),await bootstrapHostModules(),await bootstrapHostTasks(),_0x49d250=registerControllers(_0x49d250,VomeConfig);const _0x48a01d=VomeConfig['system']?.['port']??0xbb9;return _0x49d250[_0x37c370(0x3b6)](_0x48a01d),app=_0x49d250,started=!![],printStartupBanner(),registerShutdownSignals(),app;}async function stop(){const _0x69036e=_0x4727c2;if(!app)return;for(const _0x617212 of shutdownHooks)await _0x617212();await shutdownHostTasks(),await shutdownHostInfra(),await app[_0x69036e(0x2c1)](),app=undefined,started=![],hostScanned=![],resetIoc(),resetPinoLogger(),setCrudRegistrar(undefined),signalsRegistered=![];}function registerShutdownSignals(){const _0x391ba0=_0x4727c2;if(signalsRegistered)return;signalsRegistered=!![];for(const _0x4dfc32 of[_0x391ba0(0x32d),_0x391ba0(0x2b0)]){process[_0x391ba0(0x23d)](_0x4dfc32,async()=>{const _0x18ac43=_0x391ba0;await stop(),process[_0x18ac43(0x354)](0x0);});}}var App={'bootstrap':bootstrap,'shutdown':shutdown,'use':use,'start':start,'stop':stop};async function vome(_0x46e95a){const _0x396e7d=_0x4727c2;if(_0x46e95a)await _0x46e95a({'App':App});return App[_0x396e7d(0x210)]();}import{getTableColumns as _0x2f3001,getTableName as _0xd19f45}from'drizzle-orm';import{getTableColumns as _0x149367,getTableName}from'drizzle-orm';import{integer,serial,timestamp}from'drizzle-orm/pg-core';var baseColumns={'id':serial('id')[_0x4727c2(0x22a)](),'createTime':timestamp('createTime',{'withTimezone':!![]})[_0x4727c2(0x280)]()['defaultNow'](),'updateTime':timestamp(_0x4727c2(0x1ff),{'withTimezone':!![]})['notNull']()[_0x4727c2(0x296)]()[_0x4727c2(0x2c2)](()=>new Date()),'deletedAt':timestamp('deletedAt',{'withTimezone':!![]}),'tenantId':integer(_0x4727c2(0x31b))},BASE_COLUMN_COMMENTS={'id':'ID','createTime':_0x4727c2(0x1de),'updateTime':_0x4727c2(0x31a),'deletedAt':_0x4727c2(0x36a),'tenantId':'\u79DF\u6237'},registry=new WeakMap(),tables=new Set();function columnComments(_0x4b4a3c,_0x46442a={}){const _0x333276=_0x4727c2;return tables[_0x333276(0x213)](_0x4b4a3c),registry[_0x333276(0x2fc)](_0x4b4a3c,{...BASE_COLUMN_COMMENTS,...registry[_0x333276(0x389)](_0x4b4a3c)||{},..._0x46442a}),_0x4b4a3c;}function getColumnComments(_0x4a0e1f){return registry['get'](_0x4a0e1f)||{};}function listColumnCommentTables(){return[...tables];}function quoteIdent(_0x1e39cd){const _0x53e4dd=_0x4727c2;if(!/^[A-Za-z_][A-Za-z0-9_]*$/['test'](_0x1e39cd))throw new Error(_0x53e4dd(0x230)+_0x1e39cd);return'\x22'+_0x1e39cd+'\x22';}function escapeLiteral(_0x1decfd){return _0x1decfd['replace'](/'/g,'\x27\x27');}async function syncColumnCommentsToPg(_0xe559a4){const _0x2da588=_0x4727c2,_0x9d9b44=listColumnCommentTables();if(!_0x9d9b44[_0x2da588(0x202)])return 0x0;const _0x19539f=new Map(),_0x1ed783=[];for(const _0x5177c6 of _0x9d9b44){let _0x58c761;try{_0x58c761=getTableName(_0x5177c6);}catch{continue;}const _0x314b3b=_0x149367(_0x5177c6),_0x553321=getColumnComments(_0x5177c6),_0x372550=new Map();for(const [_0x3593aa,_0x4c0216]of Object[_0x2da588(0x3b8)](_0x553321)){if(!_0x4c0216||!(_0x3593aa in _0x314b3b))continue;_0x372550[_0x2da588(0x2fc)](_0x3593aa,_0x4c0216);}if(!_0x372550['size'])continue;_0x19539f[_0x2da588(0x2fc)](_0x58c761,_0x372550),_0x1ed783[_0x2da588(0x2dc)](_0x58c761);}if(!_0x1ed783[_0x2da588(0x202)])return 0x0;const _0x29b09c=_0x1ed783['map'](_0x549377=>'\x27'+escapeLiteral(_0x549377)+'\x27')[_0x2da588(0x249)](','),_0x1a2002=await _0xe559a4['unsafe'](_0x2da588(0x2f2)+_0x29b09c+_0x2da588(0x2e1)),_0x48dcb1=new Map();for(const _0x3f689f of _0x1a2002||[]){if(!_0x3f689f['table_name']||!_0x3f689f[_0x2da588(0x253)])continue;_0x48dcb1[_0x2da588(0x2fc)](_0x3f689f[_0x2da588(0x2e6)]+'.'+_0x3f689f[_0x2da588(0x253)],_0x3f689f[_0x2da588(0x379)]??null);}let _0x50a3a5=0x0;for(const [_0x3daf11,_0x52c7de]of _0x19539f){for(const [_0x32dc1a,_0x413851]of _0x52c7de){const _0x2e9da7=_0x3daf11+'.'+_0x32dc1a,_0x495273=_0x48dcb1[_0x2da588(0x389)](_0x2e9da7);if(_0x495273===_0x413851)continue;await _0xe559a4[_0x2da588(0x368)](_0x2da588(0x295)+quoteIdent(_0x3daf11)+'.'+quoteIdent(_0x32dc1a)+'\x20IS\x20\x27'+escapeLiteral(_0x413851)+'\x27'),_0x50a3a5++;}}return _0x50a3a5;}var SIDE_PREFIX2={'admin':'/admin','app':'/app'};function getSidePrefix2(_0x153ba8){return normalizePrefix(SIDE_PREFIX2[_0x153ba8]);}function lastSegment(_0x49d98d){const _0x47223b=_0x4727c2,_0x43a11c=_0x49d98d[_0x47223b(0x244)](/^\/+|\/+$/g,'')[_0x47223b(0x22f)]('/');return _0x43a11c[_0x43a11c[_0x47223b(0x202)]-0x1]||_0x49d98d||_0x47223b(0x380);}function toPascalEntityName(_0x4e4418){const _0x161f37=_0x4727c2;return _0x4e4418[_0x161f37(0x22f)]('_')[_0x161f37(0x2e3)](Boolean)[_0x161f37(0x38c)](_0x45e2ce=>_0x45e2ce['charAt'](0x0)['toUpperCase']()+_0x45e2ce[_0x161f37(0x1fb)](0x1))['join']('')+_0x161f37(0x25c);}function withAlias(_0x311a13){if(!_0x311a13?.['length'])return[];return _0x311a13['map'](_0x1d2598=>{const _0xbb4f6=_0x1a3d;if(typeof _0x1d2598!==_0xbb4f6(0x256)){const _0x199358=_0x1d2598['column'];return{..._0x1d2598,'column':_0x199358[_0xbb4f6(0x395)]('.')?_0x199358:'a.'+_0x199358};}return _0x1d2598['includes']('.')?_0x1d2598:'a.'+_0x1d2598;});}function normalizePageQueryOp(_0x429340){const _0xe3fcb4=_0x4727c2;return{'keyWordLikeFields':withAlias(_0x429340?.['keyWordLikeFields']),'fieldEq':withAlias(_0x429340?.[_0xe3fcb4(0x270)]),'fieldLike':withAlias(_0x429340?.['fieldLike']),'fieldArray':withAlias(_0x429340?.[_0xe3fcb4(0x23e)]),'fieldRange':(_0x429340?.[_0xe3fcb4(0x1e5)]??[])[_0xe3fcb4(0x38c)](_0xc54f3d=>({..._0xc54f3d,'column':_0xc54f3d['column']['includes']('.')?_0xc54f3d[_0xe3fcb4(0x3b5)]:'a.'+_0xc54f3d[_0xe3fcb4(0x3b5)]}))};}function applyFieldDictToColumns(_0x1dc87b,_0x584360){const _0x228392=_0x4727c2;for(const _0x170b2d of _0x584360){if(typeof _0x170b2d===_0x228392(0x256)||!_0x170b2d[_0x228392(0x2cc)])continue;const _0x1a6891=_0x170b2d['column'][_0x228392(0x395)]('.')?_0x170b2d[_0x228392(0x3b5)][_0x228392(0x22f)]('.')[_0x228392(0x27d)]():_0x170b2d[_0x228392(0x3b5)],_0x4c2cce=_0x1dc87b[_0x228392(0x217)](_0x1383e8=>_0x1383e8['propertyName']===_0x1a6891);if(_0x4c2cce)_0x4c2cce['dict']=_0x170b2d[_0x228392(0x2cc)];}}function columnsFromEntity(_0x1e2636){const _0x924fd2=_0x4727c2;if(!_0x1e2636||typeof _0x1e2636!==_0x924fd2(0x310))return[];try{const _0x2e65ac=_0x2f3001(_0x1e2636),_0x5c802d=getColumnComments(_0x1e2636),_0x2aa939=[];for(const [_0xe3aba7,_0xeae998]of Object[_0x924fd2(0x3b8)](_0x2e65ac)){if(_0xe3aba7===_0x924fd2(0x31b))continue;const _0x41f1a1=_0xeae998;_0x2aa939[_0x924fd2(0x2dc)]({'propertyName':_0xe3aba7,'type':String(_0x41f1a1[_0x924fd2(0x36f)]??_0x41f1a1[_0x924fd2(0x209)]??_0x924fd2(0x256)),'length':_0x41f1a1['length']!=null?String(_0x41f1a1['length']):undefined,'nullable':_0x41f1a1[_0x924fd2(0x280)]!==!![],'source':'a.'+_0xe3aba7,'comment':_0x5c802d[_0xe3aba7]});}const _0x13c2b7=new Set([_0x924fd2(0x3a3),_0x924fd2(0x1ff),'deletedAt']),_0xf207dd=_0x2aa939[_0x924fd2(0x2e3)](_0x46af7c=>!_0x13c2b7[_0x924fd2(0x211)](_0x46af7c[_0x924fd2(0x1e9)])),_0x39ce86=_0x2aa939[_0x924fd2(0x2e3)](_0x1b41d1=>_0x13c2b7[_0x924fd2(0x211)](_0x1b41d1[_0x924fd2(0x1e9)]));return[..._0xf207dd,..._0x39ce86];}catch{return[];}}function entityNameOf(_0x5316f6){if(!_0x5316f6||typeof _0x5316f6!=='object')return;try{return toPascalEntityName(_0xd19f45(_0x5316f6));}catch{return;}}function buildApis(_0x114d3f,_0x4199b5){const _0x5232e5=_0x4727c2,_0x38f355=[],_0x31e57d=new Set(),_0x2ab389=_0xf4b5af=>{const _0x30be73=_0x1a3d,_0x1b0501=_0xf4b5af[_0x30be73(0x269)]+':'+_0xf4b5af[_0x30be73(0x2b5)];if(_0x31e57d[_0x30be73(0x211)](_0x1b0501))return;_0x31e57d[_0x30be73(0x213)](_0x1b0501),_0x38f355[_0x30be73(0x2dc)](_0xf4b5af);};for(const _0x38384a of _0x114d3f[_0x5232e5(0x1e0)]){const _0x3493c0=getRouteSubPath(_0x38384a[_0x5232e5(0x2b5)],_0x114d3f[_0x5232e5(0x388)]),_0x44ed05=_0x3493c0[_0x5232e5(0x2ed)]('/')?_0x3493c0:'/'+_0x3493c0,_0x42ed0a=actionFromSubPath(_0x44ed05);_0x2ab389({'method':_0x38384a['method'][_0x5232e5(0x289)](),'path':_0x44ed05,'summary':_0x38384a[_0x5232e5(0x1f4)]??'','dts':{},'tag':'','prefix':_0x4199b5,'ignoreToken':Boolean(_0x38384a[_0x5232e5(0x200)]),'ignorePerms':Boolean(_0x38384a[_0x5232e5(0x3b2)]),'perms':effectivePerms(_0x38384a,_0x114d3f,_0x42ed0a)??[]});}for(const _0x318209 of _0x114d3f['crud']?.[_0x5232e5(0x22b)]??[]){const _0x32b44e='/'+_0x318209;_0x2ab389({'method':_0x318209===_0x5232e5(0x304)?_0x5232e5(0x389):'post','path':_0x32b44e,'summary':CRUD_SUMMARY[_0x318209]??_0x318209,'dts':{},'tag':'','prefix':_0x4199b5,'ignoreToken':![],'ignorePerms':![],'perms':effectivePerms({},_0x114d3f,_0x318209)??[]});}for(const _0x1b49db of _0x114d3f[_0x5232e5(0x391)]?.[_0x5232e5(0x30b)]??[]){const _0x7cef48='/'+_0x1b49db;_0x2ab389({'method':_0x5232e5(0x21a),'path':_0x7cef48,'summary':_0x1b49db,'dts':{},'tag':'','prefix':_0x4199b5,'ignoreToken':![],'ignorePerms':![],'perms':effectivePerms({},_0x114d3f,_0x1b49db)??[]});}return _0x38f355;}function buildEntity(_0x4aec12){const _0x1cd413=_0x4727c2,_0x2b1fa6=joinPrefix(getSidePrefix2(_0x4aec12['side']),_0x4aec12[_0x1cd413(0x388)]),_0xba813=lastSegment(_0x4aec12[_0x1cd413(0x388)]),_0xa46981=_0x4aec12[_0x1cd413(0x391)]?.['entity'],_0x2afdcd=columnsFromEntity(_0xa46981),_0x61961e=normalizePageQueryOp(_0x4aec12[_0x1cd413(0x391)]?.['pageQueryOp']);return applyFieldDictToColumns(_0x2afdcd,_0x61961e['fieldEq']),{'module':_0x4aec12[_0x1cd413(0x265)],'side':_0x4aec12['side'],'prefix':_0x2b1fa6,'name':entityNameOf(_0xa46981),'info':{'type':{'name':_0xba813,'description':_0x4aec12[_0x1cd413(0x37e)]??_0xba813}},'api':buildApis(_0x4aec12,_0x2b1fa6),'columns':_0x2afdcd,'pageQueryOp':_0x61961e,'pageColumns':_0x2afdcd};}function groupByModule(_0x2bbfa6){const _0x4f0950=_0x4727c2,_0x3669ed={};for(const _0x1d9181 of _0x2bbfa6){const _0x3a41b7=_0x3669ed[_0x1d9181['module']]??[];_0x3a41b7[_0x4f0950(0x2dc)](_0x1d9181),_0x3669ed[_0x1d9181['module']]=_0x3a41b7;}return _0x3669ed;}function isEpsEnabled(){const _0x39c28d=_0x4727c2;return Boolean(VomeConfig[_0x39c28d(0x20a)]?.['eps']);}function buildEps(_0x26d523){const _0xc17b27=_0x4727c2;if(!isEpsEnabled())return{};return groupByModule(listControllers(_0x26d523)[_0xc17b27(0x38c)](buildEntity));}var Eps={'controllers':listControllers,'admin':()=>buildEps('admin'),'app':()=>buildEps('app'),'enabled':isEpsEnabled};import'reflect-metadata';var ROUTES_PENDING_KEY=_0x4727c2(0x263);function joinRoute(_0x3c494f,_0x5f2449){return joinPrefix(_0x3c494f,_0x5f2449==='/'?'':_0x5f2449);}function asMiddlewareList(_0x4e6f46){const _0xeb8818=_0x4727c2;if(_0x4e6f46==null)return;return Array[_0xeb8818(0x327)](_0x4e6f46)?_0x4e6f46:[_0x4e6f46];}function appendPendingRoute(_0x56e8f3,_0x51e4e4){const _0x54c9f1=_0x4727c2,_0x1693cc=Reflect['getMetadata'](ROUTES_PENDING_KEY,_0x56e8f3)??[];_0x1693cc[_0x54c9f1(0x2dc)](_0x51e4e4),Reflect[_0x54c9f1(0x328)](ROUTES_PENDING_KEY,_0x1693cc,_0x56e8f3);}function createParamDecorator(_0x431b0f){const _0x334102=_0x4727c2,_0x294962=_0x431b0f===_0x334102(0x3aa)?'Param':_0x431b0f==='body'?_0x334102(0x303):_0x334102(0x35d);return _0x4514ee=>(_0x45dfb1,_0x1830c7,_0x22b45e)=>{const _0x1b8be6=_0x334102;if(_0x1830c7===undefined)throw new Error('[Controller]\x20@'+_0x294962+'\x20只能用于方法参数');const _0x38bf07=_0x45dfb1[_0x1b8be6(0x1e4)];appendRouteParam(_0x38bf07,String(_0x1830c7),{'index':_0x22b45e,'source':_0x431b0f,'schema':_0x4514ee});};}function pickCrudOptions(_0x2f968c){const {api:_0x4a6662,entity:_0x5042ba,service:_0x3c147e,serviceApis:_0x15d6c7,before:_0x307a5b,pageQueryOp:_0x2dad7d,listQueryOp:_0xefd232,insertParam:_0x216a87,infoIgnoreProperty:_0x5c5de4}=_0x2f968c;if(_0x4a6662==null&&_0x5042ba==null&&_0x3c147e==null&&_0x15d6c7==null&&_0x307a5b==null&&_0x2dad7d==null&&_0xefd232==null&&_0x216a87==null&&_0x5c5de4==null)return;return{'api':_0x4a6662,'entity':_0x5042ba,'service':_0x3c147e,'serviceApis':_0x15d6c7,'before':_0x307a5b,'pageQueryOp':_0x2dad7d,'listQueryOp':_0xefd232,'insertParam':_0x216a87,'infoIgnoreProperty':_0x5c5de4};}function Controller(_0x433f64=''){const _0xb57a1d=_0x4727c2,_0x230040=typeof _0x433f64===_0xb57a1d(0x256),_0x3d0ba5=_0x230040?{'prefix':_0x433f64}:_0x433f64;return _0x5f3d3c=>{const _0x5852b0=_0xb57a1d;registerProvider({'token':_0x5f3d3c,'useClass':_0x5f3d3c,'scope':_0x5852b0(0x218)});const _0x3ed024=getControllerScanContext(),_0x588ef4=_0x230040&&_0x433f64===''||!_0x230040&&(_0x3d0ba5[_0x5852b0(0x388)]==null||_0x3d0ba5[_0x5852b0(0x388)]===''),_0x252581=normalizePrefix(_0x588ef4&&_0x3ed024?.[_0x5852b0(0x292)]?parseControllerAutoPrefix(_0x3ed024[_0x5852b0(0x292)]):_0x3d0ba5[_0x5852b0(0x388)]??''),_0x29d283=Reflect['getMetadata'](ROUTES_PENDING_KEY,_0x5f3d3c)??[],_0x134888=pickCrudOptions(_0x3d0ba5);registerController({'token':_0x5f3d3c,'prefix':_0x252581,'module':_0x3d0ba5[_0x5852b0(0x265)]??_0x3ed024?.[_0x5852b0(0x265)]??'unknown','side':_0x3d0ba5[_0x5852b0(0x3b1)]??_0x3ed024?.[_0x5852b0(0x3b1)]??_0x5852b0(0x32b),'description':_0x3d0ba5[_0x5852b0(0x37e)],'file':_0x3ed024?.[_0x5852b0(0x292)],'middleware':asMiddlewareList(_0x3d0ba5[_0x5852b0(0x274)]),'crud':_0x134888,'routes':_0x29d283[_0x5852b0(0x38c)](_0x9d5f99=>{const _0x32af7e=_0x5852b0,_0x2b58fd=getRouteParams(_0x5f3d3c,_0x9d5f99[_0x32af7e(0x1e6)]),_0x3f1b78=schemaFromParams(_0x2b58fd),_0x5acb2f=[..._0x9d5f99[_0x32af7e(0x274)]??[],...getRouteMiddleware(_0x5f3d3c,_0x9d5f99[_0x32af7e(0x1e6)])];return{..._0x9d5f99,'path':joinRoute(_0x252581,_0x9d5f99[_0x32af7e(0x2b5)][_0x32af7e(0x2ed)]('/')?_0x9d5f99[_0x32af7e(0x2b5)]['slice'](0x1):_0x9d5f99[_0x32af7e(0x2b5)]),'params':_0x2b58fd,'body':_0x3f1b78?.[_0x32af7e(0x3ba)],'query':_0x3f1b78?.[_0x32af7e(0x1ed)],'routeParams':_0x3f1b78?.['params'],'public':isRoutePublic(_0x5f3d3c,_0x9d5f99['handler']),'ignorePerms':isRouteIgnorePerms(_0x5f3d3c,_0x9d5f99[_0x32af7e(0x1e6)]),'perms':getRoutePerms(_0x5f3d3c,_0x9d5f99['handler']),'middleware':_0x5acb2f[_0x32af7e(0x202)]?_0x5acb2f:undefined};})}),Reflect[_0x5852b0(0x352)](ROUTES_PENDING_KEY,_0x5f3d3c),clearRouteParams(_0x5f3d3c),clearRoutePublic(_0x5f3d3c),clearRouteMiddleware(_0x5f3d3c),clearRoutePerms(_0x5f3d3c),clearRouteIgnorePerms(_0x5f3d3c);};}function Use(..._0x2c543e){return(_0x2828ef,_0x48a196)=>{const _0x29db91=_0x2828ef['constructor'];appendRouteMiddleware(_0x29db91,String(_0x48a196),_0x2c543e);};}function createMethodDecorator(_0x1a4ad8){return(_0x493365='',_0x1f70dd)=>(_0x37832d,_0x4286a4)=>{const _0xa87113=_0x1a3d,_0x1dc210=_0x37832d[_0xa87113(0x1e4)];appendPendingRoute(_0x1dc210,{'method':_0x1a4ad8,'path':_0x493365,'handler':String(_0x4286a4),'summary':_0x1f70dd?.[_0xa87113(0x1f4)]});};}function Public(){return(_0x3ae41e,_0x29d7fb)=>{const _0x2a65f1=_0x1a3d,_0x847d00=_0x3ae41e[_0x2a65f1(0x1e4)];markRoutePublic(_0x847d00,String(_0x29d7fb));};}function Perms(..._0x1173a8){return(_0x5aa96b,_0x4eab3a)=>{const _0x1c6c02=_0x5aa96b['constructor'];setRoutePerms(_0x1c6c02,String(_0x4eab3a),_0x1173a8);};}function IgnorePerms(){return(_0x5e8570,_0x4fe0e7)=>{const _0x28de72=_0x1a3d,_0x363a0f=_0x5e8570[_0x28de72(0x1e4)];markRouteIgnorePerms(_0x363a0f,String(_0x4fe0e7));};}var Body=createParamDecorator(_0x4727c2(0x3ba)),Query=createParamDecorator('query'),Param=createParamDecorator(_0x4727c2(0x3aa)),Get=createMethodDecorator(_0x4727c2(0x2c0)),Post=createMethodDecorator(_0x4727c2(0x3bc)),Put=createMethodDecorator(_0x4727c2(0x222)),Delete=createMethodDecorator(_0x4727c2(0x2b9)),Patch=createMethodDecorator(_0x4727c2(0x251));class BasePlugin{['pluginInfo'];[_0x4727c2(0x3bb)];['cache'];[_0x4727c2(0x268)];async[_0x4727c2(0x3b4)](_0x123798,_0x586fa6,_0x1c9ede,_0x36d4f9){const _0xe8c613=_0x4727c2;this[_0xe8c613(0x335)]=_0x123798,this[_0xe8c613(0x3bb)]=_0x586fa6,this[_0xe8c613(0x267)]=_0x36d4f9?.[_0xe8c613(0x267)],this[_0xe8c613(0x268)]=_0x36d4f9?.[_0xe8c613(0x268)],await this[_0xe8c613(0x357)]();}async[_0x4727c2(0x357)](){}}import{existsSync,readFileSync}from'fs';import{createRequire}from'module';import{join as _0x138fed}from'path';import{createHash}from'crypto';import{homedir}from'os';import{join as _0x2a03e9}from'path';function pDataPath(){const _0x27ae60=_0x4727c2,_0x29ad2d=createHash(_0x27ae60(0x266))[_0x27ae60(0x282)](String(VomeConfig[_0x27ae60(0x246)]??_0x27ae60(0x20a)))[_0x27ae60(0x372)]('hex');return _0x2a03e9(homedir(),'.vome',_0x29ad2d);}function pPluginPath(){const _0x3036d2=_0x4727c2;return _0x2a03e9(pDataPath(),_0x3036d2(0x1fc));}function pModulesPath(){const _0x56c509=_0x4727c2;return _0x2a03e9(pDataPath(),_0x56c509(0x2f4));}function pModulePath(_0x4f3506){return _0x2a03e9(pModulesPath(),_0x4f3506);}var hostRequire=createRequire(import.meta.url);function pluginRequire(_0x1c7658){if(_0x1c7658==='vome-plugin-runtime')return{'BasePlugin':BasePlugin};return hostRequire(_0x1c7658);}function loadPluginClass(_0x197397){const _0x1fe20b=_0x4727c2;try{const _0x2dd665=_0x197397[_0x1fe20b(0x244)](/export\s+const\s+Plugin\s*=/g,_0x1fe20b(0x3ad))[_0x1fe20b(0x244)](/export\s+\{[^}]*\bPlugin\b[^}]*\};?/g,'')[_0x1fe20b(0x244)](/export\s+const\s+handlers\s*=/g,'var\x20handlers\x20=')[_0x1fe20b(0x244)](/export\s+\{[^}]*\bhandlers\b[^}]*\};?/g,'')['replace'](/export\s+class\s+(\w+)/g,_0x1fe20b(0x2c3))[_0x1fe20b(0x244)](/export\s+default\s+/g,'')[_0x1fe20b(0x244)](/import\s+\{?\s*BasePlugin\s*\}?\s*from\s*['"][^'"]+['"];?/g,'')[_0x1fe20b(0x244)](/import\s+BasePlugin\s+from\s*['"][^'"]+['"];?/g,'')[_0x1fe20b(0x244)](/require\(\s*['"]vome-plugin-runtime['"]\s*\)/g,'({\x20BasePlugin\x20})'),_0x3cd627=new Function('BasePlugin','require',_0x1fe20b(0x265),_0x1fe20b(0x2c8),_0x2dd665+'\x0avar\x20__Plugin\x20=\x20(typeof\x20Plugin\x20!==\x20\x27undefined\x27)\x0a\x20\x20?\x20Plugin\x0a\x20\x20:\x20(module.exports\x20&&\x20(module.exports.Plugin\x20||\x20module.exports.default\x20||\x20module.exports));\x0aif\x20(typeof\x20__Plugin\x20===\x20\x27undefined\x27\x20||\x20__Plugin\x20===\x20null)\x20{\x0a\x20\x20throw\x20new\x20Error(\x27missing\x20export\x20Plugin\x27);\x0a}\x0areturn\x20__Plugin;'),_0x3d1af8={'exports':{}};return _0x3cd627(BasePlugin,pluginRequire,_0x3d1af8,_0x3d1af8[_0x1fe20b(0x2c8)]);}catch(_0x2b8048){throw new Error(_0x1fe20b(0x33e)+(_0x2b8048 instanceof Error?_0x2b8048[_0x1fe20b(0x318)]:String(_0x2b8048)));}}function readPluginScript(_0x27bcaf){const _0x43fcb8=_0x4727c2,_0x2b0c38=_0x138fed(pModulePath(_0x27bcaf),_0x43fcb8(0x2eb),'index.js');if(existsSync(_0x2b0c38))return readFileSync(_0x2b0c38,_0x43fcb8(0x2d5));const _0x37de20=_0x138fed(pPluginPath(),_0x27bcaf);if(!existsSync(_0x37de20))return;try{const _0x489ac6=JSON[_0x43fcb8(0x2e9)](readFileSync(_0x37de20,'utf8'));return _0x489ac6[_0x43fcb8(0x207)]?.[_0x43fcb8(0x2ba)];}catch{return;}}import{existsSync as _0x9a50c2,readFileSync as _0x335bf3,readdirSync as _0x109931,statSync}from'fs';import{createRequire as _0x17e74c}from'module';import{join as _0x4b3091}from'path';var registry2=new Map(),hostRequire2=_0x17e74c(import.meta.url);function pluginRequire2(_0x3a5562){if(_0x3a5562==='vome-plugin-runtime')return{'BasePlugin':BasePlugin};return hostRequire2(_0x3a5562);}function normalizePath(_0x4d97ec){const _0x4cb400=_0x4727c2,_0x4386f7=_0x4d97ec[_0x4cb400(0x2ed)]('/')?_0x4d97ec:'/'+_0x4d97ec;return _0x4386f7[_0x4cb400(0x244)](/\/+$/,'')||'/';}function normalizeMethod(_0xb10f0f){const _0x105caa=_0x4727c2;return _0xb10f0f[_0x105caa(0x2bd)]();}function normalizeModuleScript(_0x50d4d3){const _0x260db4=_0x4727c2;return _0x50d4d3[_0x260db4(0x244)](/export\s+const\s+handlers\s*=/g,_0x260db4(0x2c4))['replace'](/export\s+\{[^}]*\bhandlers\b[^}]*\};?/g,'')['replace'](/export\s+default\s+\{/g,_0x260db4(0x337))['replace'](/export\s+const\s+Plugin\s*=/g,_0x260db4(0x3ad))['replace'](/export\s+\{[^}]*\bPlugin\b[^}]*\};?/g,'')[_0x260db4(0x244)](/export\s+class\s+(\w+)/g,_0x260db4(0x2c3))[_0x260db4(0x244)](/import\s+\{?\s*BasePlugin\s*\}?\s*from\s*['"][^'"]+['"];?/g,'')[_0x260db4(0x244)](/import\s+BasePlugin\s+from\s*['"][^'"]+['"];?/g,'')[_0x260db4(0x244)](/require\(\s*['"]vome-plugin-runtime['"]\s*\)/g,_0x260db4(0x260));}function loadModuleHandlers(_0x519377,_0x8884fd=!![]){const _0x5d3c24=_0x4727c2,_0x3c9fb6=normalizeModuleScript(_0x519377),_0x334006=new Function('BasePlugin','require',_0x5d3c24(0x265),_0x5d3c24(0x2c8),_0x3c9fb6+_0x5d3c24(0x397)),_0x480089={'exports':{}},_0x5f04e9=_0x334006(BasePlugin,pluginRequire2,_0x480089,_0x480089['exports']);if(!_0x5f04e9||typeof _0x5f04e9!=='object'){if(_0x8884fd)throw new Error('missing\x20export\x20handlers');return{};}return _0x5f04e9;}var ModuleRegistry={'get'(_0x2f301e){return registry2['get'](_0x2f301e);},'list'(){const _0x53e0b2=_0x4727c2;return[...registry2[_0x53e0b2(0x3b8)]()][_0x53e0b2(0x38c)](([_0x337708,_0x4c03ae])=>({'key':_0x337708,'manifest':_0x4c03ae[_0x53e0b2(0x375)],'routes':_0x4c03ae[_0x53e0b2(0x1e0)]}));},'load'(_0x262cd2){const _0x1a0c03=_0x4727c2;if(!_0x262cd2||!/^[a-zA-Z0-9_-]+$/[_0x1a0c03(0x298)](_0x262cd2))throw new Error(_0x1a0c03(0x287)+_0x262cd2);const _0x54559b=pModulePath(_0x262cd2),_0x3cb41b=_0x4b3091(_0x54559b,_0x1a0c03(0x35c));if(!_0x9a50c2(_0x3cb41b))throw new Error(_0x1a0c03(0x370)+_0x262cd2);const _0x2bf2fc=JSON['parse'](_0x335bf3(_0x3cb41b,_0x1a0c03(0x2d5))),_0x285d6c=(_0x2bf2fc[_0x1a0c03(0x1e0)]??[])[_0x1a0c03(0x38c)](_0x80ff83=>({..._0x80ff83,'method':normalizeMethod(_0x80ff83['method']),'path':normalizePath(_0x80ff83[_0x1a0c03(0x2b5)])}));let _0x42b782={};const _0x667946=_0x4b3091(_0x54559b,_0x1a0c03(0x2eb),_0x1a0c03(0x36b));if(_0x9a50c2(_0x667946)){const _0xd54574=_0x335bf3(_0x667946,_0x1a0c03(0x2d5));_0x42b782=loadModuleHandlers(_0xd54574,_0x285d6c[_0x1a0c03(0x202)]>0x0);for(const _0x4ad62c of _0x285d6c){if(typeof _0x42b782[_0x4ad62c[_0x1a0c03(0x1e6)]]!==_0x1a0c03(0x305))throw new Error('模块\x20'+_0x262cd2+'\x20缺少\x20handler:\x20'+_0x4ad62c[_0x1a0c03(0x1e6)]);}}else{if(_0x285d6c[_0x1a0c03(0x202)])throw new Error('模块\x20'+_0x262cd2+_0x1a0c03(0x2e4));}return registry2[_0x1a0c03(0x2fc)](_0x262cd2,{'manifest':_0x2bf2fc,'handlers':_0x42b782,'routes':_0x285d6c}),registry2[_0x1a0c03(0x389)](_0x262cd2);},'unload'(_0x392ea7){const _0x41d808=_0x4727c2;registry2[_0x41d808(0x232)](_0x392ea7);},async 'dispatch'(_0x40a28c,_0x2fbd65,_0x597e4e,_0x4e3bfa){const _0x26de50=_0x4727c2,_0x1eea2f=registry2['get'](_0x40a28c);if(!_0x1eea2f)return{'ok':![],'status':0x194,'message':_0x26de50(0x273)};const _0x50648a=normalizeMethod(_0x2fbd65),_0x3c3d22=normalizePath(_0x597e4e),_0x542c08=_0x1eea2f['routes']['find'](_0x2a47a6=>_0x2a47a6[_0x26de50(0x269)]===_0x50648a&&_0x2a47a6[_0x26de50(0x2b5)]===_0x3c3d22);if(!_0x542c08)return{'ok':![],'status':0x194,'message':_0x26de50(0x396)};const _0xa85b73=_0x1eea2f[_0x26de50(0x212)][_0x542c08[_0x26de50(0x1e6)]];if(typeof _0xa85b73!=='function')return{'ok':![],'status':0x1f4,'message':_0x26de50(0x2e7)+_0x542c08[_0x26de50(0x1e6)]};try{const _0x43ca58=await _0xa85b73(_0x4e3bfa);return{'ok':!![],'data':_0x43ca58,'route':_0x542c08};}catch(_0x5b82d9){const _0x589f20=_0x5b82d9 instanceof Error?_0x5b82d9['message']:String(_0x5b82d9);return{'ok':![],'status':0x1f4,'message':_0x589f20,'route':_0x542c08};}},'bootstrap'(){const _0x2ce253=_0x4727c2,_0x22b1b1=pModulesPath();if(!_0x9a50c2(_0x22b1b1))return;for(const _0x1bbfe2 of _0x109931(_0x22b1b1)){const _0x56c043=_0x4b3091(_0x22b1b1,_0x1bbfe2);if(!statSync(_0x56c043)['isDirectory']())continue;if(!_0x9a50c2(_0x4b3091(_0x56c043,_0x2ce253(0x35c))))continue;try{this['load'](_0x1bbfe2),console[_0x2ce253(0x2e2)](_0x2ce253(0x241)+_0x1bbfe2);}catch(_0x467fcd){console[_0x2ce253(0x1f8)](_0x2ce253(0x204)+_0x1bbfe2+':',_0x467fcd instanceof Error?_0x467fcd['message']:_0x467fcd);}}}};import{existsSync as _0x286eff,statSync as _0x2209a8}from'fs';import{join as _0x199eb5,normalize,sep}from'path';import{Elysia as _0x4890ac}from'elysia';var PREFIX=_0x4727c2(0x20c);function contentType(_0x503074){const _0x2d9189=_0x4727c2,_0x14e40d=_0x503074[_0x2d9189(0x289)]();if(_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x29e)))return'text/html;\x20charset=utf-8';if(_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x28a))||_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x1f0)))return _0x2d9189(0x386);if(_0x14e40d['endsWith'](_0x2d9189(0x2f0)))return _0x2d9189(0x21e);if(_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x235)))return _0x2d9189(0x362);if(_0x14e40d[_0x2d9189(0x3a9)]('.svg'))return _0x2d9189(0x345);if(_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x1f7)))return _0x2d9189(0x366);if(_0x14e40d[_0x2d9189(0x3a9)]('.jpg')||_0x14e40d[_0x2d9189(0x3a9)]('.jpeg'))return _0x2d9189(0x2df);if(_0x14e40d['endsWith'](_0x2d9189(0x3b9)))return _0x2d9189(0x37a);if(_0x14e40d[_0x2d9189(0x3a9)](_0x2d9189(0x25d)))return _0x2d9189(0x2bc);if(_0x14e40d['endsWith']('.map'))return _0x2d9189(0x255);return _0x2d9189(0x2a4);}var microApps=new _0x4890ac({'name':_0x4727c2(0x271)})['get'](PREFIX+'/*',({params:_0x4bf5ba,set:_0x4774c3})=>{const _0x2b8466=_0x4727c2,_0x17d466=String(_0x4bf5ba['*']||''),_0x3c8967=_0x17d466[_0x2b8466(0x22f)]('/')['filter'](Boolean);if(!_0x3c8967[_0x2b8466(0x202)])return _0x4774c3[_0x2b8466(0x2d7)]=0x194,_0x2b8466(0x2b3);const _0x155681=_0x3c8967[0x0];if(!/^[a-zA-Z0-9_-]+$/['test'](_0x155681))return _0x4774c3['status']=0x190,'Invalid\x20app\x20key';const _0x2d5a93=_0x199eb5(pModulePath(_0x155681),_0x2b8466(0x373));if(!_0x286eff(_0x2d5a93)||!_0x2209a8(_0x2d5a93)[_0x2b8466(0x1e8)]())return _0x4774c3[_0x2b8466(0x2d7)]=0x194,_0x2b8466(0x1db);let _0x349997=_0x3c8967['slice'](0x1)[_0x2b8466(0x249)]('/')||_0x2b8466(0x39c);if(_0x349997[_0x2b8466(0x3a9)]('/'))_0x349997+=_0x2b8466(0x39c);const _0x28e1cd=normalize(_0x199eb5(_0x2d5a93,_0x349997));if(!_0x28e1cd[_0x2b8466(0x2ed)](_0x2d5a93+sep)&&_0x28e1cd!==_0x2d5a93)return _0x4774c3[_0x2b8466(0x2d7)]=0x193,_0x2b8466(0x2ec);let _0x3ed57c=_0x28e1cd;_0x286eff(_0x3ed57c)&&_0x2209a8(_0x3ed57c)[_0x2b8466(0x1e8)]()&&(_0x3ed57c=_0x199eb5(_0x3ed57c,_0x2b8466(0x39c)));if(!_0x286eff(_0x3ed57c)||!_0x2209a8(_0x3ed57c)[_0x2b8466(0x2ea)]())return _0x4774c3[_0x2b8466(0x2d7)]=0x194,_0x2b8466(0x2b3);return _0x4774c3[_0x2b8466(0x23f)][_0x2b8466(0x25b)]=contentType(_0x3ed57c),_0x4774c3[_0x2b8466(0x23f)]['cache-control']=_0x2b8466(0x3c0),_0x4774c3[_0x2b8466(0x23f)][_0x2b8466(0x2ad)]='*',Bun['file'](_0x3ed57c);});import{Elysia as _0x155ea5}from'elysia';function ok(_0xbc3353){const _0x5385a1=_0x4727c2;return{'code':RES_CODE[_0x5385a1(0x2f8)],'message':'success','data':_0xbc3353??null};}function fail(_0xf0d91d,_0x501207=RES_CODE[_0x4727c2(0x34c)]){return{'code':_0x501207,'message':_0xf0d91d};}async function handleExt(_0x1bad81){const _0x112904=_0x4727c2,_0x7a2010=_0x1bad81[_0x112904(0x3aa)][_0x112904(0x2d3)];if(!_0x7a2010||!/^[a-zA-Z0-9_-]+$/[_0x112904(0x298)](_0x7a2010))return _0x1bad81[_0x112904(0x2fc)][_0x112904(0x2d7)]=0x190,fail(_0x112904(0x36e));const _0x1f0e0e=String(_0x1bad81['params']['*']||''),_0x3da807=('/'+_0x1f0e0e)[_0x112904(0x244)](/\/+/g,'/'),_0x10acf9=Context[_0x112904(0x389)](),_0x30714c=ModuleRegistry['get'](_0x7a2010);if(!_0x30714c)return _0x1bad81['set'][_0x112904(0x2d7)]=0x194,fail(_0x112904(0x2c5));const _0x52d58b=_0x1bad81['request'][_0x112904(0x269)]['toUpperCase'](),_0x4ac05b=_0x3da807[_0x112904(0x244)](/\/+$/,'')||'/',_0x22fd2f=_0x30714c[_0x112904(0x1e0)][_0x112904(0x217)](_0x26161f=>_0x26161f[_0x112904(0x269)]===_0x52d58b&&_0x26161f[_0x112904(0x2b5)]===_0x4ac05b);if(!_0x22fd2f)return _0x1bad81[_0x112904(0x2fc)][_0x112904(0x2d7)]=0x194,fail(_0x112904(0x396));if(_0x22fd2f['perms']&&!_0x10acf9?.['isSuper']){const _0x4aeaa3=_0x10acf9?.[_0x112904(0x2b6)]??[];if(!_0x4aeaa3[_0x112904(0x395)](_0x22fd2f['perms']))return _0x1bad81[_0x112904(0x2d7)](0x193);}const _0x684fb4=await ModuleRegistry['dispatch'](_0x7a2010,_0x52d58b,_0x3da807,{'body':_0x1bad81[_0x112904(0x3ba)],'query':_0x1bad81['query']??{},'params':_0x1bad81[_0x112904(0x3aa)],'headers':_0x1bad81[_0x112904(0x34d)][_0x112904(0x23f)],'adminId':_0x10acf9?.[_0x112904(0x2fb)]});if(!_0x684fb4['ok'])return _0x1bad81[_0x112904(0x2fc)][_0x112904(0x2d7)]=_0x684fb4['status'],fail(_0x684fb4[_0x112904(0x318)]);return ok(_0x684fb4['data']);}function createModuleGateway(_0x3585e2){const _0x243066=_0x4727c2;return new _0x155ea5({'name':'module-gateway'})['use'](_0x3585e2['adminAuth'])[_0x243066(0x2f5)]('/admin/ext/:key/*',handleExt,{'adminAuth':!![]})[_0x243066(0x2f5)](_0x243066(0x314),handleExt,{'adminAuth':!![]});}import{Elysia as _0x1059e1}from'elysia';function defineAuthMacro(_0x562de0,_0x555cc8){const _0x4f9467=_0x4727c2;return new _0x1059e1({'name':_0x562de0+_0x4f9467(0x22e)})['macro']({[_0x562de0]:{'resolve':_0x555cc8}})['as'](_0x4f9467(0x39a));}var package_default={'name':_0x4727c2(0x234),'version':_0x4727c2(0x205),'description':_0x4727c2(0x3a2),'license':'MIT','type':_0x4727c2(0x265),'files':[_0x4727c2(0x22c),_0x4727c2(0x2a5),_0x4727c2(0x2fd)],'main':_0x4727c2(0x2f3),'types':_0x4727c2(0x371),'exports':{'.':{'types':_0x4727c2(0x371),'import':_0x4727c2(0x2f3),'default':_0x4727c2(0x2f3)},'./server':{'types':_0x4727c2(0x214),'import':_0x4727c2(0x38b),'default':_0x4727c2(0x38b)},'./admin':{'types':'./dist/admin/index.d.ts','import':_0x4727c2(0x25f),'default':'./dist/admin/index.js'},'./admin/*':_0x4727c2(0x2b2),'./admin/styles/base.css':_0x4727c2(0x299),'./typings/*':_0x4727c2(0x26a)},'scripts':{'build:server':_0x4727c2(0x367),'build:admin':_0x4727c2(0x225),'build':_0x4727c2(0x398),'obfuscate':_0x4727c2(0x2cf),'build:obfuscate':_0x4727c2(0x334),'prepare':_0x4727c2(0x226),'prepublishOnly':_0x4727c2(0x226)},'peerDependencies':{'elysia':'>=1.0.0','reflect-metadata':_0x4727c2(0x264),'drizzle-orm':'>=0.30.0','drizzle-zod':'>=0.5.0','vue':_0x4727c2(0x2e0),'vue-router':_0x4727c2(0x33b),'pinia':_0x4727c2(0x1eb),'vue-sonner':_0x4727c2(0x1eb),'@vueuse/core':_0x4727c2(0x39b),'clsx':_0x4727c2(0x1eb),'tailwind-merge':_0x4727c2(0x1eb),'dompurify':_0x4727c2(0x1dd),'marked':_0x4727c2(0x216)},'peerDependenciesMeta':{'drizzle-orm':{'optional':!![]},'drizzle-zod':{'optional':!![]},'vue':{'optional':!![]},'vue-router':{'optional':!![]},'pinia':{'optional':!![]},'vue-sonner':{'optional':!![]},'@vueuse/core':{'optional':!![]},'clsx':{'optional':!![]},'tailwind-merge':{'optional':!![]},'dompurify':{'optional':!![]},'marked':{'optional':!![]}},'devDependencies':{'bun-types':_0x4727c2(0x377),'drizzle-orm':_0x4727c2(0x377),'drizzle-zod':'^0.8.3','elysia':_0x4727c2(0x377),'javascript-obfuscator':'^5.4.7','reflect-metadata':'^0.2.2','typescript':_0x4727c2(0x377)},'dependencies':{'@bogeychan/elysia-logger':'^0.1.10','@elysiajs/openapi':_0x4727c2(0x208),'pino':_0x4727c2(0x228),'pino-pretty':_0x4727c2(0x1e7)}},version=package_default[_0x4727c2(0x231)];function _0x1a3d(_0x20edc5,_0x5c4b88){_0x20edc5=_0x20edc5-0x1da;const _0x35d74e=_0x35d7();let _0x1a3df9=_0x35d74e[_0x20edc5];if(_0x1a3d['sdRDvN']===undefined){var _0x59a366=function(_0x5daf74){const _0x2f2017='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x59c491='',_0x124388='';for(let _0x2cd2ac=0x0,_0x1b9a45,_0x3c367f,_0x426b38=0x0;_0x3c367f=_0x5daf74['charAt'](_0x426b38++);~_0x3c367f&&(_0x1b9a45=_0x2cd2ac%0x4?_0x1b9a45*0x40+_0x3c367f:_0x3c367f,_0x2cd2ac++%0x4)?_0x59c491+=String['fromCharCode'](0xff&_0x1b9a45>>(-0x2*_0x2cd2ac&0x6)):0x0){_0x3c367f=_0x2f2017['indexOf'](_0x3c367f);}for(let _0x25f2a8=0x0,_0x20c6cf=_0x59c491['length'];_0x25f2a8<_0x20c6cf;_0x25f2a8++){_0x124388+='%'+('00'+_0x59c491['charCodeAt'](_0x25f2a8)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x124388);};_0x1a3d['pwteJe']=_0x59a366,_0x1a3d['FoQjbz']={},_0x1a3d['sdRDvN']=!![];}const _0x2903ab=_0x35d74e[0x0],_0x3d5165=_0x20edc5+_0x2903ab,_0x1d11d6=_0x1a3d['FoQjbz'][_0x3d5165];return!_0x1d11d6?(_0x1a3df9=_0x1a3d['pwteJe'](_0x1a3df9),_0x1a3d['FoQjbz'][_0x3d5165]=_0x1a3df9):_0x1a3df9=_0x1d11d6,_0x1a3df9;}export{vome,version,tableHasDepartmentId,syncColumnCommentsToPg,scanFiles,resolveTenantScope,resolveDataScope,readPluginScript,q,pPluginPath,pModulesPath,pModulePath,pDataPath,normalizeHost,noTenant,noDataScope,microApps,loadPluginClass,loadModuleHandlers,listProviders,listControllers,isTenantEnabled,isEpsEnabled,isCommException,getRepository,getEnv,getColumnComments,entitySchemas,defineAuthMacro,createModuleGateway,columnComments,baseColumns,attachCrudRoutes,applyRowScopes,applyDataScopeWhere,appendInjectMeta,VomeConfig,Use,ScopeEnum,Repository,RES_CODE,Query,Put,Public,Provide,Post,Perms,Patch,Param,ModuleRegistry,Logger,Ioc,InjectRepository,Inject,IgnorePerms,Get,Eps,Delete,DbStore,Controller,Context,CommException,Body,BaseService,BasePlugin,BaseController,BASE_COLUMN_COMMENTS,App};
|