后台打洞测试

This commit is contained in:
snltty
2024-09-16 15:07:51 +08:00
parent 0ae571052b
commit 83a2c0d564
33 changed files with 278 additions and 214 deletions

View File

@@ -7,7 +7,7 @@ sidebar_position: 6
## 1、不修改源码的Action方式
:::tip[说明]
服务端`server.json`中的,`Relay中继``SForward穿透``SignIn信标`,都可以设置`ActionUrl``ActionUrl`不为空时这些操作都会发送HTTP POST请求到`ActionUrl`并携带json参数可用于自定义验证。参数暂时不支持固定设置这需要你自己连接客户端管理接口设置参数。
服务端`action.json`中的,`RelayActionUrl中继``SForwardActionUrl穿透``SignInActionUrl信标`都可以设置支持HTTP POST的URL不为空时这些操作都会发送HTTP POST请求到`ActionUrl`并携带json参数可用于自定义验证。参数暂时不支持固定设置这需要你自己连接客户端管理接口设置参数。
以javascript 为例,设置参数方法:
```
@@ -29,7 +29,7 @@ ws.onopen = () => {
:::tip[说明]
你可以在任意对方编写这些代码,可以参考 `plugins->action`action方式实现了这些自定义认证
你可以在任意对方编写这些代码,可以参考 `plugins->action`action插件就是使用以下方式实现
#### 2.1、连接服务器验证
```

View File

@@ -0,0 +1,54 @@
using System;
using System.Threading.Tasks;
namespace linker.libs
{
public static class TimerHelper
{
public static void SetTimeout(Action action, int delayMs)
{
Task.Run(async () =>
{
await Task.Delay(delayMs);
action();
});
}
public static void SetInterval(Func<bool> action, int delayMs)
{
Task.Run(async () =>
{
while (true)
{
if (action() == false)
{
break;
}
await Task.Delay(delayMs).ConfigureAwait(false);
}
});
}
public static void SetInterval(Func<Task<bool>> action, int delayMs)
{
Task.Run(async () =>
{
while (true)
{
if (await action() == false)
{
break;
}
await Task.Delay(delayMs).ConfigureAwait(false);
}
});
}
public static void Async(Action action)
{
Task.Run(action);
}
public static void Async(Func<Task> action)
{
Task.Run(action);
}
}
}

View File

