CavemanTcp le brinda el máximo control en la creación de aplicaciones basadas en TCP que involucran clientes y servidores.
Con CavemanTcp, tienes control total sobre la lectura y escritura de datos. CavemanTcp está diseñado para aquellos que desean un control explícito sobre cuándo se leen o escriben los datos o desean construir una máquina de estado sobre TCP.
Importante:
Dado que CavemanTcp depende de la aplicación consumidora para especificar cuándo leer o escribir, no hay subprocesos en segundo plano que monitoreen continuamente el estado de la conexión TCP (a diferencia de SimpleTcp y WatsonTcp). Por lo tanto, debe crear sus aplicaciones con la expectativa de que se pueda generar una excepción mientras se encuentra en medio de una lectura o escritura.
A partir de la versión 1.3.0, se agregó compatibilidad con TCP keepalive para .NET Core y .NET Framework; desafortunadamente, .NET Standard no ofrece este soporte, por lo que no está presente para aplicaciones que usan CavemanTcp dirigidas a .NET Standard.
Guid
en lugar de string ipPort
ListClients
ahora devuelve una enumeración de ClientMetadata
Send
y Read
que utilizan string ipPort
están marcados como obsoletosAddClient
se acercó a la aceptación de la conexiónnet461
net472
net48
net6.0
net7.0
y net8.0
using CavemanTcp ;
// Instantiate
TcpServer server = new TcpServer ( "127.0.0.1" , 8000 , false , null , null ) ;
server . Logger = Logger ;
// Set callbacks
server . Events . ClientConnected += ( s , e ) =>
{
Console . WriteLine ( "Client " + e . Client . ToString ( ) + " connected to server" ) ;
} ;
server . Events . ClientDisconnected += ( s , e ) =>
{
Console . WriteLine ( "Client " + e . Client . ToString ( ) + " disconnected from server" ) ;
} ;
// Start server
server . Start ( ) ;
// Send [Data] to client at [guid]
Guid guid = Guid . Parse ( "00001111-2222-3333-4444-555566667777" ) ;
WriteResult wr = null ;
wr = server . Send ( guid , "[Data]" ) ;
wr = server . SendWithTimeout ( [ ms ] , guid , "[Data]" ) ;
wr = await server . SendAsync ( guid , "[Data]" ) ;
wr = await server . SendWithTimeoutAsync ( [ ms ] , guid , "[Data]" ) ;
// Receive [count] bytes of data from client at [guid]
ReadResult rr = null ;
rr = server . Read ( guid , [ count ] ) ;
rr = server . ReadWithTimeout ( [ ms ] , guid , count ) ;
rr = await server . ReadAsync ( guid , [ count ] ) ;
rr = await server . ReadWithTimeoutAsync ( [ ms ] , guid , [ count ] ) ;
// List clients
List < ClientMetadata > clients = server . GetClients ( ) . ToList ( ) ;
// Disconnect a client
server . DisconnectClient ( guid ) ;
using CavemanTcp ;
// Instantiate
TcpClient client = new TcpClient ( "127.0.0.1" , 8000 , false , null , null ) ;
client . Logger = Logger ;
// Set callbacks
client . Events . ClientConnected += ( s , e ) =>
{
Console . WriteLine ( "Connected to server" ) ;
} ;
client . Events . ClientDisconnected += ( s , e ) =>
{
Console . WriteLine ( "Disconnected from server" ) ;
} ;
// Connect to server
client . Connect ( 10 ) ;
// Send data to server
WriteResult wr = null ;
wr = client . Send ( "[Data]" ) ;
wr = client . SendWithTimeout ( [ ms ] , "[Data]" ) ;
wr = await client . SendAsync ( "[Data]" ) ;
wr = await client . SendWithTimeoutAsync ( [ ms ] , "[Data]" ) ;
// Read [count] bytes of data from server
ReadResult rr = null ;
rr = client . Read ( [ count ] ) ;
rr = client . ReadWithTimeout ( [ ms ] , count ) ;
rr = await client . ReadAsync ( [ count ] ) ;
rr = await client . ReadWithTimeoutAsync ( [ ms ] , [ count ] ) ;
WriteResult
y ReadResult
contienen una propiedad Status
que indica una de las siguientes opciones:
ClientNotFound
: solo aplicable para operaciones de lectura y escritura del servidorSuccess
: la operación fue exitosaTimeout
: la operación expiró (reservada para uso futuro)Disconnected
: el par desconectado WriteResult
también incluye:
BytesWritten
: el número de bytes escritos en el socket. ReadResult
también incluye:
BytesRead
: el número de bytes leídos del socket.DataStream
: un MemoryStream
que contiene los datos solicitados.Data
: una representación de byte[]
de DataStream
. El uso de esta propiedad leerá completamente DataStream
hasta el final. IMPORTANTE
127.0.0.1
como dirección IP del oyente, solo podrá aceptar conexiones desde el host local.null
, *
, +
o 0.0.0.0
para la dirección IP del oyente (requiere privilegios de administrador para escuchar en cualquier dirección IP) Cuando se utiliza cualquiera de las API que le permiten especificar un tiempo de espera (es decir, SendWithTimeout
, SendWithTimeoutAsync
, ReadWithTimeout
y ReadWithTimeoutAsync
), el WriteResult
y ReadResult
resultantes, como se mencionó anteriormente, indicarán si se agotó el tiempo de espera de la operación.
Es importante comprender qué indica un tiempo de espera y, más importante aún, qué no indica.
NetworkStream
o SslStream
subyacente.NetworkStream
o SslStream
subyacente en la cantidad asignada de milisegundos.timeoutMs
son -1
o cualquier número entero positivo. -1
indica que no hay tiempo de espera y es lo mismo que usar una API que no especifica un tiempo de esperaBytesRead
o BytesWritten
(si estaba leyendo o escribiendo) en caso de que se agote el tiempo de espera. Es posible que el tiempo de espera se haya producido a mitad de la operación y, por lo tanto, será importante recuperarse del fallo.ReadWithTimeout
con un tiempo de espera de 10 segundos, intentando leer 50.000 bytes.ReadResult
con Status == ReadResultStatus.Timeout
y la propiedad BytesRead
se establece en 30.000NetworkStream
o SslStream
subyacente del cliente.A partir de la versión 1.3.0, se agregó compatibilidad con TCP keepalive a CavemanTcp, principalmente para solucionar el problema de que se cierre una interfaz de red, se desconecte el cable o los medios dejen de estar disponibles. Es importante tener en cuenta que los keepalives son compatibles con .NET Core y .NET Framework, pero NO con .NET Standard. A partir de esta versión, .NET Standard no proporciona funciones para el mantenimiento de TCP.
Los keepalive de TCP están habilitados de forma predeterminada.
server . Keepalive . EnableTcpKeepAlives = true ;
server . Keepalive . TcpKeepAliveInterval = 5 ; // seconds to wait before sending subsequent keepalive
server . Keepalive . TcpKeepAliveTime = 5 ; // seconds to wait before sending a keepalive
server . Keepalive . TcpKeepAliveRetryCount = 5 ; // number of failed keepalive probes before terminating connection
Algunas notas importantes sobre los keepalives de TCP:
Keepalive.TcpKeepAliveRetryCount
solo se aplica a .NET Core; para .NET Framework, este valor se fuerza a 10 ¡Un agradecimiento especial a aquellos que han ayudado a mejorar la biblioteca hasta ahora!
@LeaT113 @Kliodna @zzampong @SaintedPsycho @samisil @eatyouroats @CetinOzdil @akselatom @wtarr
¿Necesita ayuda o tiene comentarios? ¡Por favor presente un problema aquí!
Consulte CHANGELOG.md.
Un agradecimiento especial a VektorPicker por el ícono gratuito de Caveman: http://www.vectorpicker.com/caveman-icon_490587_47.html