Skip to content

Commit 2788fd4

Browse files
committed
do client authorize when start reverse connection.
1 parent 91073e4 commit 2788fd4

10 files changed

Lines changed: 97 additions & 33 deletions

File tree

src/NSmartProxy.ClientRouter/Router.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,7 @@ public class Router
4949

5050
public ServerConnnectionManager ConnectionManager;
5151
public bool IsStarted = false;
52+
public string Token = Global.NO_TOKEN_STRING;
5253

5354
internal Config ClientConfig;
5455
internal static INSmartLogger Logger = new NullLogger(); //inject

src/NSmartProxy.ClientRouter/ServerConnnectionManager.cs

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ public class ServerConnnectionManager
2424
{
2525
private int MAX_CONNECT_SIZE = 6;//magic value,单个应用最大连接数,有些应用端支持多连接,需要调高此值,当该值较大时,此值会增加
2626
private int _clientID = 0;
27-
private string _token = "notoken";
27+
private string _token = Global.NO_TOKEN_STRING;
2828

2929
public List<TcpClient> ConnectedConnections;
3030
public ServiceClientListCollection ServiceClientList; //key:appid value;ClientApp
@@ -190,7 +190,22 @@ public async Task ConnectAppToServer(int appid)
190190
try
191191
{
192192
//1.连接服务端
193-
await secclient.ConnectWithAuthAsync(config.ProviderAddress, config.ProviderPort);
193+
var state = await secclient.ConnectWithAuthAsync(config.ProviderAddress, config.ProviderPort);
194+
switch (state)
195+
{
196+
case AuthState.Success:
197+
Router.Logger.Debug("验证成功。");
198+
break;
199+
case AuthState.Fail:
200+
Router.Logger.Debug("验证失败。");
201+
//终止程序
202+
return;
203+
case AuthState.Error:
204+
Router.Logger.Debug("校验出错。");
205+
//终止程序
206+
return;
207+
}
208+
194209
//2.发送clientid和appid信息,向服务端申请连接
195210
//连接到位后增加相关的元素并且触发客户端连接事件
196211
await client.GetStream().WriteAndFlushAsync(requestBytes, 0, requestBytes.Length);

src/NSmartProxy.Infrastructure/Shared/Global.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
/// </summary>
66
public sealed class Global
77
{
8+
public const string NO_TOKEN_STRING = "notoken";
89
public const string NSmartProxyClientName = "NSmartProxy Client v0.6";
910
public const string NSmartProxyServerName = "NSmartProxy Server v0.6";
1011

src/NSmartProxy.Infrastructure/Shared/IDbOperator.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ public interface IDbOperator : IDisposable
1111
void Update(long key, string value);
1212
List<string> Select(int startIndex, int length);
1313
string Get(long key);
14+
string Get(string key);
1415
void Delete(int index);
1516
long GetLength();
1617
void Close();

src/NSmartProxy.Infrastructure/Shared/SecurityTcpClient.cs

Lines changed: 29 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
using System.Threading.Tasks;
99
using NSmartProxy.Database;
1010
using NSmartProxy.Infrastructure;
11+
using NSmartProxy.Shared;
1112

1213
namespace NSmartProxy.Authorize
1314
{
@@ -37,23 +38,23 @@ public static async Task<SecurityTcpClient> AcceptSecureTcpClientAsync(this TcpL
3738
return stc;
3839
}
3940

40-
public static SecurityTcpClient WrapClient(this TcpClient client,string secureToken)
41+
public static SecurityTcpClient WrapClient(this TcpClient client, string secureToken)
4142
{
4243
return new SecurityTcpClient(secureToken, null, ClientTypeEnum.Client, client);
4344
}
4445

45-
public static SecurityTcpClient WrapServer(this TcpClient client,IDbOperator dbOp)
46+
public static SecurityTcpClient WrapServer(this TcpClient client, IDbOperator dbOp)
4647
{
4748
return new SecurityTcpClient(null, dbOp, ClientTypeEnum.Server, client);
4849
}
4950
}
5051

51-
public enum AuthState
52+
public enum AuthState : byte
5253
{
53-
Success,
54-
Fail,
55-
Timeout,
56-
Error
54+
Success = 0x01,
55+
Fail = 0x00,
56+
Timeout = 0xFF,
57+
Error = 0x99,
5758
}
5859

5960
public enum ClientTypeEnum
@@ -66,13 +67,14 @@ public enum ClientTypeEnum
6667
/// 2位固定0xF9 2 n
6768
/// 服务端需要指定持久化逻辑,客户端只需token
6869
/// </summary>
69-
public class SecurityTcpClient
70+
public class SecurityTcpClient
7071
{
7172
public IDbOperator DbOp;
7273

7374
public string Token = "";
7475
public readonly byte F9 = 0xF9;//固定标识位
7576
public String ErrorMessage = "";
77+
public bool AllowAnonymousUser = false;
7678
//TODO 是否校验
7779
public bool IsValid;
7880
public ClientTypeEnum ClientType;
@@ -83,30 +85,26 @@ public class SecurityTcpClient
8385
/// </summary>
8486
/// <param name="secureToken"></param>
8587
/// <param name="dbOp"></param>
86-
public SecurityTcpClient(string secureToken, IDbOperator dbOp, ClientTypeEnum clientType,TcpClient client)
88+
public SecurityTcpClient(string secureToken, IDbOperator dbOp, ClientTypeEnum clientType, TcpClient client)
8789
{
8890
Token = secureToken;
8991
DbOp = dbOp;
9092
ClientType = clientType;
9193
Client = client;
9294
}
9395

94-
95-
96-
97-
9896

9997
/// <summary>
10098
/// 带加密串传输
10199
/// </summary>
102100
/// <param name="host"></param>
103101
/// <param name="port"></param>
104102
/// <returns></returns>
105-
public async Task ConnectWithAuthAsync(string host, int port)
103+
public async Task<AuthState> ConnectWithAuthAsync(string host, int port)
106104
{
107105
if (String.IsNullOrEmpty(Token))
108106
{
109-
return;
107+
return AuthState.Error;
110108
}
111109

112110
//标识位 token长度 值
@@ -117,10 +115,12 @@ public async Task ConnectWithAuthAsync(string host, int port)
117115
await stream.WriteAsync(new byte[] { F9 }, 0, 1);//1标识 长度1
118116
await stream.WriteAsync(StringUtil.IntTo2Bytes(Token.Length), 0, 2);//2token长度 长度2
119117
await stream.WriteAndFlushAsync(ASCIIEncoding.ASCII.GetBytes(Token));//3token
118+
byte[] bytes = new byte[1];
119+
await stream.ReadAsync(bytes, 0, 1);
120+
return (AuthState)bytes[0];
120121
}
121122

122123

123-
124124
/// <summary>
125125
/// 服务端校验
126126
/// </summary>
@@ -159,13 +159,20 @@ public async Task<AuthResult> AuthorizeAsync()
159159

160160
var token = ASCIIEncoding.ASCII.GetString(tokenBytes);
161161
//TODO ***校验Token
162-
if (token == "notoken")
162+
if (token == Global.NO_TOKEN_STRING)
163163
{
164-
return new AuthResult()
165-
{
166-
ErrorMessage = "校验成功",
167-
ResultState = AuthState.Success
168-
};
164+
if (AllowAnonymousUser)
165+
return new AuthResult()
166+
{
167+
ErrorMessage = "校验成功",
168+
ResultState = AuthState.Success
169+
};
170+
else
171+
return new AuthResult()
172+
{
173+
ErrorMessage = "校验失败,服务端不支持匿名登陆",
174+
ResultState = AuthState.Fail
175+
};
169176
}
170177
else
171178
{

src/NSmartProxy/ClientConnectionManager.cs

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ public class ClientConnectionManager
3434
private ClientConnectionManager()
3535
{
3636
Server.Logger.Debug("ClientManager initialized");
37-
// Task.Run(ListenServiceClient);
37+
// Task.Run(ListenServiceClient);
3838
}
3939

4040
private readonly object _lockObject = new Object();
@@ -59,7 +59,7 @@ public async Task ListenServiceClient(IDbOperator dbOp)
5959
}
6060

6161
/// <summary>
62-
/// 处理反向连接请求
62+
/// 处理反向连接请求(服务端)
6363
/// </summary>
6464
/// <param name="incomeClient"></param>
6565
/// <returns></returns>
@@ -72,7 +72,13 @@ private async Task ProcessReverseRequest(SecurityTcpClient incomeClient)
7272
if (!result.IsSuccess)
7373
{
7474
Server.Logger.Debug("SecurityTcpClient校验失败:" + incomeClient.ErrorMessage);
75-
iClient.Close();//如果校验失败则直接关闭连接
75+
await iClient.GetStream().WriteAsync(new byte[] { (byte)result.ResultState });
76+
iClient.Close();//如果校验失败则发送一个字节的直接关闭连接
77+
}
78+
else
79+
{
80+
Server.Logger.Debug("SecurityTcpClient校验成功!");
81+
await iClient.GetStream().WriteAsync(new byte[] { (byte)result.ResultState });
7682
}
7783

7884
//读取头四个字节
@@ -150,7 +156,7 @@ public byte[] ArrageConfigIds(byte[] appRequestBytes, byte[] consumerPortBytes)
150156

151157
clientModel.ClientId = tempClientId;
152158
clientId = tempClientId;
153-
159+
154160
break;
155161
}
156162
}

src/NSmartProxy/Database/NSmartDb.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -178,5 +178,11 @@ public string Get(long key)
178178
{
179179
return Bytes2String(hashf.Get(BitConverter.GetBytes(key)));
180180
}
181+
182+
public string Get(string key)
183+
{
184+
var point2Value = hashf.Get(String2Bytes(key));
185+
return Bytes2String(hashf.Get(point2Value));
186+
}
181187
}
182188
}

