@@ -554,58 +554,111 @@ export default {
554554 }
555555
556556 if (request.method === 'GET') {
557- if (url.pathname === '/region') {
557+ // 处理 /{UUID}/region 或 /{自定义路径}/region
558+ if (url.pathname.endsWith('/region')) {
559+ const pathParts = url.pathname.split('/').filter(p => p);
558560
559- const ci = getConfigValue('p', env.p || env.P);
560- const manualRegion = getConfigValue('wk', env.wk || env.WK);
561-
562- if (manualRegion && manualRegion.trim()) {
563- return new Response(JSON.stringify({
564- region: manualRegion.trim().toUpperCase(),
565- detectionMethod: '手动指定地区',
566- manualRegion: manualRegion.trim().toUpperCase(),
567- timestamp: new Date().toISOString()
568- }), {
569- headers: { 'Content-Type': 'application/json' }
570- });
571- } else if (ci && ci.trim()) {
572- return new Response(JSON.stringify({
573- region: 'CUSTOM',
574- detectionMethod: '自定义ProxyIP模式', ci: ci,
575- timestamp: new Date().toISOString()
576- }), {
577- headers: { 'Content-Type': 'application/json' }
578- });
579- } else {
580- const detectedRegion = await detectWorkerRegion(request);
581- return new Response(JSON.stringify({
582- region: detectedRegion,
583- detectionMethod: 'API检测',
584- timestamp: new Date().toISOString()
585- }), {
586- headers: { 'Content-Type': 'application/json' }
587- });
561+ if (pathParts.length === 2 && pathParts[1] === 'region') {
562+ const pathIdentifier = pathParts[0];
563+ let isValid = false;
564+
565+ if (cp && cp.trim()) {
566+ // 使用自定义路径
567+ const cleanCustomPath = cp.trim().startsWith('/') ? cp.trim().substring(1) : cp.trim();
568+ isValid = (pathIdentifier === cleanCustomPath);
569+ } else {
570+ // 使用UUID路径
571+ isValid = (isValidFormat(pathIdentifier) && pathIdentifier === at);
572+ }
573+
574+ if (isValid) {
575+ const ci = getConfigValue('p', env.p || env.P);
576+ const manualRegion = getConfigValue('wk', env.wk || env.WK);
577+
578+ if (manualRegion && manualRegion.trim()) {
579+ return new Response(JSON.stringify({
580+ region: manualRegion.trim().toUpperCase(),
581+ detectionMethod: '手动指定地区',
582+ manualRegion: manualRegion.trim().toUpperCase(),
583+ timestamp: new Date().toISOString()
584+ }), {
585+ headers: { 'Content-Type': 'application/json' }
586+ });
587+ } else if (ci && ci.trim()) {
588+ return new Response(JSON.stringify({
589+ region: 'CUSTOM',
590+ detectionMethod: '自定义ProxyIP模式', ci: ci,
591+ timestamp: new Date().toISOString()
592+ }), {
593+ headers: { 'Content-Type': 'application/json' }
594+ });
595+ } else {
596+ const detectedRegion = await detectWorkerRegion(request);
597+ return new Response(JSON.stringify({
598+ region: detectedRegion,
599+ detectionMethod: 'API检测',
600+ timestamp: new Date().toISOString()
601+ }), {
602+ headers: { 'Content-Type': 'application/json' }
603+ });
604+ }
605+ } else {
606+ return new Response(JSON.stringify({
607+ error: '访问被拒绝',
608+ message: '路径验证失败'
609+ }), {
610+ status: 403,
611+ headers: { 'Content-Type': 'application/json' }
612+ });
613+ }
588614 }
589615 }
590616
591- if (url.pathname === '/test-api') {
592- try {
593- const testRegion = await detectWorkerRegion(request);
594- return new Response(JSON.stringify({
595- detectedRegion: testRegion,
596- message: 'API测试完成',
597- timestamp: new Date().toISOString()
598- }), {
599- headers: { 'Content-Type': 'application/json' }
600- });
601- } catch (error) {
602- return new Response(JSON.stringify({
603- error: error.message,
604- message: 'API测试失败'
605- }), {
606- status: 500,
607- headers: { 'Content-Type': 'application/json' }
608- });
617+ // 处理 /{UUID}/test-api 或 /{自定义路径}/test-api
618+ if (url.pathname.endsWith('/test-api')) {
619+ const pathParts = url.pathname.split('/').filter(p => p);
620+
621+ if (pathParts.length === 2 && pathParts[1] === 'test-api') {
622+ const pathIdentifier = pathParts[0];
623+ let isValid = false;
624+
625+ if (cp && cp.trim()) {
626+ // 使用自定义路径
627+ const cleanCustomPath = cp.trim().startsWith('/') ? cp.trim().substring(1) : cp.trim();
628+ isValid = (pathIdentifier === cleanCustomPath);
629+ } else {
630+ // 使用UUID路径
631+ isValid = (isValidFormat(pathIdentifier) && pathIdentifier === at);
632+ }
633+
634+ if (isValid) {
635+ try {
636+ const testRegion = await detectWorkerRegion(request);
637+ return new Response(JSON.stringify({
638+ detectedRegion: testRegion,
639+ message: 'API测试完成',
640+ timestamp: new Date().toISOString()
641+ }), {
642+ headers: { 'Content-Type': 'application/json' }
643+ });
644+ } catch (error) {
645+ return new Response(JSON.stringify({
646+ error: error.message,
647+ message: 'API测试失败'
648+ }), {
649+ status: 500,
650+ headers: { 'Content-Type': 'application/json' }
651+ });
652+ }
653+ } else {
654+ return new Response(JSON.stringify({
655+ error: '访问被拒绝',
656+ message: '路径验证失败'
657+ }), {
658+ status: 403,
659+ headers: { 'Content-Type': 'application/json' }
660+ });
661+ }
609662 }
610663 }
611664
@@ -2798,7 +2851,7 @@ async function handleSubscriptionPage(request, user = null) {
27982851 let isCustomIPMode = false;
27992852 let isManualRegionMode = false;
28002853 try {
2801- const response = await fetch('/region');
2854+ const response = await fetch(window.location.pathname + '/region');
28022855 const data = await response.json();
28032856
28042857 if (data.region === 'CUSTOM') {
@@ -2940,7 +2993,7 @@ async function handleSubscriptionPage(request, user = null) {
29402993
29412994 const t = translations[isFarsi ? 'fa' : 'zh'];
29422995
2943- const response = await fetch('/test-api');
2996+ const response = await fetch(window.location.pathname + '/test-api');
29442997 const data = await response.json();
29452998
29462999 if (data.detectedRegion) {
0 commit comments