asaihost-nodejs 0.0.9 → 0.0.10
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/InterventionLog-WNVDQFAH.cjs.map +1 -1
- package/dist/LogStore-AP4T2CFD.cjs.map +1 -1
- package/dist/asaihost-nodejs.cjs +684 -492
- package/dist/asaihost-nodejs.cjs.map +1 -1
- package/dist/asaihost-nodejs.es.js +291 -99
- package/dist/asaihost-nodejs.es.js.map +1 -1
- package/dist/chunk-2BCIIKRG.cjs.map +1 -1
- package/dist/{chunk-OTL2B4WS.es.js → chunk-3E4Y5ATG.es.js} +2 -2
- package/dist/{chunk-ZK4O4Z2O.cjs → chunk-5EWEKXQI.cjs} +20 -20
- package/dist/chunk-5EWEKXQI.cjs.map +1 -0
- package/dist/chunk-ARHPHWT5.cjs.map +1 -1
- package/dist/{chunk-GXOFLFFW.cjs → chunk-FRPN33BY.cjs} +3 -2
- package/dist/chunk-FRPN33BY.cjs.map +1 -0
- package/dist/{chunk-WXW5DYNU.cjs → chunk-H2QP5J7X.cjs} +9 -9
- package/dist/chunk-H2QP5J7X.cjs.map +1 -0
- package/dist/chunk-HR5JKN7Y.cjs.map +1 -1
- package/dist/{chunk-BOIRAQXE.es.js → chunk-M3NURHGU.es.js} +2 -1
- package/dist/chunk-O6LVLSNB.cjs.map +1 -1
- package/dist/chunk-OCEBEEP5.cjs.map +1 -1
- package/dist/chunk-SMVZ3ZDJ.cjs.map +1 -1
- package/dist/chunk-U2YJH2RW.cjs.map +1 -1
- package/dist/{chunk-5WJQD4RZ.es.js → chunk-UKZ3DP37.es.js} +3 -3
- package/dist/intervention-hooks-4NAAAZK3.cjs.map +1 -1
- package/dist/log-alert-LAJ6VSAG.cjs.map +1 -1
- package/dist/log-formats-TUXGMCCU.cjs.map +1 -1
- package/dist/{password-4P7IZUDQ.es.js → password-2ZBHQQBF.es.js} +3 -3
- package/dist/password-T762KJOI.cjs +20 -0
- package/dist/password-T762KJOI.cjs.map +1 -0
- package/dist/user-store-6QNAL4CK.cjs +12 -0
- package/dist/user-store-6QNAL4CK.cjs.map +1 -0
- package/dist/{user-store-FXD2N55G.es.js → user-store-ZI67TXSI.es.js} +3 -3
- package/package.json +1 -1
- package/dist/chunk-GXOFLFFW.cjs.map +0 -1
- package/dist/chunk-WXW5DYNU.cjs.map +0 -1
- package/dist/chunk-ZK4O4Z2O.cjs.map +0 -1
- package/dist/password-MDYRL6ZD.cjs +0 -20
- package/dist/password-MDYRL6ZD.cjs.map +0 -1
- package/dist/user-store-55HOLHEM.cjs +0 -12
- package/dist/user-store-55HOLHEM.cjs.map +0 -1
- /package/dist/{chunk-OTL2B4WS.es.js.map → chunk-3E4Y5ATG.es.js.map} +0 -0
- /package/dist/{chunk-BOIRAQXE.es.js.map → chunk-M3NURHGU.es.js.map} +0 -0
- /package/dist/{chunk-5WJQD4RZ.es.js.map → chunk-UKZ3DP37.es.js.map} +0 -0
- /package/dist/{password-4P7IZUDQ.es.js.map → password-2ZBHQQBF.es.js.map} +0 -0
- /package/dist/{user-store-FXD2N55G.es.js.map → user-store-ZI67TXSI.es.js.map} +0 -0
|
@@ -50,7 +50,7 @@ import {
|
|
|
50
50
|
secureCompare,
|
|
51
51
|
validatePasswordChange,
|
|
52
52
|
verifyPassword
|
|
53
|
-
} from "./chunk-
|
|
53
|
+
} from "./chunk-3E4Y5ATG.es.js";
|
|
54
54
|
import {
|
|
55
55
|
USER_LV,
|
|
56
56
|
applySecretsToHostConfig,
|
|
@@ -62,20 +62,21 @@ import {
|
|
|
62
62
|
resolveHttpsCertFromPaths,
|
|
63
63
|
stripForbiddenSecretsFromHostConfig,
|
|
64
64
|
validateAsaiSecrets
|
|
65
|
-
} from "./chunk-
|
|
65
|
+
} from "./chunk-UKZ3DP37.es.js";
|
|
66
66
|
import {
|
|
67
67
|
getDefaultResetPassword,
|
|
68
68
|
getPasswordPolicy,
|
|
69
69
|
getPermissionThreshold,
|
|
70
70
|
getPublicSecurityConfig,
|
|
71
71
|
getUserLevelConfigSync,
|
|
72
|
+
getUserStoreConfig,
|
|
72
73
|
isPasswordExpired,
|
|
73
74
|
isValidUserLv,
|
|
74
75
|
loadUserLevelConfig,
|
|
75
76
|
resolveRoleForLevel,
|
|
76
77
|
saveUserLevelConfig,
|
|
77
78
|
validatePasswordWithPolicy
|
|
78
|
-
} from "./chunk-
|
|
79
|
+
} from "./chunk-M3NURHGU.es.js";
|
|
79
80
|
import {
|
|
80
81
|
getDataServerForAsDb
|
|
81
82
|
} from "./chunk-ZQBHJRAO.es.js";
|
|
@@ -1000,6 +1001,11 @@ async function clearStaleWsIfDead($asai, hostdir, us, existingWs) {
|
|
|
1000
1001
|
if (map?.[us]) delete map[us];
|
|
1001
1002
|
return true;
|
|
1002
1003
|
}
|
|
1004
|
+
if (existingWs._asaiKicked) {
|
|
1005
|
+
terminateWs(existingWs);
|
|
1006
|
+
if (map?.[us] === existingWs) delete map[us];
|
|
1007
|
+
return true;
|
|
1008
|
+
}
|
|
1003
1009
|
if (!isWsStillActive(existingWs)) {
|
|
1004
1010
|
terminateWs(existingWs);
|
|
1005
1011
|
if (map?.[us] === existingWs) delete map[us];
|
|
@@ -1025,22 +1031,38 @@ function getWsUserinfo(req, $asai) {
|
|
|
1025
1031
|
}
|
|
1026
1032
|
__name(getWsUserinfo, "getWsUserinfo");
|
|
1027
1033
|
function listOnlineWsUsers($asai, hostdir) {
|
|
1034
|
+
return listOnlineWsEntries($asai, hostdir).map((e) => e.us);
|
|
1035
|
+
}
|
|
1036
|
+
__name(listOnlineWsUsers, "listOnlineWsUsers");
|
|
1037
|
+
function listOnlineWsEntries($asai, hostdir) {
|
|
1028
1038
|
const users = [];
|
|
1039
|
+
const seen = /* @__PURE__ */ new Set();
|
|
1029
1040
|
const map = $asai.connectionsws || {};
|
|
1030
1041
|
const dirs = hostdir ? [hostdir] : Object.keys(map);
|
|
1031
1042
|
for (const dir of dirs) {
|
|
1032
1043
|
for (const [us, ws2] of Object.entries(map[dir] || {})) {
|
|
1033
1044
|
if (!us || us === "asai") continue;
|
|
1034
1045
|
if (isWsStillActive(ws2)) {
|
|
1035
|
-
|
|
1046
|
+
if (seen.has(us)) continue;
|
|
1047
|
+
seen.add(us);
|
|
1048
|
+
const rawLv = ws2?.Userinfo?.[1];
|
|
1049
|
+
if (rawLv === "" || rawLv == null) {
|
|
1050
|
+
users.push({ us, lv: null });
|
|
1051
|
+
} else {
|
|
1052
|
+
const lvNum = Number(rawLv);
|
|
1053
|
+
users.push({
|
|
1054
|
+
us,
|
|
1055
|
+
lv: Number.isFinite(lvNum) ? lvNum : null
|
|
1056
|
+
});
|
|
1057
|
+
}
|
|
1036
1058
|
} else if (map[dir]?.[us] === ws2) {
|
|
1037
1059
|
delete map[dir][us];
|
|
1038
1060
|
}
|
|
1039
1061
|
}
|
|
1040
1062
|
}
|
|
1041
|
-
return
|
|
1063
|
+
return users;
|
|
1042
1064
|
}
|
|
1043
|
-
__name(
|
|
1065
|
+
__name(listOnlineWsEntries, "listOnlineWsEntries");
|
|
1044
1066
|
function isUserOnlineOnWs($asai, us, hostdir) {
|
|
1045
1067
|
if (!us || us === "asai") return false;
|
|
1046
1068
|
const map = $asai.connectionsws || {};
|
|
@@ -1054,19 +1076,73 @@ function isUserOnlineOnWs($asai, us, hostdir) {
|
|
|
1054
1076
|
return false;
|
|
1055
1077
|
}
|
|
1056
1078
|
__name(isUserOnlineOnWs, "isUserOnlineOnWs");
|
|
1057
|
-
function kickUserWs($asai, us, hostdir) {
|
|
1079
|
+
async function kickUserWs($asai, us, hostdir) {
|
|
1058
1080
|
if (!us || us === "asai") return;
|
|
1059
1081
|
const map = $asai.connectionsws || {};
|
|
1060
1082
|
const dirs = hostdir ? [hostdir] : Object.keys(map);
|
|
1083
|
+
const waits = [];
|
|
1061
1084
|
for (const dir of dirs) {
|
|
1062
1085
|
const ws2 = map[dir]?.[us];
|
|
1063
1086
|
if (!ws2) continue;
|
|
1087
|
+
if (map[dir]?.[us] === ws2) delete map[dir][us];
|
|
1064
1088
|
try {
|
|
1065
|
-
ws2.
|
|
1089
|
+
ws2._asaiKicked = Date.now();
|
|
1066
1090
|
} catch {
|
|
1067
1091
|
}
|
|
1068
|
-
|
|
1092
|
+
waits.push(
|
|
1093
|
+
new Promise((resolve6) => {
|
|
1094
|
+
let done = false;
|
|
1095
|
+
const finish = /* @__PURE__ */ __name(() => {
|
|
1096
|
+
if (done) return;
|
|
1097
|
+
done = true;
|
|
1098
|
+
try {
|
|
1099
|
+
ws2.off?.("close", finish);
|
|
1100
|
+
} catch {
|
|
1101
|
+
}
|
|
1102
|
+
resolve6();
|
|
1103
|
+
}, "finish");
|
|
1104
|
+
try {
|
|
1105
|
+
ws2.once?.("close", finish);
|
|
1106
|
+
} catch {
|
|
1107
|
+
}
|
|
1108
|
+
const payload = JSON.stringify({
|
|
1109
|
+
ty: "publish/web",
|
|
1110
|
+
db: {
|
|
1111
|
+
exit: 1,
|
|
1112
|
+
type: "err",
|
|
1113
|
+
lang: "forcedout",
|
|
1114
|
+
langpm: `${us}`,
|
|
1115
|
+
con: `${us} forced out by another login`
|
|
1116
|
+
}
|
|
1117
|
+
});
|
|
1118
|
+
const hardClose = /* @__PURE__ */ __name(() => {
|
|
1119
|
+
try {
|
|
1120
|
+
if (typeof ws2.terminate === "function") ws2.terminate();
|
|
1121
|
+
else ws2.close();
|
|
1122
|
+
} catch {
|
|
1123
|
+
try {
|
|
1124
|
+
ws2.close();
|
|
1125
|
+
} catch {
|
|
1126
|
+
}
|
|
1127
|
+
}
|
|
1128
|
+
}, "hardClose");
|
|
1129
|
+
try {
|
|
1130
|
+
ws2.send(payload, () => {
|
|
1131
|
+
hardClose();
|
|
1132
|
+
finish();
|
|
1133
|
+
});
|
|
1134
|
+
} catch {
|
|
1135
|
+
hardClose();
|
|
1136
|
+
finish();
|
|
1137
|
+
}
|
|
1138
|
+
setTimeout(() => {
|
|
1139
|
+
hardClose();
|
|
1140
|
+
finish();
|
|
1141
|
+
}, 150);
|
|
1142
|
+
})
|
|
1143
|
+
);
|
|
1069
1144
|
}
|
|
1145
|
+
if (waits.length) await Promise.all(waits);
|
|
1070
1146
|
}
|
|
1071
1147
|
__name(kickUserWs, "kickUserWs");
|
|
1072
1148
|
async function removeSessionOnWsClose($asai, us, token) {
|
|
@@ -1109,7 +1185,8 @@ async function isOkWs($asai, hostdir, ws2, _req, hostcfg) {
|
|
|
1109
1185
|
rejectIncomingWs(ws2, {
|
|
1110
1186
|
lang: "pageworking",
|
|
1111
1187
|
langpm: `${us}`,
|
|
1112
|
-
con: `${us} page already running
|
|
1188
|
+
con: `${us} page already running`,
|
|
1189
|
+
online: listOnlineWsEntries($asai, hostdir)
|
|
1113
1190
|
});
|
|
1114
1191
|
return false;
|
|
1115
1192
|
}
|
|
@@ -1125,7 +1202,8 @@ async function isOkWs($asai, hostdir, ws2, _req, hostcfg) {
|
|
|
1125
1202
|
rejectIncomingWs(ws2, {
|
|
1126
1203
|
lang: "logged",
|
|
1127
1204
|
langpm: `${us}`,
|
|
1128
|
-
con: `${us} logged in
|
|
1205
|
+
con: `${us} logged in!`,
|
|
1206
|
+
online: listOnlineWsEntries($asai, hostdir)
|
|
1129
1207
|
});
|
|
1130
1208
|
return false;
|
|
1131
1209
|
}
|
|
@@ -1137,19 +1215,22 @@ async function isOkWs($asai, hostdir, ws2, _req, hostcfg) {
|
|
|
1137
1215
|
(item) => item.Userinfo?.[2] === tk && item.Userinfo?.[0] !== us
|
|
1138
1216
|
);
|
|
1139
1217
|
const maxOnline = hostcfg.maxonline || 100;
|
|
1218
|
+
const online = listOnlineWsEntries($asai, hostdir);
|
|
1140
1219
|
if (sameTkWs) {
|
|
1141
1220
|
rejectIncomingWs(ws2, {
|
|
1142
1221
|
lang: "loggedsametk",
|
|
1143
1222
|
langpm: `${us}(${sameTkWs.Userinfo[0]})`,
|
|
1144
|
-
con: `${us}(${sameTkWs.Userinfo[0]}) logged in
|
|
1223
|
+
con: `${us}(${sameTkWs.Userinfo[0]}) logged in!`,
|
|
1224
|
+
online
|
|
1145
1225
|
});
|
|
1146
1226
|
return false;
|
|
1147
1227
|
}
|
|
1148
|
-
if (
|
|
1228
|
+
if (online.length >= maxOnline) {
|
|
1149
1229
|
rejectIncomingWs(ws2, {
|
|
1150
1230
|
lang: "maxlogged",
|
|
1151
1231
|
langpm: `${maxOnline}`,
|
|
1152
|
-
con: `max ${maxOnline} users online
|
|
1232
|
+
con: `max ${maxOnline} users online!`,
|
|
1233
|
+
online
|
|
1153
1234
|
});
|
|
1154
1235
|
return false;
|
|
1155
1236
|
}
|
|
@@ -1533,11 +1614,11 @@ function createSkipChecker($asai) {
|
|
|
1533
1614
|
}
|
|
1534
1615
|
if (exact.size === 0 && prefixes.length === 0) return () => false;
|
|
1535
1616
|
return (url) => {
|
|
1536
|
-
const
|
|
1537
|
-
if (!
|
|
1538
|
-
if (exact.has(
|
|
1617
|
+
const path9 = normalizeRequestPath(url);
|
|
1618
|
+
if (!path9) return false;
|
|
1619
|
+
if (exact.has(path9)) return true;
|
|
1539
1620
|
for (let i = 0; i < prefixes.length; i++) {
|
|
1540
|
-
if (
|
|
1621
|
+
if (path9.startsWith(prefixes[i])) return true;
|
|
1541
1622
|
}
|
|
1542
1623
|
return false;
|
|
1543
1624
|
};
|
|
@@ -2424,7 +2505,7 @@ async function attachServerUserLevel(req, $asai) {
|
|
|
2424
2505
|
if (!Array.isArray(userinfo) || !userinfo[0]) return;
|
|
2425
2506
|
const us = String(userinfo[0]);
|
|
2426
2507
|
try {
|
|
2427
|
-
const { createUserStore: createUserStore2 } = await import("./user-store-
|
|
2508
|
+
const { createUserStore: createUserStore2 } = await import("./user-store-ZI67TXSI.es.js");
|
|
2428
2509
|
const user = await createUserStore2($asai).findByUsername(us);
|
|
2429
2510
|
if (user && user.status === "active") {
|
|
2430
2511
|
req._serverUser = { us: user.us, lv: user.lv, status: user.status };
|
|
@@ -2455,11 +2536,11 @@ function getSecurityConfig($asai) {
|
|
|
2455
2536
|
return $asai?.hostconfig?.security || {};
|
|
2456
2537
|
}
|
|
2457
2538
|
__name(getSecurityConfig, "getSecurityConfig");
|
|
2458
|
-
function pathMatchesPattern(
|
|
2539
|
+
function pathMatchesPattern(path9, pattern) {
|
|
2459
2540
|
if (pattern.endsWith("*")) {
|
|
2460
|
-
return
|
|
2541
|
+
return path9.startsWith(pattern.slice(0, -1));
|
|
2461
2542
|
}
|
|
2462
|
-
return
|
|
2543
|
+
return path9 === pattern;
|
|
2463
2544
|
}
|
|
2464
2545
|
__name(pathMatchesPattern, "pathMatchesPattern");
|
|
2465
2546
|
function isAuthSkipped($asai, pathname) {
|
|
@@ -4066,6 +4147,37 @@ async function purgeOfflineSessions($asai, hostdir, store) {
|
|
|
4066
4147
|
__name(purgeOfflineSessions, "purgeOfflineSessions");
|
|
4067
4148
|
|
|
4068
4149
|
// src/sysserver/api/login/index.ts
|
|
4150
|
+
import fs9 from "fs";
|
|
4151
|
+
import path4 from "path";
|
|
4152
|
+
async function resolveUserLv($asai, store, us, wsLv) {
|
|
4153
|
+
if (!us) return null;
|
|
4154
|
+
try {
|
|
4155
|
+
const user = await store.findByUsername(us);
|
|
4156
|
+
if (user && user.lv != null && Number.isFinite(Number(user.lv))) {
|
|
4157
|
+
return Number(user.lv);
|
|
4158
|
+
}
|
|
4159
|
+
} catch {
|
|
4160
|
+
}
|
|
4161
|
+
try {
|
|
4162
|
+
const cfg = getUserStoreConfig($asai);
|
|
4163
|
+
const dir = String(cfg?.opt?.dir || "");
|
|
4164
|
+
if (dir) {
|
|
4165
|
+
const base = path4.isAbsolute(dir) ? dir : path4.join(process.cwd(), dir);
|
|
4166
|
+
const safeUs = us.replace(/[\\/:*?"<>|]/g, "");
|
|
4167
|
+
const file = path4.join(base, "json", `${safeUs}.json`);
|
|
4168
|
+
if (safeUs && fs9.existsSync(file)) {
|
|
4169
|
+
const raw = JSON.parse(fs9.readFileSync(file, "utf8"));
|
|
4170
|
+
const lv = Number(raw?.lv);
|
|
4171
|
+
if (Number.isFinite(lv)) return lv;
|
|
4172
|
+
}
|
|
4173
|
+
}
|
|
4174
|
+
} catch {
|
|
4175
|
+
}
|
|
4176
|
+
if (wsLv === null || wsLv === void 0 || wsLv === "") return null;
|
|
4177
|
+
const n = Number(wsLv);
|
|
4178
|
+
return Number.isFinite(n) ? n : null;
|
|
4179
|
+
}
|
|
4180
|
+
__name(resolveUserLv, "resolveUserLv");
|
|
4069
4181
|
function getSecurity($asai) {
|
|
4070
4182
|
return $asai?.hostconfig?.security || {};
|
|
4071
4183
|
}
|
|
@@ -4229,10 +4341,7 @@ var login_default = /* @__PURE__ */ __name(($asai) => {
|
|
|
4229
4341
|
if (hostcfg.ckws) {
|
|
4230
4342
|
const existingWs = $asai.connectionsws?.[hostdir]?.[us];
|
|
4231
4343
|
if (existingWs) {
|
|
4232
|
-
|
|
4233
|
-
if (!cleared) {
|
|
4234
|
-
kickUserWs($asai, us, hostdir);
|
|
4235
|
-
}
|
|
4344
|
+
await clearStaleWsIfDead($asai, hostdir, us, existingWs);
|
|
4236
4345
|
}
|
|
4237
4346
|
}
|
|
4238
4347
|
const quotaCheck = await canLogin($asai, us, hostdir);
|
|
@@ -4279,6 +4388,56 @@ var login_default = /* @__PURE__ */ __name(($asai) => {
|
|
|
4279
4388
|
return sendFail(res, err?.message || err, opt);
|
|
4280
4389
|
}
|
|
4281
4390
|
}
|
|
4391
|
+
if (url.startsWith("/api/user/login/force/")) {
|
|
4392
|
+
try {
|
|
4393
|
+
const us = sanitizeString(String(req?.Userinfo?.[0] || ""), 64);
|
|
4394
|
+
if (!us) return sendErr(res, "AUTH_MISSING", void 0, opt);
|
|
4395
|
+
const myLv = Number(req?.Userinfo?.[1] ?? 0);
|
|
4396
|
+
const targetUs = sanitizeString(String(body?.targetUs || body?.us || ""), 64);
|
|
4397
|
+
const kicked = [];
|
|
4398
|
+
if (isUserOnlineOnWs($asai, us, hostdir)) {
|
|
4399
|
+
await kickUserWs($asai, us, hostdir);
|
|
4400
|
+
kicked.push(us);
|
|
4401
|
+
}
|
|
4402
|
+
const onlineRaw = listOnlineWsEntries($asai, hostdir).filter((e) => e.us !== us);
|
|
4403
|
+
const online = await Promise.all(
|
|
4404
|
+
onlineRaw.map(async (e) => ({
|
|
4405
|
+
us: e.us,
|
|
4406
|
+
lv: await resolveUserLv($asai, store, e.us, e.lv)
|
|
4407
|
+
}))
|
|
4408
|
+
);
|
|
4409
|
+
const candidates = targetUs ? online.filter((e) => e.us === targetUs) : online;
|
|
4410
|
+
for (const entry of candidates) {
|
|
4411
|
+
const entryLv = entry.lv == null ? NaN : Number(entry.lv);
|
|
4412
|
+
if (!Number.isFinite(entryLv) || myLv < entryLv) {
|
|
4413
|
+
if (targetUs) {
|
|
4414
|
+
return sendErr(res, "AUTH_FORBIDDEN", void 0, opt);
|
|
4415
|
+
}
|
|
4416
|
+
continue;
|
|
4417
|
+
}
|
|
4418
|
+
await kickUserWs($asai, entry.us, hostdir);
|
|
4419
|
+
kicked.push(entry.us);
|
|
4420
|
+
}
|
|
4421
|
+
if (!kicked.length && online.length) {
|
|
4422
|
+
return sendErr(res, "AUTH_FORBIDDEN", void 0, opt);
|
|
4423
|
+
}
|
|
4424
|
+
logSecurityEvent($asai, {
|
|
4425
|
+
type: "AUTH_SUCCESS",
|
|
4426
|
+
path: url,
|
|
4427
|
+
method: "POST",
|
|
4428
|
+
user: us,
|
|
4429
|
+
ip,
|
|
4430
|
+
detail: `force_login_kick:${kicked.join(",") || "none"}`
|
|
4431
|
+
});
|
|
4432
|
+
return sendSuccess(
|
|
4433
|
+
res,
|
|
4434
|
+
{ ok: true, us, kicked, online: listOnlineWsEntries($asai, hostdir) },
|
|
4435
|
+
opt
|
|
4436
|
+
);
|
|
4437
|
+
} catch (err) {
|
|
4438
|
+
return sendFail(res, err?.message || err, opt);
|
|
4439
|
+
}
|
|
4440
|
+
}
|
|
4282
4441
|
if (url.startsWith("/api/user/login/admin/kick/")) {
|
|
4283
4442
|
if (!await checkAdmin(req, url, getPermissionThreshold($asai, "adminWrite"))) {
|
|
4284
4443
|
return sendErr(res, "AUTH_FORBIDDEN", void 0, opt);
|
|
@@ -4292,7 +4451,7 @@ var login_default = /* @__PURE__ */ __name(($asai) => {
|
|
|
4292
4451
|
if (!isSessionUserOnline($asai, target.us, hostdir)) {
|
|
4293
4452
|
return sendErr(res, "SESSION_NOT_ONLINE", void 0, opt);
|
|
4294
4453
|
}
|
|
4295
|
-
kickUserWs($asai, target.us, hostdir);
|
|
4454
|
+
await kickUserWs($asai, target.us, hostdir);
|
|
4296
4455
|
await store.removeSession(sessionId);
|
|
4297
4456
|
const operator = String(req?.Userinfo?.[0] || "");
|
|
4298
4457
|
await logSessionTerminate($asai, {
|
|
@@ -4491,6 +4650,39 @@ var login_default = /* @__PURE__ */ __name(($asai) => {
|
|
|
4491
4650
|
await loadUserLevelConfig($asai);
|
|
4492
4651
|
return sendSuccess(res, getPublicSecurityConfig($asai, lang), opt);
|
|
4493
4652
|
}
|
|
4653
|
+
if (url.startsWith("/api/user/login/online/")) {
|
|
4654
|
+
try {
|
|
4655
|
+
const us = sanitizeString(String(req?.Userinfo?.[0] || ""), 64);
|
|
4656
|
+
if (!us) return sendErr(res, "AUTH_MISSING", void 0, opt);
|
|
4657
|
+
const rawOnline = listOnlineWsEntries($asai, hostdir);
|
|
4658
|
+
const online = await Promise.all(
|
|
4659
|
+
rawOnline.map(async (e) => ({
|
|
4660
|
+
us: e.us,
|
|
4661
|
+
lv: await resolveUserLv($asai, store, e.us, e.lv)
|
|
4662
|
+
}))
|
|
4663
|
+
);
|
|
4664
|
+
const rawMy = req?.Userinfo?.[1];
|
|
4665
|
+
const wsMyLv = rawMy === null || rawMy === void 0 || rawMy === "" ? null : Number(rawMy);
|
|
4666
|
+
const myLvOut = await resolveUserLv(
|
|
4667
|
+
$asai,
|
|
4668
|
+
store,
|
|
4669
|
+
us,
|
|
4670
|
+
Number.isFinite(wsMyLv) ? wsMyLv : null
|
|
4671
|
+
);
|
|
4672
|
+
return sendSuccess(
|
|
4673
|
+
res,
|
|
4674
|
+
{
|
|
4675
|
+
us,
|
|
4676
|
+
lv: myLvOut,
|
|
4677
|
+
online,
|
|
4678
|
+
maxonline: $asai.getHost?.(hostdir)?.maxonline ?? 100
|
|
4679
|
+
},
|
|
4680
|
+
opt
|
|
4681
|
+
);
|
|
4682
|
+
} catch (err) {
|
|
4683
|
+
return sendFail(res, err?.message || err, opt);
|
|
4684
|
+
}
|
|
4685
|
+
}
|
|
4494
4686
|
if (url.startsWith("/api/user/login/admin/levels/")) {
|
|
4495
4687
|
if (!await checkAdmin(req, url, getPermissionThreshold($asai, "adminRead"))) {
|
|
4496
4688
|
return sendErr(res, "AUTH_FORBIDDEN", void 0, opt);
|
|
@@ -4613,10 +4805,10 @@ var As_default = {
|
|
|
4613
4805
|
return relativePath;
|
|
4614
4806
|
},
|
|
4615
4807
|
//创建多层文件夹 同步
|
|
4616
|
-
ensureDir(
|
|
4808
|
+
ensureDir(fs12, relativePath) {
|
|
4617
4809
|
const absPathDir = this.toDirPath(relativePath);
|
|
4618
4810
|
const absPath = this.toAbsolutePath(relativePath);
|
|
4619
|
-
if (!
|
|
4811
|
+
if (!fs12.existsSync(absPath)) {
|
|
4620
4812
|
let pathTmp = "";
|
|
4621
4813
|
absPathDir.split("/").forEach((el) => {
|
|
4622
4814
|
if (el) {
|
|
@@ -4624,8 +4816,8 @@ var As_default = {
|
|
|
4624
4816
|
pathTmp += "/";
|
|
4625
4817
|
}
|
|
4626
4818
|
pathTmp += el;
|
|
4627
|
-
if (!
|
|
4628
|
-
if (!
|
|
4819
|
+
if (!fs12.existsSync(pathTmp)) {
|
|
4820
|
+
if (!fs12.mkdirSync(pathTmp, { recursive: true })) {
|
|
4629
4821
|
return absPath;
|
|
4630
4822
|
}
|
|
4631
4823
|
}
|
|
@@ -4634,10 +4826,10 @@ var As_default = {
|
|
|
4634
4826
|
}
|
|
4635
4827
|
return absPath;
|
|
4636
4828
|
},
|
|
4637
|
-
makeDir(
|
|
4829
|
+
makeDir(fs12, filePaths) {
|
|
4638
4830
|
return new Promise((resolve6, reject) => {
|
|
4639
4831
|
try {
|
|
4640
|
-
const newPath = this.ensureDir(
|
|
4832
|
+
const newPath = this.ensureDir(fs12, filePaths);
|
|
4641
4833
|
resolve6(newPath);
|
|
4642
4834
|
} catch (err) {
|
|
4643
4835
|
reject(err);
|
|
@@ -5234,7 +5426,7 @@ var AsDb_default = /* @__PURE__ */ __name(($asai, cfg) => {
|
|
|
5234
5426
|
}, "default");
|
|
5235
5427
|
|
|
5236
5428
|
// src/sysserver/lib/common/reqWork.ts
|
|
5237
|
-
import * as
|
|
5429
|
+
import * as path5 from "path";
|
|
5238
5430
|
var reqWork_default = /* @__PURE__ */ __name(($asai) => {
|
|
5239
5431
|
function hostDefault2(mod) {
|
|
5240
5432
|
if (mod && typeof mod === "object" && "default" in mod) {
|
|
@@ -5250,16 +5442,16 @@ var reqWork_default = /* @__PURE__ */ __name(($asai) => {
|
|
|
5250
5442
|
throw new Error("Missing path");
|
|
5251
5443
|
}
|
|
5252
5444
|
const decoded = decodeURIComponent(String(rawPath));
|
|
5253
|
-
if (
|
|
5254
|
-
return
|
|
5445
|
+
if (path5.isAbsolute(decoded)) {
|
|
5446
|
+
return path5.normalize(decoded);
|
|
5255
5447
|
}
|
|
5256
5448
|
const rel = decoded.replace(/^\.(\/)?/, "");
|
|
5257
5449
|
const serverRoot = $asai?.serverRoot;
|
|
5258
5450
|
if (serverRoot && rel) {
|
|
5259
|
-
const absRoot =
|
|
5260
|
-
const abs =
|
|
5261
|
-
const relCheck =
|
|
5262
|
-
if (relCheck === "" || !relCheck.startsWith("..") && !
|
|
5451
|
+
const absRoot = path5.resolve(serverRoot);
|
|
5452
|
+
const abs = path5.resolve(absRoot, rel);
|
|
5453
|
+
const relCheck = path5.relative(absRoot, abs);
|
|
5454
|
+
if (relCheck === "" || !relCheck.startsWith("..") && !path5.isAbsolute(relCheck)) {
|
|
5263
5455
|
return abs;
|
|
5264
5456
|
}
|
|
5265
5457
|
}
|
|
@@ -5319,18 +5511,18 @@ __export(AsFs_exports, {
|
|
|
5319
5511
|
write: () => write,
|
|
5320
5512
|
writeJson: () => writeJson
|
|
5321
5513
|
});
|
|
5322
|
-
import
|
|
5323
|
-
import
|
|
5514
|
+
import fs10 from "fs/promises";
|
|
5515
|
+
import path6 from "path";
|
|
5324
5516
|
async function ensureFile(filePath) {
|
|
5325
|
-
const normalized =
|
|
5326
|
-
await
|
|
5327
|
-
const fh = await
|
|
5517
|
+
const normalized = path6.normalize(filePath);
|
|
5518
|
+
await fs10.mkdir(path6.dirname(normalized), { recursive: true });
|
|
5519
|
+
const fh = await fs10.open(normalized, "a");
|
|
5328
5520
|
await fh.close();
|
|
5329
5521
|
}
|
|
5330
5522
|
__name(ensureFile, "ensureFile");
|
|
5331
5523
|
async function pathExists(filePath) {
|
|
5332
5524
|
try {
|
|
5333
|
-
await
|
|
5525
|
+
await fs10.access(path6.normalize(filePath));
|
|
5334
5526
|
return true;
|
|
5335
5527
|
} catch {
|
|
5336
5528
|
return false;
|
|
@@ -5338,7 +5530,7 @@ async function pathExists(filePath) {
|
|
|
5338
5530
|
}
|
|
5339
5531
|
__name(pathExists, "pathExists");
|
|
5340
5532
|
async function readJson(filePath) {
|
|
5341
|
-
const raw = await
|
|
5533
|
+
const raw = await fs10.readFile(path6.normalize(filePath), "utf8");
|
|
5342
5534
|
return JSON.parse(raw);
|
|
5343
5535
|
}
|
|
5344
5536
|
__name(readJson, "readJson");
|
|
@@ -5349,34 +5541,34 @@ function resolvePathUnderBase(baseDir, relPath) {
|
|
|
5349
5541
|
if (relPath.includes("\0")) {
|
|
5350
5542
|
throw new Error("Invalid path");
|
|
5351
5543
|
}
|
|
5352
|
-
const base =
|
|
5353
|
-
const target =
|
|
5354
|
-
const rel =
|
|
5355
|
-
if (rel.startsWith("..") ||
|
|
5544
|
+
const base = path6.resolve(baseDir);
|
|
5545
|
+
const target = path6.resolve(base, relPath.replace(/\\/g, "/"));
|
|
5546
|
+
const rel = path6.relative(base, target);
|
|
5547
|
+
if (rel.startsWith("..") || path6.isAbsolute(rel)) {
|
|
5356
5548
|
throw new Error("Path not allowed");
|
|
5357
5549
|
}
|
|
5358
5550
|
return target;
|
|
5359
5551
|
}
|
|
5360
5552
|
__name(resolvePathUnderBase, "resolvePathUnderBase");
|
|
5361
5553
|
async function readLogDir(dir) {
|
|
5362
|
-
const resolved =
|
|
5363
|
-
const stats = await
|
|
5554
|
+
const resolved = path6.resolve(dir);
|
|
5555
|
+
const stats = await fs10.stat(resolved);
|
|
5364
5556
|
if (!stats.isDirectory()) {
|
|
5365
5557
|
throw new Error("Not a directory");
|
|
5366
5558
|
}
|
|
5367
|
-
const dirName =
|
|
5368
|
-
const entries = await
|
|
5559
|
+
const dirName = path6.basename(resolved);
|
|
5560
|
+
const entries = await fs10.readdir(resolved, { withFileTypes: true });
|
|
5369
5561
|
const children = await Promise.all(
|
|
5370
5562
|
entries.map(async (entry) => {
|
|
5371
|
-
const fullPath =
|
|
5372
|
-
const st = await
|
|
5563
|
+
const fullPath = path6.join(resolved, entry.name);
|
|
5564
|
+
const st = await fs10.stat(fullPath);
|
|
5373
5565
|
const dot = entry.name.lastIndexOf(".");
|
|
5374
5566
|
const type = entry.isDirectory() ? "dir" : dot > -1 ? entry.name.substring(dot) : "file";
|
|
5375
5567
|
return {
|
|
5376
5568
|
name: entry.name,
|
|
5377
5569
|
size: st.size,
|
|
5378
5570
|
time: st.mtime.toISOString(),
|
|
5379
|
-
path:
|
|
5571
|
+
path: path6.normalize(fullPath),
|
|
5380
5572
|
type,
|
|
5381
5573
|
created: st.birthtime.toISOString(),
|
|
5382
5574
|
permissions: st.mode.toString(8).slice(-3)
|
|
@@ -5387,7 +5579,7 @@ async function readLogDir(dir) {
|
|
|
5387
5579
|
name: dirName,
|
|
5388
5580
|
size: stats.size,
|
|
5389
5581
|
time: stats.mtime.toISOString(),
|
|
5390
|
-
path:
|
|
5582
|
+
path: path6.normalize(resolved),
|
|
5391
5583
|
type: "dir",
|
|
5392
5584
|
created: stats.birthtime.toISOString(),
|
|
5393
5585
|
permissions: stats.mode.toString(8).slice(-3),
|
|
@@ -5397,7 +5589,7 @@ async function readLogDir(dir) {
|
|
|
5397
5589
|
__name(readLogDir, "readLogDir");
|
|
5398
5590
|
async function removeFile(filePath) {
|
|
5399
5591
|
try {
|
|
5400
|
-
await
|
|
5592
|
+
await fs10.unlink(path6.normalize(filePath));
|
|
5401
5593
|
} catch (err) {
|
|
5402
5594
|
if (err?.code !== "ENOENT") throw err;
|
|
5403
5595
|
}
|
|
@@ -5405,13 +5597,13 @@ async function removeFile(filePath) {
|
|
|
5405
5597
|
__name(removeFile, "removeFile");
|
|
5406
5598
|
var remove = removeFile;
|
|
5407
5599
|
async function write(filePath, content) {
|
|
5408
|
-
const normalized =
|
|
5409
|
-
await
|
|
5410
|
-
await
|
|
5600
|
+
const normalized = path6.normalize(filePath);
|
|
5601
|
+
await fs10.mkdir(path6.dirname(normalized), { recursive: true });
|
|
5602
|
+
await fs10.writeFile(normalized, content, "utf8");
|
|
5411
5603
|
}
|
|
5412
5604
|
__name(write, "write");
|
|
5413
5605
|
async function read(filePath) {
|
|
5414
|
-
return
|
|
5606
|
+
return fs10.readFile(path6.normalize(filePath), "utf8");
|
|
5415
5607
|
}
|
|
5416
5608
|
__name(read, "read");
|
|
5417
5609
|
async function writeJson(filePath, data) {
|
|
@@ -5447,7 +5639,7 @@ __export(common_exports, {
|
|
|
5447
5639
|
toSetObject: () => toSetObject,
|
|
5448
5640
|
toWherePairs: () => toWherePairs
|
|
5449
5641
|
});
|
|
5450
|
-
import * as
|
|
5642
|
+
import * as path7 from "path";
|
|
5451
5643
|
function promisifySqlDb(query, sql) {
|
|
5452
5644
|
return new Promise((resolve6, reject) => {
|
|
5453
5645
|
query(sql, (err, result) => {
|
|
@@ -5512,11 +5704,11 @@ function toInsertRows(sql) {
|
|
|
5512
5704
|
}
|
|
5513
5705
|
__name(toInsertRows, "toInsertRows");
|
|
5514
5706
|
function isPathInside(baseDir, targetPath) {
|
|
5515
|
-
const base =
|
|
5516
|
-
const target =
|
|
5517
|
-
const relative5 =
|
|
5707
|
+
const base = path7.resolve(baseDir);
|
|
5708
|
+
const target = path7.resolve(targetPath);
|
|
5709
|
+
const relative5 = path7.relative(base, target);
|
|
5518
5710
|
if (!relative5) return true;
|
|
5519
|
-
return !relative5.startsWith("..") && !
|
|
5711
|
+
return !relative5.startsWith("..") && !path7.isAbsolute(relative5);
|
|
5520
5712
|
}
|
|
5521
5713
|
__name(isPathInside, "isPathInside");
|
|
5522
5714
|
function joinTablePath(table, ...segments) {
|
|
@@ -5697,8 +5889,8 @@ var Sql_default = {
|
|
|
5697
5889
|
};
|
|
5698
5890
|
|
|
5699
5891
|
// src/sysserver/db/src/file/Index.ts
|
|
5700
|
-
import * as
|
|
5701
|
-
import * as
|
|
5892
|
+
import * as fs11 from "fs";
|
|
5893
|
+
import * as path8 from "path";
|
|
5702
5894
|
function dbDriver(opt = {}) {
|
|
5703
5895
|
const { Sql, DbCommon } = opt;
|
|
5704
5896
|
const { isPathInside: isPathInside2, joinTablePath: joinTablePath2 } = DbCommon;
|
|
@@ -5712,20 +5904,20 @@ function dbDriver(opt = {}) {
|
|
|
5712
5904
|
this.fileDel = (config.del || 0) !== 0;
|
|
5713
5905
|
this.createDir = config.create || false;
|
|
5714
5906
|
const root = config.$asai?.serverRoot || getPrimaryServerRoot();
|
|
5715
|
-
this.baseDirAbs =
|
|
5907
|
+
this.baseDirAbs = path8.resolve(root, config.dir);
|
|
5716
5908
|
}
|
|
5717
5909
|
dbLog(...args) {
|
|
5718
5910
|
(this.config?.$asai?.$log || console.log)("FILE", ...args);
|
|
5719
5911
|
}
|
|
5720
5912
|
checkFile(file) {
|
|
5721
|
-
return
|
|
5913
|
+
return fs11.existsSync(this.getAbsPath(file, false));
|
|
5722
5914
|
}
|
|
5723
5915
|
/** 解析相对路径并限制在数据根目录内,防止路径穿越(跨平台) */
|
|
5724
5916
|
resolvePath(relPath) {
|
|
5725
5917
|
if (!relPath) {
|
|
5726
5918
|
return this.baseDirAbs;
|
|
5727
5919
|
}
|
|
5728
|
-
const abs =
|
|
5920
|
+
const abs = path8.isAbsolute(relPath) ? path8.normalize(relPath) : path8.resolve(this.baseDirAbs, relPath);
|
|
5729
5921
|
if (!isPathInside2(this.baseDirAbs, abs)) {
|
|
5730
5922
|
throw new Error("Path not allowed");
|
|
5731
5923
|
}
|
|
@@ -5739,15 +5931,15 @@ function dbDriver(opt = {}) {
|
|
|
5739
5931
|
if (!relPath) {
|
|
5740
5932
|
return "";
|
|
5741
5933
|
}
|
|
5742
|
-
return
|
|
5934
|
+
return path8.isAbsolute(relPath) ? path8.relative(this.baseDirAbs, relPath) : relPath;
|
|
5743
5935
|
}
|
|
5744
5936
|
ensureDir(relPath) {
|
|
5745
5937
|
const relative5 = this.normalizeRelPath(relPath);
|
|
5746
|
-
const dirPath =
|
|
5938
|
+
const dirPath = path8.dirname(relative5);
|
|
5747
5939
|
const absDir = this.resolvePath(dirPath === "." ? "" : dirPath);
|
|
5748
|
-
if (this.createDir && !
|
|
5940
|
+
if (this.createDir && !fs11.existsSync(absDir)) {
|
|
5749
5941
|
this.dbLog("mkdir", "[MKDIR]", absDir);
|
|
5750
|
-
|
|
5942
|
+
fs11.mkdirSync(absDir, { recursive: true });
|
|
5751
5943
|
}
|
|
5752
5944
|
return absDir;
|
|
5753
5945
|
}
|
|
@@ -5763,34 +5955,34 @@ function dbDriver(opt = {}) {
|
|
|
5763
5955
|
}
|
|
5764
5956
|
deldir(relativePath) {
|
|
5765
5957
|
const absPath = this.resolvePath(relativePath);
|
|
5766
|
-
if (!
|
|
5958
|
+
if (!fs11.existsSync(absPath)) {
|
|
5767
5959
|
return;
|
|
5768
5960
|
}
|
|
5769
5961
|
this.dbLog("delete", "[RMDIR]", absPath);
|
|
5770
|
-
const entries =
|
|
5962
|
+
const entries = fs11.readdirSync(absPath, { withFileTypes: true });
|
|
5771
5963
|
for (const entry of entries) {
|
|
5772
|
-
const current =
|
|
5964
|
+
const current = path8.join(absPath, entry.name);
|
|
5773
5965
|
if (entry.isDirectory()) {
|
|
5774
|
-
this.deldir(
|
|
5966
|
+
this.deldir(path8.join(relativePath, entry.name));
|
|
5775
5967
|
} else {
|
|
5776
5968
|
this.dbLog("delete", "[UNLINK]", current);
|
|
5777
|
-
|
|
5969
|
+
fs11.unlinkSync(current);
|
|
5778
5970
|
}
|
|
5779
5971
|
}
|
|
5780
|
-
|
|
5972
|
+
fs11.rmdirSync(absPath);
|
|
5781
5973
|
}
|
|
5782
5974
|
getReadPath(file, sql) {
|
|
5783
5975
|
const candidates = [];
|
|
5784
5976
|
if (sql?.filename) {
|
|
5785
|
-
candidates.push({ dir:
|
|
5786
|
-
candidates.push({ dir:
|
|
5977
|
+
candidates.push({ dir: path8.join(file, sql.filename) });
|
|
5978
|
+
candidates.push({ dir: path8.join(file + ".delete" + this.fileExt, sql.filename) });
|
|
5787
5979
|
} else {
|
|
5788
5980
|
candidates.push({ dir: file });
|
|
5789
5981
|
candidates.push({ dir: file + this.fileExt + ".delete" });
|
|
5790
5982
|
}
|
|
5791
5983
|
for (const candidate of candidates) {
|
|
5792
5984
|
const abs = this.getAbsPath(candidate.dir, false);
|
|
5793
|
-
if (
|
|
5985
|
+
if (fs11.existsSync(abs)) {
|
|
5794
5986
|
return { path: abs, dir: candidate.dir };
|
|
5795
5987
|
}
|
|
5796
5988
|
}
|
|
@@ -5802,13 +5994,13 @@ function dbDriver(opt = {}) {
|
|
|
5802
5994
|
return { path: "", dir: read2.dir };
|
|
5803
5995
|
}
|
|
5804
5996
|
if (sql?.filename) {
|
|
5805
|
-
return { path:
|
|
5997
|
+
return { path: path8.dirname(read2.path), dir: path8.dirname(read2.dir) };
|
|
5806
5998
|
}
|
|
5807
5999
|
return { path: read2.path, dir: read2.dir };
|
|
5808
6000
|
}
|
|
5809
6001
|
getNewPath(file, sql) {
|
|
5810
6002
|
if (sql?.filename) {
|
|
5811
|
-
return this.getAbsPath(
|
|
6003
|
+
return this.getAbsPath(path8.join(file, sql.filename), true);
|
|
5812
6004
|
}
|
|
5813
6005
|
return this.getAbsPath(file, true);
|
|
5814
6006
|
}
|
|
@@ -5816,7 +6008,7 @@ function dbDriver(opt = {}) {
|
|
|
5816
6008
|
try {
|
|
5817
6009
|
const filePath = sql?.type === "insert" ? this.getNewPath(file, sql) : this.getReadPath(file, sql).path || this.getNewPath(file, sql);
|
|
5818
6010
|
this.dbLog("write", "[WRITE]", filePath);
|
|
5819
|
-
|
|
6011
|
+
fs11.writeFileSync(filePath, data, "utf8");
|
|
5820
6012
|
return "ok";
|
|
5821
6013
|
} catch (e) {
|
|
5822
6014
|
this.dbLog("write failed", "[WRITE ERROR]", e);
|
|
@@ -5830,7 +6022,7 @@ function dbDriver(opt = {}) {
|
|
|
5830
6022
|
return { error: "empty" };
|
|
5831
6023
|
}
|
|
5832
6024
|
this.dbLog("read", "[READ]", read2.path);
|
|
5833
|
-
const data =
|
|
6025
|
+
const data = fs11.readFileSync(read2.path, { encoding }) || "";
|
|
5834
6026
|
const fileName = this.fileExt && read2.dir.endsWith(this.fileExt) ? read2.dir : read2.dir + this.fileExt;
|
|
5835
6027
|
return [{ data, file: fileName }];
|
|
5836
6028
|
} catch (e) {
|
|
@@ -5847,12 +6039,12 @@ function dbDriver(opt = {}) {
|
|
|
5847
6039
|
if (this.fileDel && sql?.deltrue) {
|
|
5848
6040
|
const target = del.path + ".delete" + this.fileExt;
|
|
5849
6041
|
this.dbLog("soft delete", "[SOFT DELETE]", `${del.path} -> ${target}`);
|
|
5850
|
-
|
|
6042
|
+
fs11.renameSync(del.path, target);
|
|
5851
6043
|
} else if (sql?.filename) {
|
|
5852
6044
|
this.deldir(del.dir);
|
|
5853
6045
|
} else {
|
|
5854
6046
|
this.dbLog("delete", "[DELETE]", del.path);
|
|
5855
|
-
|
|
6047
|
+
fs11.unlinkSync(del.path);
|
|
5856
6048
|
}
|
|
5857
6049
|
return "ok";
|
|
5858
6050
|
} catch (e) {
|
|
@@ -5871,11 +6063,11 @@ function dbDriver(opt = {}) {
|
|
|
5871
6063
|
const original = del.path.replace(new RegExp(`.delete${extPattern}$`), "");
|
|
5872
6064
|
if (original !== del.path) {
|
|
5873
6065
|
this.dbLog("restore", "[RESTORE]", `${del.path} -> ${original}`);
|
|
5874
|
-
|
|
6066
|
+
fs11.renameSync(del.path, original);
|
|
5875
6067
|
}
|
|
5876
6068
|
} else {
|
|
5877
6069
|
this.dbLog("force delete", "[FORCE DELETE]", del.path);
|
|
5878
|
-
|
|
6070
|
+
fs11.unlinkSync(del.path);
|
|
5879
6071
|
}
|
|
5880
6072
|
return "ok";
|
|
5881
6073
|
} catch (e) {
|
|
@@ -5889,7 +6081,7 @@ function dbDriver(opt = {}) {
|
|
|
5889
6081
|
this.dbLog("list", "[LIST]", absDir);
|
|
5890
6082
|
let entries;
|
|
5891
6083
|
try {
|
|
5892
|
-
entries =
|
|
6084
|
+
entries = fs11.readdirSync(absDir, { withFileTypes: true });
|
|
5893
6085
|
} catch {
|
|
5894
6086
|
return sql?.list ? { open: [], delete: [] } : [];
|
|
5895
6087
|
}
|
|
@@ -5901,9 +6093,9 @@ function dbDriver(opt = {}) {
|
|
|
5901
6093
|
const isDelete = fileName.endsWith(deleteSuffix);
|
|
5902
6094
|
const baseName = isDelete ? fileName.slice(0, -deleteSuffix.length) : fileName;
|
|
5903
6095
|
if (this.fileExt && !baseName.endsWith(this.fileExt)) continue;
|
|
5904
|
-
const fullPath =
|
|
6096
|
+
const fullPath = path8.join(absDir, fileName);
|
|
5905
6097
|
try {
|
|
5906
|
-
const data =
|
|
6098
|
+
const data = fs11.readFileSync(fullPath, "utf8");
|
|
5907
6099
|
const entryData = { data, file: baseName };
|
|
5908
6100
|
if (isDelete) {
|
|
5909
6101
|
if (sql?.list) result.delete.push(entryData);
|
|
@@ -6669,7 +6861,7 @@ var initAsaiHostNodejs2 = {
|
|
|
6669
6861
|
createTransportDataHandler,
|
|
6670
6862
|
wireTransportConnectionLogs
|
|
6671
6863
|
};
|
|
6672
|
-
var PLUGIN_VERSION = true ? "0.0.
|
|
6864
|
+
var PLUGIN_VERSION = true ? "0.0.10" : "0.0.1";
|
|
6673
6865
|
var index_default = initAsaiHostNodejs2;
|
|
6674
6866
|
export {
|
|
6675
6867
|
Index_default as AsaiCommon,
|