src/NSmartProxy/Extension/HttpServerStaticFiles/login.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
<img class="mb-4" src="favicon.ico" alt="" width="72" height="72">
3939
<h1 class="h3 mb-3 font-weight-normal">Please sign in</h1>
4040
<label for="inputEmail" class="sr-only">UserName</label>
41-
<input type="number" min="0" max="65535" id="inputEmail" name="userName" class="form-control" placeholder="UserName" required autofocus>
41+
<input type="text" id="inputEmail" name="userName" class="form-control" placeholder="UserName" required autofocus>
4242
<label for="inputPassword" class="sr-only">Password</label>
4343
<input type="password" id="inputPassword" name="userPwd" class="form-control" placeholder="Password" required>
4444
<div class="checkbox mb-3">

src/NSmartProxy/Extension/HttpServer_APIs.cs

Lines changed: 30 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
using System.Net.Sockets;
55
using System.Text;
66
using NSmartProxy.Database;
7+
using NSmartProxy.Shared;
78

89
namespace NSmartProxy.Extension
910
{
@@ -49,11 +50,11 @@ public string[] GetLogInfo(string filekey)
4950

5051
#region login
5152
[FormAPI]
52-
public string Login(string userid, string userpwd)
53+
public string Login(string username, string userpwd)
5354
{
5455

5556
//1.校验
56-
dynamic user = Dbop.Get(long.Parse(userid))?.ToDynamic();
57+
dynamic user = Dbop.Get(username)?.ToDynamic();
5758
if (user == null)
5859
{
5960
return "error: user not exist.";
@@ -64,7 +65,7 @@ public string Login(string userid, string userpwd)
6465
}
6566

6667
//2.给token
67-
string output = $"{userid}|{DateTime.Now.ToString("yyyy-MM-dd")}";
68+
string output = $"{username}|{DateTime.Now.ToString("yyyy-MM-dd")}";
6869
string token = EncryptHelper.AES_Encrypt(output);
6970
return string.Format(@"
7071
<html>
@@ -77,6 +78,32 @@ public string Login(string userid, string userpwd)
7778
</html>
7879
", token);
7980
}
81+
82+
/// <summary>
83+
/// 提供非web的登陆方法
84+
/// </summary>
85+
/// <param name="username"></param>
86+
/// <param name="userpwd"></param>
87+
/// <returns></returns>
88+
[API]
89+
public string LoginFromClient(string username, string userpwd)
90+
{
91+
//1.校验
92+
dynamic user = Dbop.Get(username)?.ToDynamic();
93+
if (user == null)
94+
{
95+
return "error: user not exist.";
96+
}
97+
if (user.userPwd != EncryptHelper.SHA256(userpwd))
98+
{
99+
return "error: wrong password.";
100+
}
101+
102+
//2.给token
103+
string output = $"{username}|{DateTime.Now.ToString("yyyy-MM-dd")}";
104+
string token = EncryptHelper.AES_Encrypt(output);
105+
return new { token = token, version = Global.NSmartProxyServerName }.ToJsonString();
106+
}
80107
#endregion
81108

82109
#region users

src/NSmartProxyClient/appsettings.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
"ProviderPort": "19974", //反向连接的端口
33
"ProviderConfigPort": "12308", //配置服务的端口
44
//"ProviderAddress": "47.90.204.25", //配置服务的地址,可以是域名(eg.:www.tmoonlight.com)也可以是ip(eg.:211.54.5.4)
5-
"ProviderAddress": "2017studio.imwork.net",
5+
"ProviderAddress": "127.0.0.1",
66
//"ProviderAddress": "124.116.157.31",
77

88
//反向代理客户端,可以配置多个

0 commit comments

Comments
 (0)