private void OnPackageReceived(Socket socket, NatPackageInfo packageInfo) { Task.Run(() => { var tcpModel = packageInfo.Raw; //先gzip压缩 再转为16进制字符串 var body = DataHelper.Compress(packageInfo.Raw); var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.TCP, Action = (int)TcpAction.TransferData, Data = new TcpModel() { ServerId = RemoteSession.ServerId, Host = RemoteSession.Host, Local = RemoteSession.Local, SessionId = RemoteSession.SessionId, Content = body }.ToJson() }); //转发给服务器 NatClient.Send(pack); HandleLog.WriteLine($"<---- {RemoteSession.SessionId} 收到报文{packageInfo.Raw.Length}字节"); }); }
private void Received(TcpSession session, NatRequestInfo requestInfo) { Task.Run(() => { try { while (session.NatSession == null) { Thread.Sleep(50); } //先gzip压缩 再转为16进制字符串 var body = DataHelper.Compress(requestInfo.Raw); //转发数据 var pack = new JsonData() { Type = (int)JsonType.TCP, Action = (int)TcpAction.TransferData, Data = new TcpModel() { ServerId = ServerId, Host = session.Map?.remote_endpoint, Local = session.Map?.local_endpoint, SessionId = session.SessionId, Content = body }.ToJson() }; session.NatSession.Send(PackHelper.CreatePack(pack)); HandleLog.WriteLine($"<---- {session.SessionId} 收到报文{body.Length}字节"); } catch (Exception ex) { HandleLog.WriteLine($"【{session.Local}】请求参数:{requestInfo.Raw.ToHexWithSpace()},处理发生异常:{ex}"); } }); }
public static void ChangeMap(int type, Map map) { try { map.ChangeType = type; ChangeMapList(map); var natClient = NATServer.GetSingle(c => c.Client?.id == map.client_id); if (natClient == null) { return; } ChangeMap(map, natClient); var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.NAT, Action = (int)NatAction.MapChange, Data = map.ToJson() }); natClient.Send(pack); } catch (Exception ex) { HandleLog.WriteLine($"映射更新异常:{ex},参数为:{JsonHelper.Instance.Serialize(map)}"); } }
public ActionResult Index() { ViewBag.Message = "Top Trumps is the card game that brings your favourite things to life, whether it's fast cars, football or Star Wars."; packHelper.CreatePack(); return(View()); }
static void OnClientConnected(Socket socket) { //发送注册包给服务端 var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.NAT, Action = (int)NatAction.Connect, Data = Secret }); NatClient?.Send(pack); }
public void SendServerMessage(NatSession session, ServerMessage serverMessage) { HandleLog.WriteLine(serverMessage.Message); var pack = new JsonData() { Type = (int)JsonType.NAT, Action = (int)NatAction.ServerMessage, Data = serverMessage.ToJson() }; //转发给客户端 session?.Send(PackHelper.CreatePack(pack)); }
private void Received(HttpSession session, HttpRequestInfo requestInfo) { try { var httpModel = new HttpModel { RequestTime = DateTime.Now, ServerId = ServerId, SessionId = session.SessionId }; var filter = ReceiveFilter as HttpReceiveFilter; filter.DecodePackage(ref httpModel); //转发请求 var natSession = NATServer.GetSingle(c => c.MapList.Any(c => c.remote_endpoint == httpModel.Host)); if (natSession == null) { //TODO 错误页面 HandleLog.WriteLine($"穿透客户端未连接到服务器,请求地址:{httpModel.Host}{httpModel.Path}"); var response = new HttpResponse() { Status = 404, ContentType = "text/html", Body = Encoding.UTF8.GetBytes("nat client not found") }; //把处理信息返回到客户端 session.Send(response.Write()); } else { //转发数据 var pack = new JsonData() { Type = (int)JsonType.HTTP, Action = (int)HttpAction.Request, Data = httpModel.ToJson() }; natSession.Send(PackHelper.CreatePack(pack)); session.NatSession = natSession; } } catch (Exception ex) { HandleLog.WriteLine($"【{session.Local}】请求地址:{requestInfo.BaseUrl}{requestInfo.Path},处理发生异常:{ex}"); } }
static void SendHeart() { while (IsReConnect) { Thread.Sleep(50000); if (NatClient.IsConnected) { //发送心跳包给服务端 var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.NAT, Action = (int)NatAction.Heart, Data = Secret }); NatClient?.Send(pack); } } }
public void CloseLocalClient(TcpSession session) { var pack = new JsonData() { Type = (int)JsonType.TCP, Action = (int)TcpAction.Close, Data = new TcpModel() { ServerId = ServerId, Host = session.Map?.remote_endpoint, Local = session.Map?.local_endpoint, SessionId = session.SessionId }.ToJson() }; //转发给客户端 session.NatSession?.Send(PackHelper.CreatePack(pack)); }
private void Connected(TcpSession session) { try { //转发连接请求 var natSession = ServerHanlder.NATServer.GetSingle(c => c.MapList?.Any(m => m.remote_port == ServerOption.Port) ?? false); if (natSession == null) { session?.Close(); HandleLog.WriteLine($"请求:{session.Local}失败,Nat客户端连接不在线!"); return; } var map = natSession.MapList?.Find(c => c.remote_port == ServerOption.Port); if (map == null) { session?.Close(); HandleLog.WriteLine($"请求:{session.Local}失败,映射{session.Local}不存在!"); return; } session.Map = map; //tcp连接注册包 var pack = new JsonData() { Type = (int)JsonType.TCP, Action = (int)TcpAction.Connect, Data = new TcpModel() { ServerId = ServerId, Host = map?.remote_endpoint, Local = map?.local_endpoint, SessionId = session.SessionId }.ToJson() }; natSession.Send(PackHelper.CreatePack(pack)); session.NatSession = natSession; HandleLog.WriteLine($"客户端【{session.SessionId},{session.Remote}】已连接【{session.Local}】"); } catch (Exception ex) { HandleLog.WriteLine($"连接【{session.SessionId},{session.Local}】发生异常:{ex}"); } }
private void Received(HttpSession session, HttpRequestInfo requestInfo) { Task.Run(() => { try { if (!requestInfo.Success) { HandleLog.WriteLine($"http请求解析异常,ip地址:{session.Remote}"); session.Write("request parse error"); return; } var httpModel = new HttpModel { RequestTime = DateTime.Now, ServerId = ServerId, SessionId = session.SessionId }; var filter = ReceiveFilter as HttpReceiveFilter; filter.DecodePackage(ref httpModel); session.RequestInfo = requestInfo; var map = ServerHanlder.MapList.Find(c => c.remote_endpoint == httpModel.Host || (c.remote == httpModel.Host && c.remote_port == 80)); if (map == null) { HandleLog.WriteLine($"映射不存在,请求:{httpModel.Host}{httpModel.Path} {httpModel.Headers.ToJson()} {httpModel.Content.ToUTF8String()}"); //把处理信息返回到客户端 session.Write("map not found"); return; } //正向代理www.supernat.cn if (map.proxy_type == (int)proxy_type.正向代理) { ForwardProxy(session, httpModel, map); return; } //转发请求 var natSession = ServerHanlder.NATServer.GetSingle(c => c.MapList.Any(c => c.remote_endpoint == httpModel.Host || (c.remote == httpModel.Host && c.remote_port == 80))); if (natSession == null) { HandleLog.WriteLine($"穿透客户端未连接到服务器,请求地址:{httpModel.Host}{httpModel.Path}"); //把处理信息返回到客户端 session.Write("nat client not found"); } else { //压缩Body httpModel.Content = requestInfo.ContentLength > 0 ? DataHelper.Compress(requestInfo.Body) : null; //转发数据 var pack = new JsonData() { Type = (int)JsonType.HTTP, Action = (int)HttpAction.Request, Data = httpModel.ToJson() }; natSession.Send(PackHelper.CreatePack(pack)); session.NatSession = natSession; } } catch (Exception ex) { HandleLog.WriteLine($"【{session.Local}】请求地址:{requestInfo.BaseUrl}{requestInfo.Path},处理发生异常:{ex}"); //把处理信息返回到客户端 session.Write("server error"); } }); }
public static async void ProcessData(NatClient natClient, NatPackageInfo packageInfo) { try { switch (packageInfo.Body.Action) { case (byte)HttpAction.Request: { var httpModel = packageInfo.Body.Data.FromJson <HttpModel>(); var map = natClient.Client.MapList.Find(c => c.remote_endpoint == httpModel.Host || (c.remote == httpModel.Host && c.remote_port == 80)); if (map == null) { HandleLog.WriteLine($"映射不存在,外网访问地址:{httpModel.Host}"); return; } using HttpRequestMessage httpRequest = new HttpRequestMessage() { Method = new HttpMethod(httpModel.Method), RequestUri = new Uri($"{map.protocol}://{map.local_endpoint}{httpModel.Path}") }; HandleLog.WriteLine($"{map.name} {httpModel.Method} {httpRequest.RequestUri.AbsoluteUri} {httpModel.Headers.ToJson()}{Environment.NewLine}"); string bodyStr = string.Empty; if (httpRequest.Method != HttpMethod.Get && httpModel.Content?.Length > 0) { var body = DataHelper.Decompress(httpModel.Content); //解压 bodyStr = body.ToUTF8String(); httpRequest.Content = new StringContent(bodyStr, Encoding.UTF8, httpModel.ContentType.Split(";")[0]); } HandleLog.WriteLine($"{map.name} {httpModel.Method} {httpRequest.RequestUri.AbsoluteUri}{Environment.NewLine}【Header】{httpModel.Headers.ToJson()}{$"{Environment.NewLine}【Body】{bodyStr}".If(httpModel.Content?.Length < 1024)}{Environment.NewLine}"); using HttpClient _httpClient = new HttpClient(); //替换Host 不然400 Bad Request httpModel.Headers["Host"] = map.local_endpoint; foreach (var item in httpModel.Headers) { if (!item.Key.EqualsWhithNoCase("Content-Type")) { if (!httpRequest.Content?.Headers.TryAddWithoutValidation(item.Key, item.Value) ?? true) { _httpClient.DefaultRequestHeaders.TryAddWithoutValidation(item.Key, item.Value); } } } if (map.protocol == "https") { ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls; } var response = await _httpClient.SendAsync(httpRequest); //回传给服务器 httpModel.HttpVersion = $"{map.protocol.ToUpper()}/{response.Version.ToString()}"; httpModel.StatusCode = (int)response.StatusCode; httpModel.StatusMessage = response.StatusCode.ToString(); httpModel.Local = map.local_endpoint; httpModel.Headers = response.Headers.ToDictionary(); httpModel.ResponseTime = DateTime.Now; foreach (var item in response.Content.Headers) { if (item.Key.EqualsWhithNoCase("Content-Type")) { httpModel.ContentType = string.Join(";", item.Value); } else { if (item.Key.EqualsWhithNoCase("Content-Length")) { continue; } httpModel.Headers.Add(item.Key, string.Join(";", item.Value)); } } httpModel.Headers.Remove("Transfer-Encoding"); //response收到的是完整的 这个响应头要去掉 不然浏览器解析出错 var returnContent = DataHelper.StreamToBytes(response.Content.ReadAsStreamAsync().Result); if (returnContent.Length > 0) { httpModel.Content = DataHelper.Compress(returnContent); } var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.HTTP, Action = (int)HttpAction.Response, Data = httpModel.ToJson() }); natClient?.Send(pack); HandleLog.WriteLine($"{map.name} {httpModel.Method} {httpRequest.RequestUri.AbsoluteUri}{$"{returnContent.ToUTF8String()}".If(returnContent.Length < 1024)} {httpModel.StatusCode} {httpModel.StatusMessage} {Math.Round(returnContent.Length * 1.00 / 1024, 1)}KB{Environment.NewLine}"); break; } } } catch (Exception ex) { HandleLog.WriteLine($"处理请求异常:{ex}"); var pack = PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.HTTP, Action = (int)HttpAction.Response, Data = new HttpModel() { StatusCode = (int)HttpStatusCode.BadRequest, ContentType = "text/html", Content = DataHelper.Compress(Encoding.UTF8.GetBytes($"server error")) }.ToJson() }); natClient?.Send(pack); } }
public void ProcessData(NatSession session, NatRequestInfo requestInfo) { try { switch (requestInfo.Body.Action) { case (int)NatAction.Connect: { //注册包 var secret = requestInfo.Body.Data.ToString(); HandleLog.WriteLine($"收到连接{session.Remote}的注册包,密钥为:{secret},当前映射个数:{session.MapList.Count}", false); var bll = new ClientBll(); var client = bll.GetOne(secret).Data; if (client == null) { HandleLog.WriteLine($"主机【{session.Remote}】密钥不正确!!"); SendServerMessage(session, new ServerMessage() { Message = "主机密钥不正确,请确认是否填写正确!" }); return; } var checkSessions = GetList(c => c.Client?.secret == secret && c.SessionId != session.SessionId); if (checkSessions.Any()) { checkSessions.ForEach(c => { SendServerMessage(c, new ServerMessage() { Message = "该主机密钥已被其它主机使用,您已被迫下线!" }); Thread.Sleep(500); c.Close(); }); } var mapBll = new MapBll(); session.MapList = mapBll.GetMapList(secret).Data ?? new List <Map>(); client.MapList = session.MapList; session.Client = client; //原样返回回复客户端注册成功 requestInfo.Body.Data = client.ToJson(); session.Send(PackHelper.CreatePack(requestInfo.Body)); Task.Run(() => { //更新在线状态 var bll = new ClientBll(); var updateRst = bll.UpdateOnlineStatus(new Client() { secret = session.Client.secret, is_online = true, last_heart_time = DateTime.Now }); HandleLog.WriteLine($"更新主机【{session.Client.name}】在线状态结果:{updateRst.Message}", false); }); } break; case (int)NatAction.Heart: { //心跳包 var secret = requestInfo.Body.Data.ToString(); HandleLog.WriteLine($"收到连接{session.Remote}的心跳包,密钥为:{secret},当前映射个数:{session.MapList.Count}", false); Task.Run(() => { //更新在线状态 var bll = new ClientBll(); var updateRst = bll.UpdateOnlineStatus(new Client() { secret = session.Client.secret, is_online = true, last_heart_time = DateTime.Now }); HandleLog.WriteLine($"更新主机【{session.Client.name}】在线状态结果:{updateRst.Message}", false); }); } break; } } catch (Exception ex) { HandleLog.WriteLine($"穿透处理异常,{ex}"); } }
private void OnHandleContext(IAsyncResult ar) { try { //继续异步监听下一次请求 HttpListener.BeginGetContext(OnHandleContext, HttpListener); //当前请求上下文 var context = HttpListener.EndGetContext(ar); //转发请求 var natSession = NATServer.GetSingle(c => c.MapList.Any(c => c.remote_endpoint == context.Request.Url.Authority)); if (natSession == null) { //TODO 错误页面 HandleLog.WriteLine($"穿透客户端未连接到服务器,请求地址:{context.Request.Url.AbsoluteUri}"); context.Response.StatusCode = 404; var returnByteArr = Encoding.UTF8.GetBytes("nat client not found"); using var stream = context.Response.OutputStream; //把处理信息返回到客户端 stream.WriteAsync(returnByteArr, 0, returnByteArr.Length); } else { var sessionId = Guid.NewGuid().ToString(); ContextDict.Add(sessionId, context); var map = natSession.MapList.Find(c => c.remote_endpoint == context.Request.Url.Authority); var httpModel = new HttpModel() { RequestTime = DateTime.Now, ServerId = ServerId, HttpVersion = $"{map?.protocol.ToUpper()}/{context.Request.ProtocolVersion.ToString()}", Host = context.Request.Url.Authority, SessionId = sessionId, Method = context.Request.HttpMethod, Path = context.Request.RawUrl, Headers = context.Request.Headers.ToDictionary(), ContentType = context.Request.ContentType }; var byteList = new List <byte>(); int readLen = 0; int len = 0; if (context.Request.HttpMethod != "Get") { var byteArr = new byte[2048]; do { readLen = context.Request.InputStream.Read(byteArr, 0, byteArr.Length); len += readLen; byteList.AddRange(byteArr); } while (readLen != 0); var byteData = byteList.CloneRange(0, len); var req = byteData.ToUTF8String(); if (byteData.Length > 0) { //压缩请求数据 var body = DataHelper.Compress(byteData); httpModel.Content = body; } } natSession?.Send(PackHelper.CreatePack(new JsonData() { Type = (int)JsonType.HTTP, Action = (int)HttpAction.Request, Data = httpModel.ToJson() })); } } catch (Exception ex) { HandleLog.WriteLine($"HttpServer OnHandleContext穿透处理异常,{ex}"); } }