@@ -1 +1 @@
.dropdown[data-v-619f5cb0]{border:1px solid #ddd;padding:.4rem;font-size:1.3rem;border-radius:.4rem;position:relative}.dropdown .el-icon[data-v-619f5cb0]{vertical-align:middle}.dropdown .badge[data-v-619f5cb0]{position:absolute;right:-1rem;top:-50%;border-radius:10px;background-color:#f1ae05;color:#fff;padding:.2rem .6rem;font-size:1.2rem}a[data-v-56d38c60]{color:#666;text-decoration:underline}a.green[data-v-56d38c60]{color:green;font-weight:700}a.download[data-v-56d38c60]{margin-left:.6rem}a.download .el-icon[data-v-56d38c60]{vertical-align:middle;font-weight:700;margin-left:.3rem}a.download .el-icon.loading[data-v-56d38c60]{animation:loading-56d38c60 1s linear infinite}@keyframes loading-56d38c60{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}a[data-v-a998806a]{color:#666;text-decoration:underline}a.green[data-v-a998806a]{color:green;font-weight:700}img.system[data-v-a998806a]{height:1.6rem;vertical-align:middle;margin-right:.4rem}.ipaddress span[data-v-358fba0e]{vertical-align:middle}.el-input[data-v-358fba0e]{width:15rem;margin-right:.6rem}.el-col[data-v-5b9d3bc4]{text-align:left}.el-icon.loading[data-v-8a7ccef2],a.loading[data-v-8a7ccef2]{vertical-align:middle;font-weight:700;animation:loading-8a7ccef2 1s linear infinite}.el-switch.is-disabled[data-v-8a7ccef2]{opacity:1}.el-input[data-v-8a7ccef2]{width:8rem}.gateway[data-v-8a7ccef2]{background:linear-gradient(90deg,#c5b260,#858585,#c5b260,#858585);-webkit-background-clip:text;-webkit-text-fill-color:hsla(0,0%,100%,0)}.gateway.green[data-v-8a7ccef2]{background:linear-gradient(90deg,#e4bb10,green,#e4bb10,green);-webkit-background-clip:text;-webkit-text-fill-color:hsla(0,0%,100%,0)}.delay[data-v-8a7ccef2]{position:absolute;right:0;bottom:0;line-height:normal}.switch-btn[data-v-8a7ccef2]{font-size:1.5rem}@keyframes loading-8a7ccef2{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.el-switch.is-disabled[data-v-44067f74]{opacity:1}.upgrade-wrap[data-v-44067f74]{border:1px solid #ddd;margin-bottom:2rem;padding:0 0 1rem 0}.el-switch.is-disabled[data-v-56597dfc]{opacity:1}.green[data-v-56597dfc]{font-weight:700}.el-switch.is-disabled[data-v-1f7f67a4]{opacity:1}a[data-v-19db1f43]{text-decoration:underline;font-weight:700}.head[data-v-2c1a8404]{padding-bottom:1rem}.green[data-v-2c1a8404]{color:green;font-weight:700}.error[data-v-2c1a8404]{font-weight:700}.error .el-icon[data-v-2c1a8404]{vertical-align:text-bottom}.el-select[data-v-3a13c86f]{width:12rem}.head[data-v-3a13c86f]{padding-bottom:1rem}.foot[data-v-3a13c86f]{padding-top:1rem}.page-wrap[data-v-3a13c86f]{display:inline-block}.head[data-v-5e37381c]{padding-bottom:1rem}.error[data-v-5e37381c]{font-weight:700}.error .el-icon[data-v-5e37381c]{vertical-align:text-bottom}.el-select[data-v-5512121a]{width:12rem}.head[data-v-5512121a]{padding-bottom:1rem}.foot[data-v-5512121a]{padding-top:1rem}.page-wrap[data-v-5512121a]{display:inline-block}.head[data-v-36027c60]{padding-bottom:1rem}.table-sort.el-table th.el-table__cell.is-leaf{border-bottom:0}.table-sort.el-table .el-table__inner-wrapper:before{height:0}.table-sort th[data-v-32477317]{border-bottom:0}.home-list-wrap[data-v-32477317]{padding:1rem}.home-list-wrap .page[data-v-32477317]{padding-top:1rem}.home-list-wrap .page-wrap[data-v-32477317]{display:inline-block}
.dropdown[data-v-619f5cb0]{border:1px solid #ddd;padding:.4rem;font-size:1.3rem;border-radius:.4rem;position:relative}.dropdown .el-icon[data-v-619f5cb0]{vertical-align:middle}.dropdown .badge[data-v-619f5cb0]{position:absolute;right:-1rem;top:-50%;border-radius:10px;background-color:#f1ae05;color:#fff;padding:.2rem .6rem;font-size:1.2rem}a[data-v-56d38c60]{color:#666;text-decoration:underline}a.green[data-v-56d38c60]{color:green;font-weight:700}a.download[data-v-56d38c60]{margin-left:.6rem}a.download .el-icon[data-v-56d38c60]{vertical-align:middle;font-weight:700;margin-left:.3rem}a.download .el-icon.loading[data-v-56d38c60]{animation:loading-56d38c60 1s linear infinite}@keyframes loading-56d38c60{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}a[data-v-a998806a]{color:#666;text-decoration:underline}a.green[data-v-a998806a]{color:green;font-weight:700}img.system[data-v-a998806a]{height:1.6rem;vertical-align:middle;margin-right:.4rem}.ipaddress span[data-v-358fba0e]{vertical-align:middle}.el-input[data-v-358fba0e]{width:15rem;margin-right:.6rem}.el-col[data-v-5b9d3bc4]{text-align:left}.el-icon.loading[data-v-8a7ccef2],a.loading[data-v-8a7ccef2]{vertical-align:middle;font-weight:700;animation:loading-8a7ccef2 1s linear infinite}.el-switch.is-disabled[data-v-8a7ccef2]{opacity:1}.el-input[data-v-8a7ccef2]{width:8rem}.gateway[data-v-8a7ccef2]{background:linear-gradient(90deg,#c5b260,#858585,#c5b260,#858585);-webkit-background-clip:text;-webkit-text-fill-color:hsla(0,0%,100%,0)}.gateway.green[data-v-8a7ccef2]{background:linear-gradient(90deg,#e4bb10,green,#e4bb10,green);-webkit-background-clip:text;-webkit-text-fill-color:hsla(0,0%,100%,0)}.delay[data-v-8a7ccef2]{position:absolute;right:0;bottom:0;line-height:normal}.switch-btn[data-v-8a7ccef2]{font-size:1.5rem}@keyframes loading-8a7ccef2{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.el-switch.is-disabled[data-v-44067f74]{opacity:1}.upgrade-wrap[data-v-44067f74]{border:1px solid #ddd;margin-bottom:2rem;padding:0 0 1rem 0}.el-switch.is-disabled[data-v-56597dfc]{opacity:1}.green[data-v-56597dfc]{font-weight:700}.el-switch.is-disabled[data-v-1f7f67a4]{opacity:1}a[data-v-19db1f43]{text-decoration:underline;font-weight:700}.head[data-v-2c1a8404]{padding-bottom:1rem}.green[data-v-2c1a8404]{color:green;font-weight:700}.error[data-v-2c1a8404]{font-weight:700}.error .el-icon[data-v-2c1a8404]{vertical-align:text-bottom}.el-select[data-v-3a13c86f]{width:12rem}.head[data-v-3a13c86f]{padding-bottom:1rem}.foot[data-v-3a13c86f]{padding-top:1rem}.page-wrap[data-v-3a13c86f]{display:inline-block}.head[data-v-5e37381c]{padding-bottom:1rem}.error[data-v-5e37381c]{font-weight:700}.error .el-icon[data-v-5e37381c]{vertical-align:text-bottom}.el-select[data-v-5512121a]{width:12rem}.head[data-v-5512121a]{padding-bottom:1rem}.foot[data-v-5512121a]{padding-top:1rem}.page-wrap[data-v-5512121a]{display:inline-block}.head[data-v-337b0bab]{padding-bottom:1rem}.table-sort.el-table th.el-table__cell.is-leaf{border-bottom:0}.table-sort.el-table .el-table__inner-wrapper:before{height:0}.table-sort th[data-v-32477317]{border-bottom:0}.home-list-wrap[data-v-32477317]{padding:1rem}.home-list-wrap .page[data-v-32477317]{padding-top:1rem}.home-list-wrap .page-wrap[data-v-32477317]{display:inline-block}

View File

@@ -1 +1 @@
#file-input[data-v-4892cd3c]{opacity:0;position:absolute;z-index:-1}.el-icon[data-v-4892cd3c]{font-size:1.6rem;vertical-align:middle;color:#555}#file-input[data-v-792478eb]{opacity:0;position:absolute;z-index:-1}.head[data-v-792478eb]{background-color:#f6f8fa;border-bottom:1px solid #d0d7de;box-shadow:1px 1px 4px rgba(0,0,0,.05);height:5rem;line-height:5rem}.head .logo[data-v-792478eb]{padding:.5rem 0 0 1rem}.head .logo img[data-v-792478eb]{vertical-align:top;height:4rem}.head .menu[data-v-792478eb]{padding-left:1rem;font-size:1.4rem}.head .menu li[data-v-792478eb]{box-sizing:border-box;padding:.5rem 0;margin-right:.5rem}.head .menu a[data-v-792478eb]{display:block;color:#333;padding:0 1rem;line-height:4rem}.head .menu a.router-link-active[data-v-792478eb],.head .menu a[data-v-792478eb]:hover{background-color:rgba(0,0,0,.1);font-weight:700}.head .menu a .el-icon[data-v-792478eb]{vertical-align:sub}.head .image[data-v-792478eb]{padding-right:1rem}body.sunny{background-image:url(../img/bg.a2158f12.jpg);background-repeat:no-repeat;background-size:cover;background-position:bottom;position:absolute;left:0;top:0;right:0;bottom:0}body.sunny .app-wrap{background-color:hsla(0,0%,100%,.5)}body.sunny .status-wrap{background-color:hsla(0,0%,96%,.3)}body.sunny .status-wrap .copy a{color:#333}body.sunny .el-table{background-color:hsla(0,0%,100%,.5)}body.sunny .head{background-color:rgba(246,248,250,.5)}body.sunny .el-table tr,body.sunny .el-table--striped .el-table__body tr.el-table__row--striped td.el-table__cell{background-color:rgba(246,248,250,.2)}.el-pagination__total,body.sunny .el-pagination__sizes,body.sunny .status-wrap .copy a{color:#000}body.sunny a{color:#576acf}.status-api-wrap[data-v-4470fcde]{padding-right:2rem}.status-api-wrap a[data-v-4470fcde]{color:#333}.status-api-wrap span[data-v-4470fcde]{border-radius:1rem;background-color:rgba(0,0,0,.1);padding:0 .6rem;margin-left:.2rem}.status-api-wrap.connected a[data-v-4470fcde]{color:green;font-weight:700}.status-api-wrap.connected span[data-v-4470fcde]{background-color:green;color:#fff}.status-api-wrap .el-icon[data-v-4470fcde]{vertical-align:text-top}.status-server-wrap[data-v-360b8353]{padding-right:.5rem}.status-server-wrap a[data-v-360b8353]{color:#333}.status-server-wrap a+a[data-v-360b8353]{margin-left:.6rem}.status-server-wrap.connected a[data-v-360b8353]{color:green;font-weight:700}.status-server-wrap .el-icon[data-v-360b8353]{vertical-align:text-bottom}.status-server-wrap a.download .el-icon[data-v-360b8353]{font-weight:700;margin-left:.3rem}.status-server-wrap a.download .el-icon.loading[data-v-360b8353]{animation:loading-360b8353 1s linear infinite}@keyframes loading-360b8353{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.el-col[data-v-5b9d3bc4]{text-align:left}.status-export-wrap[data-v-ebcc59f4]{padding-right:2rem}.status-export-wrap a[data-v-ebcc59f4]{color:#333}.status-export-wrap .el-icon[data-v-ebcc59f4]{vertical-align:text-top}.status-export-wrap .el-col[data-v-ebcc59f4]{text-align:left}a[data-v-56d38c60]{color:#666;text-decoration:underline}a.green[data-v-56d38c60]{color:green;font-weight:700}a.download[data-v-56d38c60]{margin-left:.6rem}a.download .el-icon[data-v-56d38c60]{vertical-align:middle;font-weight:700;margin-left:.3rem}a.download .el-icon.loading[data-v-56d38c60]{animation:loading-56d38c60 1s linear infinite}@keyframes loading-56d38c60{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.status-wrap[data-v-da8e5ef0]{border-top:1px solid #ddd;background-color:#f5f5f5;height:3rem;line-height:3rem;font-size:1.2rem;color:#555}.status-wrap .pay[data-v-da8e5ef0]{font-size:xxx-large}.status-wrap .pay img[data-v-da8e5ef0]{width:100%;margin:0}.status-wrap .copy[data-v-da8e5ef0]{padding-left:.5rem}.status-wrap .copy a[data-v-da8e5ef0]{color:#555}.status-wrap a.memory[data-v-da8e5ef0]{margin-right:.6rem}.status-wrap a.memory img[data-v-da8e5ef0]{height:3rem;vertical-align:bottom;margin-right:.1rem}.body[data-v-0c8014e7]{padding:1rem 0 0 0}.footer[data-v-0c8014e7]{padding:1rem 0}.body[data-v-d9c381d8]{padding:1rem 0 0 0}.footer[data-v-d9c381d8]{padding:1rem 0}.body[data-v-d420efea],.el-card+.el-card[data-v-d9c381d8]{margin-top:1rem}.footer[data-v-d420efea]{margin-top:2rem}@media screen and (max-width:1000px){body .app-wrap[data-v-5ea3415a]{width:calc(100% - 40px);height:calc(100% - 40px);position:absolute;left:20px;top:20px;right:0;bottom:0;transform:none;max-width:calc(100% - 40px)}}.app-wrap[data-v-5ea3415a]{box-sizing:border-box;background-color:#fff;border:1px solid #d0d7de;width:81rem;max-width:80%;height:90%;position:absolute;left:50%;top:50%;transform:translateX(-50%) translateY(-50%)}
#file-input[data-v-4892cd3c]{opacity:0;position:absolute;z-index:-1}.el-icon[data-v-4892cd3c]{font-size:1.6rem;vertical-align:middle;color:#555}#file-input[data-v-792478eb]{opacity:0;position:absolute;z-index:-1}.head[data-v-792478eb]{background-color:#f6f8fa;border-bottom:1px solid #d0d7de;box-shadow:1px 1px 4px rgba(0,0,0,.05);height:5rem;line-height:5rem}.head .logo[data-v-792478eb]{padding:.5rem 0 0 1rem}.head .logo img[data-v-792478eb]{vertical-align:top;height:4rem}.head .menu[data-v-792478eb]{padding-left:1rem;font-size:1.4rem}.head .menu li[data-v-792478eb]{box-sizing:border-box;padding:.5rem 0;margin-right:.5rem}.head .menu a[data-v-792478eb]{display:block;color:#333;padding:0 1rem;line-height:4rem}.head .menu a.router-link-active[data-v-792478eb],.head .menu a[data-v-792478eb]:hover{background-color:rgba(0,0,0,.1);font-weight:700}.head .menu a .el-icon[data-v-792478eb]{vertical-align:sub}.head .image[data-v-792478eb]{padding-right:1rem}body.sunny{background-image:url(../img/bg.a2158f12.jpg);background-repeat:no-repeat;background-size:cover;background-position:bottom;position:absolute;left:0;top:0;right:0;bottom:0}body.sunny .app-wrap{background-color:hsla(0,0%,100%,.5)}body.sunny .status-wrap{background-color:hsla(0,0%,96%,.3)}body.sunny .status-wrap .copy a{color:#333}body.sunny .el-table{background-color:hsla(0,0%,100%,.5)}body.sunny .head{background-color:rgba(246,248,250,.5)}body.sunny .el-table tr,body.sunny .el-table--striped .el-table__body tr.el-table__row--striped td.el-table__cell{background-color:rgba(246,248,250,.2)}.el-pagination__total,body.sunny .el-pagination__sizes,body.sunny .status-wrap .copy a{color:#000}body.sunny a{color:#576acf}.status-api-wrap[data-v-4470fcde]{padding-right:2rem}.status-api-wrap a[data-v-4470fcde]{color:#333}.status-api-wrap span[data-v-4470fcde]{border-radius:1rem;background-color:rgba(0,0,0,.1);padding:0 .6rem;margin-left:.2rem}.status-api-wrap.connected a[data-v-4470fcde]{color:green;font-weight:700}.status-api-wrap.connected span[data-v-4470fcde]{background-color:green;color:#fff}.status-api-wrap .el-icon[data-v-4470fcde]{vertical-align:text-top}.status-server-wrap[data-v-360b8353]{padding-right:.5rem}.status-server-wrap a[data-v-360b8353]{color:#333}.status-server-wrap a+a[data-v-360b8353]{margin-left:.6rem}.status-server-wrap.connected a[data-v-360b8353]{color:green;font-weight:700}.status-server-wrap .el-icon[data-v-360b8353]{vertical-align:text-bottom}.status-server-wrap a.download .el-icon[data-v-360b8353]{font-weight:700;margin-left:.3rem}.status-server-wrap a.download .el-icon.loading[data-v-360b8353]{animation:loading-360b8353 1s linear infinite}@keyframes loading-360b8353{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.el-col[data-v-5b9d3bc4]{text-align:left}.status-export-wrap[data-v-ebcc59f4]{padding-right:2rem}.status-export-wrap a[data-v-ebcc59f4]{color:#333}.status-export-wrap .el-icon[data-v-ebcc59f4]{vertical-align:text-top}.status-export-wrap .el-col[data-v-ebcc59f4]{text-align:left}a[data-v-56d38c60]{color:#666;text-decoration:underline}a.green[data-v-56d38c60]{color:green;font-weight:700}a.download[data-v-56d38c60]{margin-left:.6rem}a.download .el-icon[data-v-56d38c60]{vertical-align:middle;font-weight:700;margin-left:.3rem}a.download .el-icon.loading[data-v-56d38c60]{animation:loading-56d38c60 1s linear infinite}@keyframes loading-56d38c60{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.status-wrap[data-v-da8e5ef0]{border-top:1px solid #ddd;background-color:#f5f5f5;height:3rem;line-height:3rem;font-size:1.2rem;color:#555}.status-wrap .pay[data-v-da8e5ef0]{font-size:xxx-large}.status-wrap .pay img[data-v-da8e5ef0]{width:100%;margin:0}.status-wrap .copy[data-v-da8e5ef0]{padding-left:.5rem}.status-wrap .copy a[data-v-da8e5ef0]{color:#555}.status-wrap a.memory[data-v-da8e5ef0]{margin-right:.6rem}.status-wrap a.memory img[data-v-da8e5ef0]{height:3rem;vertical-align:bottom;margin-right:.1rem}.body[data-v-18ef6737]{padding:1rem 0 0 0}.footer[data-v-18ef6737]{padding:1rem 0}.body[data-v-c9a17ce0]{padding:1rem 0 0 0}.footer[data-v-c9a17ce0]{padding:1rem 0}.body[data-v-d420efea],.el-card+.el-card[data-v-c9a17ce0]{margin-top:1rem}.footer[data-v-d420efea]{margin-top:2rem}@media screen and (max-width:1000px){body .app-wrap[data-v-5ea3415a]{width:calc(100% - 40px);height:calc(100% - 40px);position:absolute;left:20px;top:20px;right:0;bottom:0;transform:none;max-width:calc(100% - 40px)}}.app-wrap[data-v-5ea3415a]{box-sizing:border-box;background-color:#fff;border:1px solid #d0d7de;width:81rem;max-width:80%;height:90%;position:absolute;left:50%;top:50%;transform:translateX(-50%) translateY(-50%)}

View File

@@ -1 +1 @@
<!doctype html><html lang=""><head><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width,initial-scale=1"><link rel="icon" href="favicon.ico"><title>linker.web</title><script defer="defer" src="js/chunk-vendors.df6dc380.js"></script><script defer="defer" src="js/app.052dfaf7.js"></script><link href="css/chunk-vendors.d8267b33.css" rel="stylesheet"><link href="css/app.acc92c6f.css" rel="stylesheet"></head><body><noscript><strong>We're sorry but linker.web doesn't work properly without JavaScript enabled. Please enable it to continue.</strong></noscript><div id="app"></div></body></html>
<!doctype html><html lang=""><head><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width,initial-scale=1"><link rel="icon" href="favicon.ico"><title>linker.web</title><script defer="defer" src="js/chunk-vendors.df6dc380.js"></script><script defer="defer" src="js/app.17874bee.js"></script><link href="css/chunk-vendors.d8267b33.css" rel="stylesheet"><link href="css/app.acc92c6f.css" rel="stylesheet"></head><body><noscript><strong>We're sorry but linker.web doesn't work properly without JavaScript enabled. Please enable it to continue.</strong></noscript><div id="app"></div></body></html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -195,7 +195,7 @@ namespace linker.tun
private void Read()
{
Task.Run(async () =>
TimerHelper.Async(async () =>
{
cancellationTokenSource = new CancellationTokenSource();
while (cancellationTokenSource.IsCancellationRequested == false)

View File

@@ -424,7 +424,7 @@ namespace linker.tunnel
/// </summary>
/// <param name="remoteMachineId"></param>
/// <param name="transactionId"></param>
public void StartBackground(string remoteMachineId, string transactionId, TunnelProtocolType denyProtocols,Func<bool> stopCallback, int times = 10)
public void StartBackground(string remoteMachineId, string transactionId, TunnelProtocolType denyProtocols, Func<bool> stopCallback, int times = 10)
{
if (AddBackground(remoteMachineId, transactionId) == false)
{
@@ -432,13 +432,13 @@ namespace linker.tunnel
LoggerHelper.Instance.Error($"tunnel background {remoteMachineId}@{transactionId} already exists");
return;
}
Task.Run(async () =>
TimerHelper.Async(async () =>
{
try
{
for (int i = 1; i <= times; i++)
{
await Task.Delay(i*3000);
await Task.Delay(i * 3000);
if (stopCallback()) break;
@@ -467,7 +467,7 @@ namespace linker.tunnel
{
backgroundDic.TryRemove(GetBackgroundKey(remoteMachineId, transactionId), out _);
}
private bool IsBackground(string remoteMachineId, string transactionId)
public bool IsBackground(string remoteMachineId, string transactionId)
{
return backgroundDic.ContainsKey(GetBackgroundKey(remoteMachineId, transactionId));
}

View File

@@ -296,9 +296,7 @@ namespace linker.tunnel.proxy
/// </summary>
private void TaskUdp()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
var connections = udpConnections.Where(c => c.Value.Timeout).Select(c => c.Key).ToList();
foreach (var item in connections)
@@ -314,10 +312,8 @@ namespace linker.tunnel.proxy
}
}
}
await Task.Delay(5000).ConfigureAwait(false);
}
});
return true;
},5000);
}
private void CloseClientSocketUdp(ITunnelConnection connection)

View File

@@ -356,7 +356,7 @@ namespace linker.tunnel.transport
socketUdp.ReuseBind(local);
socketUdp.WindowsUdpBug();
Task.Run(async () =>
TimerHelper.Async(async () =>
{
byte[] buffer = new byte[(1 << bufferSize) * 1024];
try
@@ -704,7 +704,7 @@ namespace linker.tunnel.transport
{
QuicConnection quicConnection = await listener.AcceptConnectionAsync().ConfigureAwait(false);
_ = Task.Run(async () =>
TimerHelper.Async(async () =>
{
while (true)
{

View File

@@ -84,7 +84,7 @@ namespace linker.tunnel.transport
{
Socket client = await socket.AcceptAsync();
_ = Task.Run(async () =>
TimerHelper.Async(async () =>
{
try
{

View File

@@ -177,7 +177,7 @@ namespace linker.tunnel.transport
socket.WindowsUdpBug();
socket.ReuseBind(local);
Task.Run(async () =>
TimerHelper.Async(async () =>
{
byte[] buffer = new byte[1024];
SocketReceiveFromResult result = await socket.ReceiveFromAsync(buffer, new IPEndPoint(IPAddress.Any, 0)).ConfigureAwait(false);

View File

@@ -348,9 +348,7 @@ namespace linker.tunnel.transport
private void CleanTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
long ticks = Environment.TickCount64;
var keys = connectionsDic.Where(c => (c.Value.Connection == null && ticks - c.Value.LastTicks > 5000) || (c.Value.Connection != null && c.Value.Connection.Connected == false)).Select(c => c.Key).ToList();
@@ -358,10 +356,8 @@ namespace linker.tunnel.transport
{
connectionsDic.TryRemove(item, out _);
}
await Task.Delay(30000);
}
});
return true;
}, 30000);
}
}

View File

@@ -51,7 +51,7 @@
</el-dialog>
</template>
<script>
import { reactive, watch,computed, inject } from 'vue';
import { reactive, watch,computed, onMounted, onUnmounted } from 'vue';
import { ElMessage } from 'element-plus';
import { useConnections, useForwardConnections, useTuntapConnections } from './connections';
import { Delete } from '@element-plus/icons-vue';
@@ -66,7 +66,7 @@ export default {
const hasTunnelRemove = computed(()=>globalData.value.hasAccess('TunnelRemove'));
const connections = useConnections();
const forwardConnections =useForwardConnections();
const forwardConnections = useForwardConnections();
const tuntapConnections = useTuntapConnections();
const state = reactive({
show: true,
@@ -96,6 +96,13 @@ export default {
}).catch(()=>{});
}
onMounted(()=>{
connections.value.updateRealTime(true);
});
onUnmounted(()=>{
connections.value.updateRealTime(false);
})
return {
state,handleDel,hasTunnelRemove
}

View File

@@ -1,13 +1,11 @@
import { getForwardConnections, removeForwardConnection } from "@/apis/forward";
import { getTuntapConnections, removeTuntapConnection } from "@/apis/tuntap";
import { injectGlobalData } from "@/provide";
import { inject, provide, ref } from "vue";
const connectionsSymbol = Symbol();
const forwardConnectionsSymbol = Symbol();
const tuntapConnectionsSymbol = Symbol();
export const provideConnections = () => {
const globalData = injectGlobalData();
const connections = ref({
showEdit: false,
speedCache: {},
@@ -15,6 +13,13 @@ export const provideConnections = () => {
currentName: '',
hashcode: 0,
hashcode1: 0,
_updateRealTime: false,
updateRealTime: (value) => {
connections.value.hashcode = 0;
connections.value.hashcode1 = 0;
connections.value._updateRealTime = value;
}
});
provide(connectionsSymbol, connections);
@@ -23,8 +28,11 @@ export const provideConnections = () => {
list: {},
});
provide(forwardConnectionsSymbol, forwardConnections);
const _getForwardConnections = () => {
getForwardConnections(connections.value.hashcode.toString()).then((res) => {
if (connections.value._updateRealTime == false)
connections.value.hashcode = res.HashCode;
if (res.List) {
parseConnections(res.List, removeForwardConnection);
@@ -43,6 +51,7 @@ export const provideConnections = () => {
provide(tuntapConnectionsSymbol, tuntapConnections);
const _getTuntapConnections = () => {
getTuntapConnections(connections.value.hashcode1.toString()).then((res) => {
if (connections.value._updateRealTime == false)
connections.value.hashcode1 = res.HashCode;
if (res.List) {
parseConnections(res.List, removeTuntapConnection);

View File

@@ -52,12 +52,12 @@
<el-form-item label="" label-width="0" v-if="state.form.hasServer">
<el-row>
<el-col :span="12">
<el-form-item label="服务" prop="server">
<el-form-item label="信标服务" prop="server">
<el-input v-model="state.form.server"/>
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="服务器密钥" prop="serverSecretKey">
<el-form-item label="信标密钥" prop="serverSecretKey">
<el-input v-model="state.form.serverSecretKey" maxlength="36" show-word-limit />
</el-form-item>
</el-col>

View File

@@ -35,7 +35,7 @@
<el-form-item label="" label-width="0">
<el-row>
<el-col :span="24">
<el-form-item label="服务器密钥" prop="signinSecretKey">
<el-form-item label="信标密钥" prop="signinSecretKey">
<el-input v-model="state.form.signinSecretKey" maxlength="36" show-word-limit />
</el-form-item>
</el-col>

View File

@@ -121,9 +121,7 @@ namespace linker
{
}
};
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
string[] files = Directory.GetFiles("logs").OrderBy(c => c).ToArray();
for (int i = 0; i < files.Length - 7; i++)
@@ -136,9 +134,8 @@ namespace linker
{
}
}
await Task.Delay(60 * 1000);
}
});
return true;
}, 60 * 1000);
}
}

View File

@@ -104,18 +104,15 @@ namespace linker.config
private void SaveTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
while (Data.Updated > 0)
{
Save();
Data.Updated--;
}
await Task.Delay(1000).ConfigureAwait(false);
}
});
return true;
}, 1000);
}
}

View File

@@ -56,9 +56,7 @@ namespace linker.plugins.client
/// </summary>
public void SignInTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(async () =>
{
if (clientSignInState.Connected == false)
{
@@ -72,9 +70,8 @@ namespace linker.plugins.client
LoggerHelper.Instance.Error(ex);
}
}
await Task.Delay(10000).ConfigureAwait(false);
}
});
return true;
},10000);
}
/// <summary>

View File

@@ -45,18 +45,15 @@ namespace linker.client.config
}
private void SaveTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
while (Data.Updated > 0)
{
Save();
Data.Updated--;
}
await Task.Delay(1000).ConfigureAwait(false);
}
});
return true;
}, 1000);
}
private void Save()
{

View File

@@ -36,7 +36,7 @@ namespace linker.plugins.forward
private void Reset(int times)
{
Task.Run(async () =>
TimerHelper.Async(async () =>
{
await TestListen();
Stop();

View File

@@ -311,15 +311,11 @@ namespace linker.plugins.relay
}
private void TestTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(async () =>
{
await TaskRelay();
await Task.Delay(5000);
}
});
return true;
}, 5000);
}
sealed class TestInfo
{

View File

@@ -246,7 +246,7 @@ namespace linker.plugins.sforward
if (testing) return;
testing = true;
Task.Run(async () =>
TimerHelper.Async(async () =>
{
try
{

View File

@@ -79,7 +79,7 @@ namespace linker.plugins.sforward.proxy
byte[] buf = ArrayPool<byte>.Shared.Rent(length);
memory.CopyTo(buffer);
_ = Task.Run(async () =>
TimerHelper.Async(async () =>
{
ulong id = ns.Increment();
try
@@ -185,7 +185,7 @@ namespace linker.plugins.sforward.proxy
udpConnectds.TryAdd(id, new UdpConnectedCache { SourceSocket = socketUdp, TargetSocket = serviceUdp });
_ = Task.Run(async () =>
TimerHelper.Async(async () =>
{
buffer = new byte[(1 << bufferSize) * 1024];
IPEndPoint tempEp = new IPEndPoint(IPAddress.Any, IPEndPoint.MinPort);
@@ -237,9 +237,7 @@ namespace linker.plugins.sforward.proxy
private void UdpTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(() =>
{
var connections = udpConnections.Where(c => c.Value.Timeout).Select(c => c.Key);
foreach (var item in connections)
@@ -255,12 +253,9 @@ namespace linker.plugins.sforward.proxy
cache.Clear();
}
}
await Task.Delay(5000).ConfigureAwait(false);
return true;
}, 5000);
}
});
}
}
public sealed class UdpTargetCache

View File

@@ -59,7 +59,7 @@ namespace linker.plugins.tuntap
}
private void Initialize()
{
Task.Run(() =>
TimerHelper.Async(() =>
{
LoggerHelper.Instance.Debug($"tuntap initialize");
linkerTunDeviceAdapter.Shutdown();
@@ -85,7 +85,7 @@ namespace linker.plugins.tuntap
{
return;
}
Task.Run(() =>
TimerHelper.Async(() =>
{
SetupBefore();
try
@@ -189,7 +189,7 @@ namespace linker.plugins.tuntap
/// <param name="info"></param>
public void UpdateConfig(TuntapInfo info)
{
Task.Run(() =>
TimerHelper.Async(() =>
{
DeleteForward();
runningConfig.Data.Tuntap.IP = info.IP;
@@ -218,7 +218,7 @@ namespace linker.plugins.tuntap
/// <returns></returns>
public TuntapInfo OnConfig(TuntapInfo info)
{
Task.Run(async () =>
TimerHelper.Async(async () =>
{
await slim.WaitAsync();
try
@@ -241,7 +241,7 @@ namespace linker.plugins.tuntap
/// </summary>
private void NotifyConfig()
{
Task.Run(async () =>
TimerHelper.Async(async () =>
{
await slim.WaitAsync();
try
@@ -438,23 +438,14 @@ namespace linker.plugins.tuntap
private void CheckTuntapStatusTask()
{
Task.Run(async () =>
{
while (true)
{
await Task.Delay(15000).ConfigureAwait(false);
try
TimerHelper.SetInterval(async () =>
{
if (runningConfig.Data.Tuntap.Running && OperatingSystem.IsWindows())
{
await InterfaceCheck().ConfigureAwait(false);
}
}
catch (Exception)
{
}
}
});
return true;
}, 15000);
}
private async Task InterfaceCheck()
{
@@ -491,9 +482,7 @@ namespace linker.plugins.tuntap
private void PingTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(async () =>
{
if (Status == TuntapStatus.Running && (runningConfig.Data.Tuntap.Switch & TuntapSwitch.ShowDelay) == TuntapSwitch.ShowDelay)
{
@@ -513,9 +502,8 @@ namespace linker.plugins.tuntap
Version.Add();
}
}
await Task.Delay(3000);
}
});
return true;
}, 3000);
}
}
}

View File

@@ -10,7 +10,6 @@ using linker.plugins.tuntap.config;
using linker.tun;
using System.Buffers.Binary;
using linker.plugins.client;
using System.Net.Sockets;
namespace linker.plugins.tuntap.proxy
{
@@ -55,14 +54,20 @@ namespace linker.plugins.tuntap.proxy
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG)
LoggerHelper.Instance.Warning($"tuntap add connection {connection.GetHashCode()} {connection.ToJson()}");
if (connections.TryGetValue(connection.RemoteMachineId, out ITunnelConnection connectionOld))
if (connections.TryGetValue(connection.RemoteMachineId, out ITunnelConnection connectionOld) && connection.Equals(connectionOld) == false)
{
connections.AddOrUpdate(connection.RemoteMachineId, connection, (a, b) => connection);
TimerHelper.SetTimeout(connectionOld.Dispose,5000);
LoggerHelper.Instance.Error($"new tunnel del {connection.Equals(connectionOld)}->{connectionOld.GetHashCode()}:{connectionOld.IPEndPoint}->{connection.GetHashCode()}:{connection.IPEndPoint}");
}
else
{
connections.AddOrUpdate(connection.RemoteMachineId, connection, (a, b) => connection);
}
connection.BeginReceive(this, null);
ipConnections.Clear();
Version.Add();
}
public async Task Receive(ITunnelConnection connection, ReadOnlyMemory<byte> buffer, object state)
@@ -76,6 +81,7 @@ namespace linker.plugins.tuntap.proxy
await Task.CompletedTask;
}
public async Task Callback(LinkerTunDevicPacket packet)
{
//IPV4广播组播
@@ -120,6 +126,7 @@ namespace linker.plugins.tuntap.proxy
await connection.SendAsync(packet.Packet);
}
/// <summary>
/// 设置IP等下有连接进来用IP匹配才能知道这个连接是要连谁
/// </summary>
@@ -197,23 +204,8 @@ namespace linker.plugins.tuntap.proxy
return null;
}
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap tunnel to {machineId}");
connection = await RelayAndP2P(machineId);
connection = await tunnelTransfer.ConnectAsync(machineId, "tuntap", TunnelProtocolType.Quic).ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap tunnel success,{connection.ToString()}");
}
if (connection == null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay to {machineId}");
connection = await relayTransfer.ConnectAsync(config.Data.Client.Id, machineId, "tuntap").ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay success,{connection.ToString()}");
}
}
if (connection != null)
{
connections.AddOrUpdate(machineId, connection, (a, b) => connection);
@@ -228,6 +220,56 @@ namespace linker.plugins.tuntap.proxy
}
return connection;
}
private async Task<ITunnelConnection> P2PAndRelay(string machineId)
{
if (tunnelTransfer.IsBackground(machineId, "tuntap")) return null;
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap tunnel to {machineId}");
ITunnelConnection connection = await tunnelTransfer.ConnectAsync(machineId, "tuntap", TunnelProtocolType.Quic).ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap tunnel success,{connection.ToString()}");
}
else
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay to {machineId}");
connection = await relayTransfer.ConnectAsync(config.Data.Client.Id, machineId, "tuntap").ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay success,{connection.ToString()}");
tunnelTransfer.StartBackground(machineId, "tuntap", TunnelProtocolType.Quic, () =>
{
return connections.TryGetValue(machineId, out ITunnelConnection connection) && connection.Connected && connection.Type == TunnelType.P2P;
});
}
}
return connection;
}
private async Task<ITunnelConnection> RelayAndP2P(string machineId)
{
if (tunnelTransfer.IsBackground(machineId, "tuntap")) return null;
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay to {machineId}");
ITunnelConnection connection = await relayTransfer.ConnectAsync(config.Data.Client.Id, machineId, "tuntap").ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay success,{connection.ToString()}");
tunnelTransfer.StartBackground(machineId, "tuntap", TunnelProtocolType.Quic, () =>
{
return connections.TryGetValue(machineId, out ITunnelConnection connection) && connection.Connected && connection.Type == TunnelType.P2P;
});
}
else
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap tunnel to {machineId}");
connection = await tunnelTransfer.ConnectAsync(machineId, "tuntap", TunnelProtocolType.Quic).ConfigureAwait(false);
if (connection != null)
{
if (LoggerHelper.Instance.LoggerLevel <= LoggerTypes.DEBUG) LoggerHelper.Instance.Debug($"tuntap relay success,{connection.ToString()}");
}
}
return connection;
}
public ConcurrentDictionary<string, ITunnelConnection> GetConnections()
{
@@ -248,6 +290,5 @@ namespace linker.plugins.tuntap.proxy
}
}
}
}

View File

@@ -97,9 +97,7 @@ namespace linker.plugins.updater
private void UpdateTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(async () =>
{
if (updateInfo.Updated)
{
@@ -112,21 +110,17 @@ namespace linker.plugins.updater
});
Update(updateInfo);
}
await Task.Delay(1000);
}
});
return true;
}, 1000);
}
private void LoadTask()
{
Task.Run(async () =>
{
while (true)
TimerHelper.SetInterval(async () =>
{
await updaterHelper.GetUpdateInfo(updateInfo);
await Task.Delay(15000);
}
});
return true;
}, 15000);
}
}

View File

@@ -41,7 +41,7 @@ namespace linker.plugins.updater
using HttpClient httpClient = new HttpClient();
string str = await httpClient.GetStringAsync($"{fileConfig.Data.Common.UpdateUrl}/version.txt").WaitAsync(TimeSpan.FromSeconds(15));
string[] arr = str.Split(Environment.NewLine).Select(c=>c.Trim('\r').Trim('\n')).ToArray();
string[] arr = str.Split(Environment.NewLine).Select(c => c.Trim('\r').Trim('\n')).ToArray();
string datetime = DateTime.Parse(arr[1]).ToString("yyyy-MM-dd HH:mm:ss");
string tag = arr[0];
@@ -205,7 +205,7 @@ namespace linker.plugins.updater
/// <param name="version"></param>
public void Confirm(UpdateInfo updateInfo, string version)
{
Task.Run(async () =>
TimerHelper.Async(async () =>
{
await DownloadUpdate(updateInfo, version);
await ExtractUpdate(updateInfo);

View File

@@ -1,3 +1,3 @@
v1.3.7
2024-09-16 01:46:15
2024-09-16 15:07:51
1. 修复首次启动客户端时虚拟网卡路由不到目标客户端的BUG