Compare commits

...

6 Commits

Author SHA1 Message Date
xream
cc58a5541e feat: 订阅刷新按钮逻辑调整为无缓存刷新订阅和流量 2024-11-10 01:22:48 +08:00
xream
772f431887 feat: 模块版文件中增加 token 路由 2024-11-08 18:10:39 +08:00
xream
2b60c515cd feat: 支持管理 token 2024-11-04 13:59:57 +08:00
xream
c8c22c3901 fix: 修复 VMess URI SNI 2024-11-01 20:27:23 +08:00
xream
d8f9466b84 feat(wip): 支持自定义 share token 2024-10-31 23:33:34 +08:00
xream
d12ccad382 feat: MMDB 加入 $utils.ipasn 2024-10-31 01:39:13 +08:00
16 changed files with 280 additions and 220 deletions

View File

@@ -1,6 +1,6 @@
{
"name": "sub-store",
"version": "2.14.409",
"version": "2.14.415",
"description": "Advanced Subscription Manager for QX, Loon, Surge, Stash and ShadowRocket.",
"main": "src/main.js",
"scripts": {
@@ -28,13 +28,12 @@
"http-proxy-middleware": "^2.0.6",
"ip-address": "^9.0.5",
"js-base64": "^3.7.2",
"jsonwebtoken": "^9.0.2",
"jsrsasign": "^11.1.0",
"lodash": "^4.17.21",
"ms": "^2.1.3",
"nanoid": "^3.3.3",
"request": "^2.88.2",
"semver": "^7.3.7",
"static-js-yaml": "^1.0.0",
"uuid": "^8.3.2"
"static-js-yaml": "^1.0.0"
},
"devDependencies": {
"@babel/core": "^7.18.0",

171
backend/pnpm-lock.yaml generated
View File

@@ -41,27 +41,24 @@ importers:
js-base64:
specifier: ^3.7.2
version: https://registry.npmmirror.com/js-base64/-/js-base64-3.7.2.tgz
jsonwebtoken:
specifier: ^9.0.2
version: 9.0.2
jsrsasign:
specifier: ^11.1.0
version: https://registry.npmmirror.com/jsrsasign/-/jsrsasign-11.1.0.tgz
lodash:
specifier: ^4.17.21
version: https://registry.npmmirror.com/lodash/-/lodash-4.17.21.tgz
ms:
specifier: ^2.1.3
version: 2.1.3
nanoid:
specifier: ^3.3.3
version: 3.3.3
request:
specifier: ^2.88.2
version: https://registry.npmmirror.com/request/-/request-2.88.2.tgz
semver:
specifier: ^7.3.7
version: https://registry.npmmirror.com/semver/-/semver-7.3.7.tgz
static-js-yaml:
specifier: ^1.0.0
version: https://registry.npmmirror.com/static-js-yaml/-/static-js-yaml-1.0.0.tgz
uuid:
specifier: ^8.3.2
version: https://registry.npmmirror.com/uuid/-/uuid-8.3.2.tgz
devDependencies:
'@babel/core':
specifier: ^7.18.0
@@ -1509,9 +1506,6 @@ packages:
engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7}
hasBin: true
buffer-equal-constant-time@1.0.1:
resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==, tarball: https://registry.npmmirror.com/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz}
buffer-equal@https://registry.npmmirror.com/buffer-equal/-/buffer-equal-1.0.0.tgz:
resolution: {integrity: sha512-tcBWO2Dl4e7Asr9hTGcpVrCe+F7DubpmqWCTbj4FHLmjqO2hIaC383acQubWtRJhdceqs5uBHs6Es+Sk//RKiQ==, tarball: https://registry.npmmirror.com/buffer-equal/-/buffer-equal-1.0.0.tgz}
version: 1.0.0
@@ -2091,9 +2085,6 @@ packages:
resolution: {integrity: sha512-eh9O+hwRHNbG4BLTjEl3nw044CkGm5X6LoaCf7LPp7UU8Qrt47JYNi6nPX8xjW97TKGKm1ouctg0QSpZe9qrnw==, tarball: https://registry.npmmirror.com/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz}
version: 0.1.2
ecdsa-sig-formatter@1.0.11:
resolution: {integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==, tarball: https://registry.npmmirror.com/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz}
ee-first@https://registry.npmmirror.com/ee-first/-/ee-first-1.1.1.tgz:
resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==, tarball: https://registry.npmmirror.com/ee-first/-/ee-first-1.1.1.tgz}
version: 1.1.1
@@ -3391,10 +3382,6 @@ packages:
version: 1.3.1
engines: {'0': node >= 0.2.0}
jsonwebtoken@9.0.2:
resolution: {integrity: sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==, tarball: https://registry.npmmirror.com/jsonwebtoken/-/jsonwebtoken-9.0.2.tgz}
engines: {node: '>=12', npm: '>=6'}
jsprim@https://registry.npmmirror.com/jsprim/-/jsprim-1.4.1.tgz:
resolution: {integrity: sha512-4Dj8Rf+fQ+/Pn7C5qeEX02op1WfOss3PKTE9Nsop3Dx+6UPxlm1dr/og7o2cRa5hNN07CACr4NFzRLtj/rjWog==, tarball: https://registry.npmmirror.com/jsprim/-/jsprim-1.4.1.tgz}
version: 1.4.1
@@ -3413,12 +3400,6 @@ packages:
resolution: {integrity: sha512-qpcRocdkUmf+UTNBYx5w6dexX5J31AKK1OmPwH630a83DdVVUIngk55RSAiIGpQyoH0dlr872VHfPjnQnK1qDQ==, tarball: https://registry.npmmirror.com/just-debounce/-/just-debounce-1.1.0.tgz}
version: 1.1.0
jwa@1.4.1:
resolution: {integrity: sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==, tarball: https://registry.npmmirror.com/jwa/-/jwa-1.4.1.tgz}
jws@3.2.2:
resolution: {integrity: sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==, tarball: https://registry.npmmirror.com/jws/-/jws-3.2.2.tgz}
keyv@https://registry.npmmirror.com/keyv/-/keyv-3.1.0.tgz:
resolution: {integrity: sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==, tarball: https://registry.npmmirror.com/keyv/-/keyv-3.1.0.tgz}
version: 3.1.0
@@ -3510,24 +3491,6 @@ packages:
resolution: {integrity: sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==, tarball: https://registry.npmmirror.com/lodash.debounce/-/lodash.debounce-4.0.8.tgz}
version: 4.0.8
lodash.includes@4.3.0:
resolution: {integrity: sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==, tarball: https://registry.npmmirror.com/lodash.includes/-/lodash.includes-4.3.0.tgz}
lodash.isboolean@3.0.3:
resolution: {integrity: sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==, tarball: https://registry.npmmirror.com/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz}
lodash.isinteger@4.0.4:
resolution: {integrity: sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==, tarball: https://registry.npmmirror.com/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz}
lodash.isnumber@3.0.3:
resolution: {integrity: sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==, tarball: https://registry.npmmirror.com/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz}
lodash.isplainobject@4.0.6:
resolution: {integrity: sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==, tarball: https://registry.npmmirror.com/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz}
lodash.isstring@4.0.1:
resolution: {integrity: sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==, tarball: https://registry.npmmirror.com/lodash.isstring/-/lodash.isstring-4.0.1.tgz}
lodash.memoize@https://registry.npmmirror.com/lodash.memoize/-/lodash.memoize-3.0.4.tgz:
resolution: {integrity: sha512-eDn9kqrAmVUC1wmZvlQ6Uhde44n+tXpqPrN8olQJbttgh0oKclk+SF54P47VEGE9CEiMeRwAP8BaM7UHvBkz2A==, tarball: https://registry.npmmirror.com/lodash.memoize/-/lodash.memoize-3.0.4.tgz}
version: 3.0.4
@@ -3536,9 +3499,6 @@ packages:
resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==, tarball: https://registry.npmmirror.com/lodash.merge/-/lodash.merge-4.6.2.tgz}
version: 4.6.2
lodash.once@4.1.1:
resolution: {integrity: sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==, tarball: https://registry.npmmirror.com/lodash.once/-/lodash.once-4.1.1.tgz}
lodash.template@https://registry.npmmirror.com/lodash.template/-/lodash.template-4.5.0.tgz:
resolution: {integrity: sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A==, tarball: https://registry.npmmirror.com/lodash.template/-/lodash.template-4.5.0.tgz}
version: 4.5.0
@@ -3741,25 +3701,18 @@ packages:
engines: {node: '>= 0.8.0'}
hasBin: true
ms@2.0.0:
resolution: {integrity: sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==, tarball: https://registry.npmmirror.com/ms/-/ms-2.0.0.tgz}
ms@2.1.1:
resolution: {integrity: sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.1.tgz}
ms@2.1.2:
resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.2.tgz}
ms@2.1.3:
resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz}
ms@https://registry.npmmirror.com/ms/-/ms-2.0.0.tgz:
resolution: {integrity: sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==, tarball: https://registry.npmmirror.com/ms/-/ms-2.0.0.tgz}
version: 2.0.0
ms@https://registry.npmmirror.com/ms/-/ms-2.1.1.tgz:
resolution: {integrity: sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.1.tgz}
version: 2.1.1
ms@https://registry.npmmirror.com/ms/-/ms-2.1.2.tgz:
resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.2.tgz}
version: 2.1.2
ms@https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz:
resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==, tarball: https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz}
version: 2.1.3
multi-stage-sourcemap@https://registry.npmmirror.com/multi-stage-sourcemap/-/multi-stage-sourcemap-0.2.1.tgz:
resolution: {integrity: sha512-umaOM+8BZByZIB/ciD3dQLzTv50rEkkGJV78ta/tIVc/J/rfGZY5y1R+fBD3oTaolx41mK8rRcyGtYbDXlzx8Q==, tarball: https://registry.npmmirror.com/multi-stage-sourcemap/-/multi-stage-sourcemap-0.2.1.tgz}
version: 0.2.1
@@ -3785,9 +3738,8 @@ packages:
version: 2.1.1
hasBin: true
nanoid@https://registry.npmmirror.com/nanoid/-/nanoid-3.3.3.tgz:
nanoid@3.3.3:
resolution: {integrity: sha512-p1sjXuopFs0xg+fPASzQ28agW1oHD7xDsd9Xkf3T15H3c/cifrFHVwrh74PdoklAPi+i7MdRsE47vm2r6JoB+w==, tarball: https://registry.npmmirror.com/nanoid/-/nanoid-3.3.3.tgz}
version: 3.3.3
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
hasBin: true
@@ -4511,9 +4463,6 @@ packages:
resolution: {integrity: sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==, tarball: https://registry.npmmirror.com/ripemd160/-/ripemd160-2.0.2.tgz}
version: 2.0.2
safe-buffer@5.2.1:
resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==, tarball: https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.2.1.tgz}
safe-buffer@https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.1.2.tgz:
resolution: {integrity: sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==, tarball: https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.1.2.tgz}
version: 5.1.2
@@ -4552,11 +4501,6 @@ packages:
resolution: {integrity: sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==, tarball: https://registry.npmmirror.com/semver/-/semver-6.3.0.tgz}
hasBin: true
semver@7.6.3:
resolution: {integrity: sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==, tarball: https://registry.npmmirror.com/semver/-/semver-7.6.3.tgz}
engines: {node: '>=10'}
hasBin: true
semver@https://registry.npmmirror.com/semver/-/semver-5.7.1.tgz:
resolution: {integrity: sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==, tarball: https://registry.npmmirror.com/semver/-/semver-5.7.1.tgz}
version: 5.7.1
@@ -5235,11 +5179,6 @@ packages:
deprecated: Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.
hasBin: true
uuid@https://registry.npmmirror.com/uuid/-/uuid-8.3.2.tgz:
resolution: {integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==, tarball: https://registry.npmmirror.com/uuid/-/uuid-8.3.2.tgz}
version: 8.3.2
hasBin: true
v8-compile-cache@https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz:
resolution: {integrity: sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==, tarball: https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz}
version: 2.3.0
@@ -6824,8 +6763,6 @@ snapshots:
node-releases: https://registry.npmmirror.com/node-releases/-/node-releases-2.0.4.tgz
picocolors: https://registry.npmmirror.com/picocolors/-/picocolors-1.0.0.tgz
buffer-equal-constant-time@1.0.1: {}
buffer-equal@https://registry.npmmirror.com/buffer-equal/-/buffer-equal-1.0.0.tgz: {}
buffer-from@https://registry.npmmirror.com/buffer-from/-/buffer-from-1.1.2.tgz: {}
@@ -7202,17 +7139,17 @@ snapshots:
debug@https://registry.npmmirror.com/debug/-/debug-2.6.9.tgz:
dependencies:
ms: https://registry.npmmirror.com/ms/-/ms-2.0.0.tgz
ms: 2.0.0
debug@https://registry.npmmirror.com/debug/-/debug-3.2.7.tgz(supports-color@https://registry.npmmirror.com/supports-color/-/supports-color-5.5.0.tgz):
dependencies:
ms: https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz
ms: 2.1.3
optionalDependencies:
supports-color: https://registry.npmmirror.com/supports-color/-/supports-color-5.5.0.tgz
debug@https://registry.npmmirror.com/debug/-/debug-4.3.4.tgz(supports-color@https://registry.npmmirror.com/supports-color/-/supports-color-8.1.1.tgz):
dependencies:
ms: https://registry.npmmirror.com/ms/-/ms-2.1.2.tgz
ms: 2.1.2
optionalDependencies:
supports-color: https://registry.npmmirror.com/supports-color/-/supports-color-8.1.1.tgz
@@ -7357,10 +7294,6 @@ snapshots:
jsbn: https://registry.npmmirror.com/jsbn/-/jsbn-0.1.1.tgz
safer-buffer: https://registry.npmmirror.com/safer-buffer/-/safer-buffer-2.1.2.tgz
ecdsa-sig-formatter@1.0.11:
dependencies:
safe-buffer: 5.2.1
ee-first@https://registry.npmmirror.com/ee-first/-/ee-first-1.1.1.tgz: {}
electron-to-chromium@https://registry.npmmirror.com/electron-to-chromium/-/electron-to-chromium-1.4.137.tgz: {}
@@ -8561,19 +8494,6 @@ snapshots:
jsonparse@https://registry.npmmirror.com/jsonparse/-/jsonparse-1.3.1.tgz: {}
jsonwebtoken@9.0.2:
dependencies:
jws: 3.2.2
lodash.includes: 4.3.0
lodash.isboolean: 3.0.3
lodash.isinteger: 4.0.4
lodash.isnumber: 3.0.3
lodash.isplainobject: 4.0.6
lodash.isstring: 4.0.1
lodash.once: 4.1.1
ms: 2.1.3
semver: 7.6.3
jsprim@https://registry.npmmirror.com/jsprim/-/jsprim-1.4.1.tgz:
dependencies:
assert-plus: https://registry.npmmirror.com/assert-plus/-/assert-plus-1.0.0.tgz
@@ -8592,17 +8512,6 @@ snapshots:
just-debounce@https://registry.npmmirror.com/just-debounce/-/just-debounce-1.1.0.tgz: {}
jwa@1.4.1:
dependencies:
buffer-equal-constant-time: 1.0.1
ecdsa-sig-formatter: 1.0.11
safe-buffer: 5.2.1
jws@3.2.2:
dependencies:
jwa: 1.4.1
safe-buffer: 5.2.1
keyv@https://registry.npmmirror.com/keyv/-/keyv-3.1.0.tgz:
dependencies:
json-buffer: https://registry.npmmirror.com/json-buffer/-/json-buffer-3.0.0.tgz
@@ -8689,24 +8598,10 @@ snapshots:
lodash.debounce@https://registry.npmmirror.com/lodash.debounce/-/lodash.debounce-4.0.8.tgz: {}
lodash.includes@4.3.0: {}
lodash.isboolean@3.0.3: {}
lodash.isinteger@4.0.4: {}
lodash.isnumber@3.0.3: {}
lodash.isplainobject@4.0.6: {}
lodash.isstring@4.0.1: {}
lodash.memoize@https://registry.npmmirror.com/lodash.memoize/-/lodash.memoize-3.0.4.tgz: {}
lodash.merge@https://registry.npmmirror.com/lodash.merge/-/lodash.merge-4.6.2.tgz: {}
lodash.once@4.1.1: {}
lodash.template@https://registry.npmmirror.com/lodash.template/-/lodash.template-4.5.0.tgz:
dependencies:
lodash._reinterpolate: https://registry.npmmirror.com/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz
@@ -8881,8 +8776,8 @@ snapshots:
js-yaml: https://registry.npmmirror.com/js-yaml/-/js-yaml-4.1.0.tgz
log-symbols: https://registry.npmmirror.com/log-symbols/-/log-symbols-4.1.0.tgz
minimatch: https://registry.npmmirror.com/minimatch/-/minimatch-5.0.1.tgz
ms: https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz
nanoid: https://registry.npmmirror.com/nanoid/-/nanoid-3.3.3.tgz
ms: 2.1.3
nanoid: 3.3.3
serialize-javascript: https://registry.npmmirror.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz
strip-json-comments: https://registry.npmmirror.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz
supports-color: https://registry.npmmirror.com/supports-color/-/supports-color-8.1.1.tgz
@@ -8909,16 +8804,14 @@ snapshots:
through2: https://registry.npmmirror.com/through2/-/through2-2.0.5.tgz
xtend: https://registry.npmmirror.com/xtend/-/xtend-4.0.2.tgz
ms@2.0.0: {}
ms@2.1.1: {}
ms@2.1.2: {}
ms@2.1.3: {}
ms@https://registry.npmmirror.com/ms/-/ms-2.0.0.tgz: {}
ms@https://registry.npmmirror.com/ms/-/ms-2.1.1.tgz: {}
ms@https://registry.npmmirror.com/ms/-/ms-2.1.2.tgz: {}
ms@https://registry.npmmirror.com/ms/-/ms-2.1.3.tgz: {}
multi-stage-sourcemap@https://registry.npmmirror.com/multi-stage-sourcemap/-/multi-stage-sourcemap-0.2.1.tgz:
dependencies:
source-map: https://registry.npmmirror.com/source-map/-/source-map-0.1.43.tgz
@@ -8941,7 +8834,7 @@ snapshots:
mutexify: https://registry.npmmirror.com/mutexify/-/mutexify-1.4.0.tgz
pretty-hrtime: https://registry.npmmirror.com/pretty-hrtime/-/pretty-hrtime-1.0.3.tgz
nanoid@https://registry.npmmirror.com/nanoid/-/nanoid-3.3.3.tgz: {}
nanoid@3.3.3: {}
nanomatch@https://registry.npmmirror.com/nanomatch/-/nanomatch-1.2.13.tgz:
dependencies:
@@ -9553,8 +9446,6 @@ snapshots:
hash-base: https://registry.npmmirror.com/hash-base/-/hash-base-3.1.0.tgz
inherits: https://registry.npmmirror.com/inherits/-/inherits-2.0.4.tgz
safe-buffer@5.2.1: {}
safe-buffer@https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.1.2.tgz: {}
safe-buffer@https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.2.1.tgz: {}
@@ -9587,8 +9478,6 @@ snapshots:
semver@6.3.0: {}
semver@7.6.3: {}
semver@https://registry.npmmirror.com/semver/-/semver-5.7.1.tgz: {}
semver@https://registry.npmmirror.com/semver/-/semver-6.3.0.tgz: {}
@@ -9610,7 +9499,7 @@ snapshots:
fresh: https://registry.npmmirror.com/fresh/-/fresh-0.5.2.tgz
http-errors: https://registry.npmmirror.com/http-errors/-/http-errors-1.7.2.tgz
mime: https://registry.npmmirror.com/mime/-/mime-1.6.0.tgz
ms: https://registry.npmmirror.com/ms/-/ms-2.1.1.tgz
ms: 2.1.1
on-finished: https://registry.npmmirror.com/on-finished/-/on-finished-2.3.0.tgz
range-parser: https://registry.npmmirror.com/range-parser/-/range-parser-1.2.1.tgz
statuses: https://registry.npmmirror.com/statuses/-/statuses-1.5.0.tgz
@@ -10236,8 +10125,6 @@ snapshots:
uuid@https://registry.npmmirror.com/uuid/-/uuid-3.4.0.tgz: {}
uuid@https://registry.npmmirror.com/uuid/-/uuid-8.3.2.tgz: {}
v8-compile-cache@https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz: {}
v8flags@https://registry.npmmirror.com/v8flags/-/v8flags-3.2.0.tgz:

View File

@@ -6,6 +6,7 @@ export const FILES_KEY = 'files';
export const MODULES_KEY = 'modules';
export const ARTIFACTS_KEY = 'artifacts';
export const RULES_KEY = 'rules';
export const TOKENS_KEY = 'tokens';
export const GIST_BACKUP_KEY = 'Auto Generated Sub-Store Backup';
export const GIST_BACKUP_FILE_NAME = 'Sub-Store';
export const ARTIFACT_REPOSITORY_KEY = 'Sub-Store Artifacts Repository';

View File

@@ -316,7 +316,7 @@ function URI_VMess() {
);
}
// https://github.com/2dust/v2rayN/wiki/%E5%88%86%E4%BA%AB%E9%93%BE%E6%8E%A5%E6%A0%BC%E5%BC%8F%E8%AF%B4%E6%98%8E(ver-2)
if (proxy.tls && proxy.sni) {
if (proxy.tls && params.sni && params.sni !== '') {
proxy.sni = params.sni;
}
let httpupgrade = false;

View File

@@ -21,6 +21,7 @@ import registerSettingRoutes from '@/restful/settings';
import registerMiscRoutes from '@/restful/miscs';
import registerSortRoutes from '@/restful/sort';
import registerFileRoutes from '@/restful/file';
import registerTokenRoutes from '@/restful/token';
import registerModuleRoutes from '@/restful/module';
migrate();
@@ -32,6 +33,7 @@ function serve() {
// register routes
registerCollectionRoutes($app);
registerSubscriptionRoutes($app);
registerTokenRoutes($app);
registerFileRoutes($app);
registerModuleRoutes($app);
registerArtifactRoutes($app);

View File

@@ -13,6 +13,9 @@ import { getISO } from '@/utils/geo';
import env from '@/utils/env';
export default function register($app) {
$app.get('/share/col/:name', downloadCollection);
$app.get('/share/sub/:name', downloadSubscription);
$app.get('/download/collection/:name', downloadCollection);
$app.get('/download/:name', downloadSubscription);
$app.get(
@@ -72,6 +75,7 @@ async function downloadSubscription(req, res) {
includeUnsupportedProxy,
resultFormat,
proxy,
noCache,
} = req.query;
let $options = {};
if (req.query.$options) {
@@ -128,6 +132,10 @@ async function downloadSubscription(req, res) {
$.info(`手动指定了 target 为 SurgeMac, 将使用 Mihomo External`);
}
if (noCache) {
$.info(`指定不使用缓存: ${noCache}`);
}
const allSubs = $.read(SUBS_KEY);
const sub = findByName(allSubs, name);
if (sub) {
@@ -148,6 +156,7 @@ async function downloadSubscription(req, res) {
},
$options,
proxy,
noCache,
});
if (
@@ -280,6 +289,7 @@ async function downloadCollection(req, res) {
includeUnsupportedProxy,
resultFormat,
proxy,
noCache,
} = req.query;
let $options = {};
@@ -322,6 +332,9 @@ async function downloadCollection(req, res) {
if (useMihomoExternal) {
$.info(`手动指定了 target 为 SurgeMac, 将使用 Mihomo External`);
}
if (noCache) {
$.info(`指定不使用缓存: ${noCache}`);
}
if (collection) {
try {
@@ -337,6 +350,7 @@ async function downloadCollection(req, res) {
},
$options,
proxy,
noCache,
});
// forward flow header from the first subscription in this collection

View File

@@ -13,6 +13,8 @@ import { produceArtifact } from '@/restful/sync';
export default function register($app) {
if (!$.read(FILES_KEY)) $.write([], FILES_KEY);
$app.get('/share/file/:name', getFile);
$app.route('/api/file/:name')
.get(getFile)
.patch(updateFile)

View File

@@ -4,11 +4,13 @@ import migrate from '@/utils/migration';
import download from '@/utils/download';
import { syncArtifacts } from '@/restful/sync';
import { gistBackupAction } from '@/restful/miscs';
import { TOKENS_KEY } from '@/constants';
import registerSubscriptionRoutes from './subscriptions';
import registerCollectionRoutes from './collections';
import registerArtifactRoutes from './artifacts';
import registerFileRoutes from './file';
import registerTokenRoutes from './token';
import registerModuleRoutes from './module';
import registerSyncRoutes from './sync';
import registerDownloadRoutes from './download';
@@ -36,6 +38,7 @@ export default function serve() {
registerSettingRoutes($app);
registerArtifactRoutes($app);
registerFileRoutes($app);
registerTokenRoutes($app);
registerModuleRoutes($app);
registerSyncRoutes($app);
registerNodeInfoRoutes($app);
@@ -176,8 +179,6 @@ export default function serve() {
fe_be_path === '/' ? '' : fe_be_path
}${be_download}`;
const jwt = eval(`require("jsonwebtoken")`);
app.use(
be_share_rewrite,
createProxyMiddleware({
@@ -186,31 +187,16 @@ export default function serve() {
pathRewrite: (path, req) => {
if (req.method.toLowerCase() !== 'get')
throw new Error('Method not allowed');
const payload = jwt.verify(
req.query.token,
fe_be_path,
const tokens = $.read(TOKENS_KEY) || [];
const token = tokens.find(
(t) =>
t.token === req.query.token &&
t.type === req.params.type &&
t.name === req.params.name &&
(t.exp == null || t.exp > Date.now()),
);
if (
payload.type !== req.params.type ||
payload.name !== req.params.name
)
throw new Error('Forbbiden');
if (payload.type === 'sub')
return path.replace(
'/share/sub/',
'/download/',
);
if (payload.type === 'col')
return path.replace(
'/share/col/',
'/download/collection/',
);
if (payload.type === 'file')
return path.replace(
'/share/file/',
'/api/file/',
);
throw new Error('Not Found');
if (!token) throw new Error('Forbbiden');
return path;
},
}),
);
@@ -218,11 +204,13 @@ export default function serve() {
be_api_rewrite,
createProxyMiddleware({
target: `http://127.0.0.1:${port}`,
changeOrigin: true,
pathRewrite: (path) => {
return path.startsWith(be_api_rewrite)
const newPath = path.startsWith(be_api_rewrite)
? path.replace(be_api_rewrite, be_api)
: path;
return newPath.includes('?')
? `${newPath}&share=true`
: `${newPath}?share=true`;
},
}),
);

View File

@@ -20,36 +20,6 @@ export default function register($app) {
$app.get('/api/utils/env', getEnv); // get runtime environment
$app.get('/api/utils/backup', gistBackup); // gist backup actions
$app.get('/api/utils/refresh', refresh);
$app.post('/api/jwt', (req, res) => {
if (!ENV().isNode) {
return failed(
res,
new RequestInvalidError(
'INVALID_ENV',
`This endpoint is only available in Node.js environment`,
),
);
}
try {
const { payload, options } = req.body;
const jwt = eval(`require("jsonwebtoken")`);
const secret = eval('process.env.SUB_STORE_FRONTEND_BACKEND_PATH');
const token = jwt.sign(payload, secret, options);
return success(res, {
token,
secret,
});
} catch (e) {
return failed(
res,
new InternalServerError(
'JWT_SIGN_FAILED',
`Failed to sign JWT token`,
`Reason: ${e.message ?? e}`,
),
);
}
});
// Storage management
$app.route('/api/storage')
@@ -95,6 +65,9 @@ export default function register($app) {
}
function getEnv(req, res) {
if (req.query.share) {
env.feature.share = true;
}
success(res, env);
}

View File

@@ -39,6 +39,7 @@ async function produceArtifact({
awaitCustomCache,
$options,
proxy,
noCache,
}) {
platform = platform || 'JSON';
@@ -72,6 +73,7 @@ async function produceArtifact({
proxy || sub.proxy,
undefined,
awaitCustomCache,
noCache,
);
} catch (err) {
errors[url] = err;
@@ -119,6 +121,7 @@ async function produceArtifact({
proxy || sub.proxy,
undefined,
awaitCustomCache,
noCache,
);
} catch (err) {
errors[url] = err;
@@ -237,6 +240,9 @@ async function produceArtifact({
proxy ||
sub.proxy ||
collection.proxy,
undefined,
undefined,
noCache,
);
} catch (err) {
errors[url] = err;
@@ -410,6 +416,9 @@ async function produceArtifact({
ua || file.ua,
undefined,
file.proxy || proxy,
undefined,
undefined,
noCache,
);
} catch (err) {
errors[url] = err;
@@ -458,6 +467,9 @@ async function produceArtifact({
ua || file.ua,
undefined,
file.proxy || proxy,
undefined,
undefined,
noCache,
);
} catch (err) {
errors[url] = err;

View File

@@ -0,0 +1,181 @@
import { deleteByName } from '@/utils/database';
import { ENV } from '@/vendor/open-api';
import { TOKENS_KEY, SUBS_KEY, FILES_KEY, COLLECTIONS_KEY } from '@/constants';
import { failed, success } from '@/restful/response';
import $ from '@/core/app';
import { RequestInvalidError, InternalServerError } from '@/restful/errors';
export default function register($app) {
if (!$.read(TOKENS_KEY)) $.write([], TOKENS_KEY);
$app.post('/api/token', signToken);
$app.route('/api/token/:token').delete(deleteToken);
$app.route('/api/tokens').get(getAllTokens);
}
function deleteToken(req, res) {
let { token } = req.params;
token = decodeURIComponent(token);
$.info(`正在删除:${token}`);
let allTokens = $.read(TOKENS_KEY);
deleteByName(allTokens, token, 'token');
$.write(allTokens, TOKENS_KEY);
success(res);
}
function getAllTokens(req, res) {
const { type, name } = req.query;
const allTokens = $.read(TOKENS_KEY) || [];
success(
res,
type || name
? allTokens.filter(
(item) =>
(type ? item.type === type : true) &&
(name ? item.name === name : true),
)
: allTokens,
);
}
async function signToken(req, res) {
if (!ENV().isNode) {
return failed(
res,
new RequestInvalidError(
'INVALID_ENV',
`This endpoint is only available in Node.js environment`,
),
);
}
try {
const { payload, options } = req.body;
const ms = eval(`require("ms")`);
let token = payload?.token;
if (token != null) {
if (typeof token !== 'string' || token.length < 1) {
return failed(
res,
new RequestInvalidError(
'INVALID_CUSTOM_TOKEN',
`Invalid custom token: ${token}`,
),
);
}
const tokens = $.read(TOKENS_KEY) || [];
if (tokens.find((t) => t.token === token)) {
return failed(
res,
new RequestInvalidError(
'DUPLICATE_TOKEN',
`Token ${token} already exists`,
),
);
}
}
const type = payload?.type;
const name = payload?.name;
if (!type || !name)
return failed(
res,
new RequestInvalidError(
'INVALID_PAYLOAD',
`payload type and name are required`,
),
);
if (type === 'col') {
const collections = $.read(COLLECTIONS_KEY) || [];
const collection = collections.find((c) => c.name === name);
if (!collection)
return failed(
res,
new RequestInvalidError(
'INVALID_COLLECTION',
`collection ${name} not found`,
),
);
} else if (type === 'file') {
const files = $.read(FILES_KEY) || [];
const file = files.find((f) => f.name === name);
if (!file)
return failed(
res,
new RequestInvalidError(
'INVALID_FILE',
`file ${name} not found`,
),
);
} else if (type === 'sub') {
const subs = $.read(SUBS_KEY) || [];
const sub = subs.find((s) => s.name === name);
if (!sub)
return failed(
res,
new RequestInvalidError(
'INVALID_SUB',
`sub ${name} not found`,
),
);
} else {
return failed(
res,
new RequestInvalidError(
'INVALID_TYPE',
`type ${name} not supported`,
),
);
}
let expiresIn = options?.expiresIn;
if (options?.expiresIn != null) {
expiresIn = ms(options.expiresIn);
if (expiresIn == null || isNaN(expiresIn) || expiresIn <= 0) {
return failed(
res,
new RequestInvalidError(
'INVALID_EXPIRES_IN',
`Invalid expiresIn option: ${options.expiresIn}`,
),
);
}
}
// const secret = eval('process.env.SUB_STORE_FRONTEND_BACKEND_PATH');
const nanoid = eval(`require("nanoid")`);
const tokens = $.read(TOKENS_KEY) || [];
// const now = Date.now();
// for (const key in tokens) {
// const token = tokens[key];
// if (token.exp != null || token.exp < now) {
// delete tokens[key];
// }
// }
if (!token) {
do {
token = nanoid.customAlphabet(nanoid.urlAlphabet)();
} while (tokens.find((t) => t.token === token));
}
tokens.push({
...payload,
token,
createdAt: Date.now(),
expiresIn: expiresIn > 0 ? options?.expiresIn : undefined,
exp: expiresIn > 0 ? Date.now() + expiresIn : undefined,
});
$.write(tokens, TOKENS_KEY);
return success(res, {
token,
// secret,
});
} catch (e) {
return failed(
res,
new InternalServerError(
'TOKEN_SIGN_FAILED',
`Failed to sign token`,
`Reason: ${e.message ?? e}`,
),
);
}
}

View File

@@ -1,17 +1,17 @@
export function findByName(list, name) {
return list.find((item) => item.name === name);
export function findByName(list, name, field = 'name') {
return list.find((item) => item[field] === name);
}
export function findIndexByName(list, name) {
return list.findIndex((item) => item.name === name);
export function findIndexByName(list, name, field = 'name') {
return list.findIndex((item) => item[field] === name);
}
export function deleteByName(list, name) {
const idx = findIndexByName(list, name);
export function deleteByName(list, name, field = 'name') {
const idx = findIndexByName(list, name, field);
list.splice(idx, 1);
}
export function updateByName(list, name, newItem) {
const idx = findIndexByName(list, name);
export function updateByName(list, name, newItem, field = 'name') {
const idx = findIndexByName(list, name, field);
list[idx] = newItem;
}

View File

@@ -21,6 +21,7 @@ export default async function download(
customProxy,
skipCustomCache,
awaitCustomCache,
noCache,
) {
let $arguments = {};
let url = rawUrl.replace(/#noFlow$/, '');
@@ -65,7 +66,7 @@ export default async function download(
if (customCacheKey && !skipCustomCache) {
const customCached = $.read(customCacheKey);
const cached = resourceCache.get(id);
if (!$arguments?.noCache && cached) {
if (!noCache && !$arguments?.noCache && cached) {
$.info(
`乐观缓存: URL ${url}\n存在有效的常规缓存\n使用常规缓存以避免重复请求`,
);
@@ -149,7 +150,7 @@ export default async function download(
// try to find in app cache
const cached = resourceCache.get(id);
if (!$arguments?.noCache && cached) {
if (!noCache && !$arguments?.noCache && cached) {
$.info(`使用缓存: ${url}`);
result = cached;
if (customCacheKey) {

View File

@@ -44,10 +44,6 @@ try {
meta.plugin = $Plugin;
}
if (isNode) {
const secret = eval('process.env.SUB_STORE_FRONTEND_BACKEND_PATH');
if (secret && eval('process.env.SUB_STORE_FRONTEND_PATH')) {
feature.share = true;
}
meta.node = {
version: eval('process.version'),
argv: eval('process.argv'),

View File

@@ -474,4 +474,7 @@ export class MMDB {
ipaso(ip) {
return this.asnReader?.asn(ip)?.autonomousSystemOrganization;
}
ipasn(ip) {
return this.asnReader?.asn(ip)?.autonomousSystemNumber;
}
}

View File

@@ -67,6 +67,7 @@ function operator(proxies = [], targetPlatform, context) {
// getISO, // 获取 ISO 3166-1 alpha-2 代码
// Gist, // Gist 类
// download, // 内部的下载方法, 见 backend/src/utils/download.js
// MMDB, // Node.js 环境 可用于模拟 Surge/Loon 的 $utils.ipasn, $utils.ipaso, $utils.geoip. 具体见 https://t.me/zhetengsha/1269
// }
// 如果只是为了快速修改或者筛选 可以参考 脚本操作支持节点快捷脚本 https://t.me/zhetengsha/970 和 脚本筛选支持节点快捷脚本 https://t.me/zhetengsha/1009