Commit 5faaa0b2 authored by justcoding121's avatar justcoding121

#184 add connection count; TODO: Find out why large number of client connections are active

parent 4047a006
......@@ -106,6 +106,7 @@ namespace Titanium.Web.Proxy.Examples.Basic
//intecept & cancel redirect or update requests
public async Task OnRequest(object sender, SessionEventArgs e)
{
Console.WriteLine("Active Connections:" + (sender as ProxyServer).ClientConnectionCount);
Console.WriteLine(e.WebSession.Request.Url);
//read request headers
......
......@@ -55,10 +55,11 @@ namespace Titanium.Web.Proxy.Network.Tcp
{
Stream?.Close();
Stream?.Dispose();
StreamReader?.Dispose();
TcpClient.LingerState = new LingerOption(true, 0);
TcpClient.Close();
TcpClient?.Close();
}
}
}
......@@ -133,10 +133,6 @@ namespace Titanium.Web.Proxy.Network.Tcp
client.ReceiveTimeout = connectionTimeOutSeconds * 1000;
client.SendTimeout = connectionTimeOutSeconds * 1000;
stream.ReadTimeout = connectionTimeOutSeconds * 1000;
stream.WriteTimeout = connectionTimeOutSeconds * 1000;
return new TcpConnection
{
UpStreamHttpProxy = externalHttpProxy,
......
......@@ -226,6 +226,8 @@ namespace Titanium.Web.Proxy
public SslProtocols SupportedSslProtocols { get; set; } = SslProtocols.Tls
| SslProtocols.Tls11 | SslProtocols.Tls12 | SslProtocols.Ssl3;
public int ClientConnectionCount { get; private set; }
/// <summary>
/// Constructor
/// </summary>
......@@ -495,7 +497,7 @@ namespace Titanium.Web.Proxy
endPoint.Listener = new TcpListener(endPoint.IpAddress, endPoint.Port);
endPoint.Listener.Start();
endPoint.Port = ((IPEndPoint) endPoint.Listener.LocalEndpoint).Port;
endPoint.Port = ((IPEndPoint)endPoint.Listener.LocalEndpoint).Port;
// accept clients asynchronously
endPoint.Listener.BeginAcceptTcpClient(OnAcceptConnection, endPoint);
}
......@@ -560,7 +562,7 @@ namespace Titanium.Web.Proxy
/// <param name="asyn"></param>
private void OnAcceptConnection(IAsyncResult asyn)
{
var endPoint = (ProxyEndPoint) asyn.AsyncState;
var endPoint = (ProxyEndPoint)asyn.AsyncState;
TcpClient tcpClient = null;
......@@ -586,6 +588,8 @@ namespace Titanium.Web.Proxy
{
Task.Run(async () =>
{
ClientConnectionCount++;
try
{
if (endPoint.GetType() == typeof(TransparentProxyEndPoint))
......@@ -599,15 +603,14 @@ namespace Titanium.Web.Proxy
}
finally
{
if (tcpClient != null)
{
//This line is important!
//contributors please don't remove it without discussion
//It helps to avoid eventual deterioration of performance due to TCP port exhaustion
//due to default TCP CLOSE_WAIT timeout for 4 minutes
tcpClient.LingerState = new LingerOption(true, 0);
tcpClient.Close();
}
//This line is important!
//contributors please don't remove it without discussion
//It helps to avoid eventual deterioration of performance due to TCP port exhaustion
//due to default TCP CLOSE_WAIT timeout for 4 minutes
tcpClient.LingerState = new LingerOption(true, 0);
tcpClient?.Close();
ClientConnectionCount--;
}
});
}
......
This diff is collapsed.
......@@ -9,6 +9,8 @@ using Titanium.Web.Proxy.Exceptions;
using Titanium.Web.Proxy.Extensions;
using Titanium.Web.Proxy.Http;
using Titanium.Web.Proxy.Helpers;
using System.Net.Sockets;
using Titanium.Web.Proxy.Network.Tcp;
namespace Titanium.Web.Proxy
{
......@@ -21,14 +23,14 @@ namespace Titanium.Web.Proxy
/// Called asynchronously when a request was successfully and we received the response
/// </summary>
/// <param name="args"></param>
/// <returns></returns>
private async Task HandleHttpSessionResponse(SessionEventArgs args)
/// <returns>true if no errors</returns>
private async Task<bool> HandleHttpSessionResponse(SessionEventArgs args)
{
//read response & headers from server
await args.WebSession.ReceiveResponse();
try
{
//read response & headers from server
await args.WebSession.ReceiveResponse();
if (!args.WebSession.Response.ResponseBodyRead)
{
args.WebSession.Response.ResponseStream = args.WebSession.ServerConnection.Stream;
......@@ -44,7 +46,7 @@ namespace Titanium.Web.Proxy
for (int i = 0; i < invocationList.Length; i++)
{
handlerTasks[i] = ((Func<object, SessionEventArgs, Task>) invocationList[i])(this, args);
handlerTasks[i] = ((Func<object, SessionEventArgs, Task>)invocationList[i])(this, args);
}
await Task.WhenAll(handlerTasks);
......@@ -53,7 +55,7 @@ namespace Titanium.Web.Proxy
if (args.ReRequest)
{
await HandleHttpSessionRequestInternal(null, args, null, null, true);
return;
return true;
}
args.WebSession.Response.ResponseLocked = true;
......@@ -125,14 +127,16 @@ namespace Titanium.Web.Proxy
}
catch (Exception e)
{
ExceptionFunc(new ProxyHttpException("Error occured wilst handling session response", e, args));
ExceptionFunc(new ProxyHttpException("Error occured whilst handling session response", e, args));
Dispose(args.ProxyClient.ClientStream, args.ProxyClient.ClientStreamReader,
args.ProxyClient.ClientStreamWriter, args);
}
finally
{
args.Dispose();
args.ProxyClient.ClientStreamWriter, args.WebSession.ServerConnection);
return false;
}
args.Dispose();
return true;
}
/// <summary>
......@@ -219,24 +223,24 @@ namespace Titanium.Web.Proxy
}
/// <summary>
/// Handle dispose of a client/server session
/// Handle dispose of a client/server session
/// </summary>
/// <param name="clientStream"></param>
/// <param name="clientStreamReader"></param>
/// <param name="clientStreamWriter"></param>
/// <param name="args"></param>
private void Dispose(Stream clientStream, CustomBinaryReader clientStreamReader,
StreamWriter clientStreamWriter, IDisposable args)
/// <param name="serverConnection"></param>
private void Dispose(Stream clientStream,
CustomBinaryReader clientStreamReader,
StreamWriter clientStreamWriter,
TcpConnection serverConnection)
{
clientStream?.Close();
clientStream?.Dispose();
clientStreamReader?.Dispose();
clientStreamWriter?.Close();
clientStreamWriter?.Dispose();
args?.Dispose();
serverConnection?.Dispose();
}
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment