static Task?BeginSendRemainderInBackground(PooledMultiplexer @this, RespConnection connection, List <IBatchedOperation> values, CancellationToken cancellationToken) { return(connection.PreferSync ? Task.Run(() => { var len = values.Count; try { for (int i = 1; i < len; i++) { Send(@this, connection, values[i], flush: i == len - 1); } } catch (Exception ex) { connection.Doom(); Debug.WriteLine(ex.Message); } }) : Task.Run(async() => { var len = values.Count; try { for (int i = 1; i < len; i++) { await SendAsync(@this, connection, values[i], cancellationToken, flush: i == len - 1).ConfigureAwait(false); } } catch (Exception ex) { connection.Doom(); Debug.WriteLine(ex.Message); } })); }
static void Ping(RespConnection connection) => connection.Call(s_ping, resp => { resp.ThrowIfError(); if (!resp.Equals(s_pong)) { Throw(); } });
static Task PingAsync(RespConnection connection) => connection.CallAsync(s_ping, resp => { resp.ThrowIfError(); if (!resp.Equals(s_pong)) { Throw(); } }).AsTask();
private ValueTask <RespConnection> ConnectAsync(CancellationToken cancellationToken) { int index = Interlocked.Increment(ref _nextConnectionIndex); var name = $"connection " + index; var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(Configuration.EndPoints.Single()); return(HandshakeAsync(RespConnection.Create(new NetworkStream(socket), name), cancellationToken)); }
internal void Call(RespConnection connection, Lifetime <Memory <RespValue> > args, Action <RespValue>?inspector = null) { using (args) { Interlocked.Increment(ref _opCount); connection.Send(RespValue.CreateAggregate(RespType.Array, args.Value)); } using var response = connection.Receive(); response.Value.ThrowIfError(); inspector?.Invoke(response.Value); }
static RespConnection CreateClient(bool asNetworkStream) { var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(ServerEndpoint); var connection = asNetworkStream ? RespConnection.Create(new NetworkStream(socket)) : RespConnection.Create(socket); // connection.Ping(); return(connection); }
internal T Call <T>(RespConnection connection, Lifetime <Memory <RespValue> > args, Func <RespValue, T> selector) { using (args) { Interlocked.Increment(ref _opCount); connection.Send(RespValue.CreateAggregate(RespType.Array, args.Value)); } using var response = connection.Receive(); response.Value.ThrowIfError(); return(selector(response.Value)); }
static RespConnection[] CreateClients(int count, bool asNetworkStream) { var clients = new RespConnection[count]; for (int i = 0; i < clients.Length; i++) { var connection = CreateClient(asNetworkStream); clients[i] = connection; } return(clients); }
public async Task Teardown() { _seredis?.Dispose(); _ssredis?.Dispose(); if (_respite != null) { await _respite.DisposeAsync(); } _seredis_server = null; _seredis_db = null; _seredis = null; _ssredis = null; _respite = null; _ssAsync = null; }
static RespConnection[] CreateClients(int count, bool asNetworkStream) { var clients = new RespConnection[count]; for (int i = 0; i < clients.Length; i++) { var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(ServerEndpoint); var connection = asNetworkStream ? RespConnection.Create(new NetworkStream(socket)) : RespConnection.Create(socket); // connection.Ping(); clients[i] = connection; } return(clients); }
internal async Task Setup(bool minimal) { _ssredis = RedisClient.New(); _ssAsync = _ssredis; if (!minimal) { _seredis = await ConnectionMultiplexer.ConnectAsync("127.0.0.1:6379"); _seredis_server = _seredis.GetServer(_seredis.GetEndPoints().Single()); _seredis_db = _seredis.GetDatabase(); var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect("127.0.0.1", 6379); _respite = RespConnection.Create(socket); } }
internal async Task CallAsync(RespConnection connection, List <IBatchedOperation> operations, CancellationToken cancellationToken) { try { int len = operations.Count; if (len == 0) { return; } // push the fisrt *before* we context-switch; the rest can wait await SendAsync(this, connection, operations[0], cancellationToken, true).ConfigureAwait(false); Task?bgSend = len == 1 ? null : BeginSendRemainderInBackground(this, connection, operations, default); foreach (var op in operations) // then receive all { using var response = await connection.ReceiveAsync().ConfigureAwait(false); try { response.Value.ThrowIfError(); op.ProcessResponse(response.Value); } catch (Exception ex) { op.TrySetException(ex); } } if (bgSend != null) { Wait(bgSend); } } catch (Exception ex) { connection.Doom(); foreach (var op in operations) // fault anything that is left after a global explosion { op.TrySetException(ex); } } }
#pragma warning disable IDE0051 // Remove unused private members static async ValueTask BasicTest() #pragma warning restore IDE0051 // Remove unused private members { var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(ServerEndpoint); await using var client = RespConnection.Create(socket); var payload = new string('a', 2048); var frame = RespValue.CreateAggregate(RespType.Array, "ping", payload); var timer = Stopwatch.StartNew(); for (int i = 0; i < 1000; i++) { client.Send(frame); using var reply = client.Receive(); reply.Value.ThrowIfError(); // client.Ping(); } timer.Stop(); Log("sync", timer.Elapsed, 1000, payload); }
public async Task ConnectAsync() { var endpoint = new IPEndPoint(IPAddress.Loopback, 6379); _muxer = await ConnectionMultiplexer.ConnectAsync(new ConfigurationOptions { EndPoints = { endpoint } }); _server = _muxer.GetServer(endpoint); SERedis(); await SERedisAsync(); var serviceProvider = new ServiceCollection().BuildServiceProvider(); var client = new ClientBuilder(serviceProvider) .UseSockets() .Build(); _connection = await client.ConnectAsync(endpoint); _bedrock = new RespBedrockProtocol(_connection); Bedrock(); await BedrockAsync(); var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(endpoint); _socket = RespConnection.Create(socket); Socket(); await SocketAsync(); socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); SocketConnection.SetRecommendedClientOptions(socket); socket.Connect(endpoint); _stream = RespConnection.Create(new NetworkStream(socket)); Stream(); await StreamAsync(); }
static async Task RunClientAsync(RespConnection client, int pingsPerClient, int pipelineDepth, string payload) { var frame = string.IsNullOrEmpty(payload) ? s_ping : RespValue.CreateAggregate(RespType.Array, "PING", payload); var expected = string.IsNullOrEmpty(payload) ? s_pong : RespValue.Create(RespType.BlobString, payload); if (pipelineDepth == 1) { for (int i = 0; i < pingsPerClient; i++) { await client.SendAsync(frame).ConfigureAwait(false); using var result = await client.ReceiveAsync().ConfigureAwait(false); result.Value.ThrowIfError(); if (!result.Value.Equals(expected)) { Throw(); } // await client.PingAsync(); } } else { using var frames = Replicate(frame, pipelineDepth); for (int i = 0; i < pingsPerClient; i++) { using var batch = await client.BatchAsync(frames.Value).ConfigureAwait(false); CheckBatchForErrors(batch.Value, expected); } } }
static void Send(PooledMultiplexer @this, RespConnection connection, IBatchedOperation op, bool flush) { Interlocked.Increment(ref @this._opCount); using var args = op.ConsumeArgs(); connection.Send(RespValue.CreateAggregate(RespType.Array, args.Value), flush); }
private static async PooledValueTask SendAsync(PooledMultiplexer @this, RespConnection connection, IBatchedOperation op, CancellationToken cancellationToken, bool flush) { Interlocked.Increment(ref @this._opCount); using var args = op.ConsumeArgs(); await connection.SendAsync(RespValue.CreateAggregate(RespType.Array, args.Value), cancellationToken, flush).ConfigureAwait(false); }
private ValueTask <RespConnection> HandshakeAsync(RespConnection connection, CancellationToken cancellationToken) => new ValueTask <RespConnection>(connection);
public RedisConnection(RespConnection connection) => _connection = connection;