doom 🐘
❔ Websockets and Async
I am just trying to use websockets to send some events from server periodically. Once close is sent from the client, I need to stop it. But how do I process client message that only occurs once in a while.
using System.Net.WebSockets;
using System.Text;
var builder = WebApplication.CreateBuilder(args);
builder.Logging.ClearProviders();
builder.Logging.AddConsole();
var app = builder.Build();
app.UseWebSockets();
app.UseDefaultFiles();
app.UseStaticFiles();
app.Use(async (context, next) =>
{
if (context.Request.Path == "/ws")
{
if (context.WebSockets.IsWebSocketRequest)
{
using var webSocket = await context.WebSockets.AcceptWebSocketAsync();
await Echo(context, webSocket);
}
else
{
context.Response.StatusCode = StatusCodes.Status400BadRequest;
}
}
else
{
await next();
}
});
async Task Echo(HttpContext context, WebSocket webSocket)
{
var buffer = new byte[1024 * 4];
var receiveResult = await webSocket.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
var message = Encoding.UTF8.GetBytes("Hello from server");
Task.Run(async () =>
{
receiveResult = await webSocket.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
app.Logger.LogInformation("Received: " + receiveResult.CloseStatusDescription);
});
while (!receiveResult.CloseStatus.HasValue)
{
await webSocket.SendAsync(new ArraySegment<byte>(message, 0, message.Length), WebSocketMessageType.Text, true, CancellationToken.None);
await Task.Delay(1000);
if (Encoding.UTF8.GetString(buffer).Contains("close"))
{
await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, receiveResult.CloseStatusDescription, CancellationToken.None);
return;
}
}
app.Logger.LogInformation("Closing connection");
};
app.Run();
using System.Net.WebSockets;
using System.Text;
var builder = WebApplication.CreateBuilder(args);
builder.Logging.ClearProviders();
builder.Logging.AddConsole();
var app = builder.Build();
app.UseWebSockets();
app.UseDefaultFiles();
app.UseStaticFiles();
app.Use(async (context, next) =>
{
if (context.Request.Path == "/ws")
{
if (context.WebSockets.IsWebSocketRequest)
{
using var webSocket = await context.WebSockets.AcceptWebSocketAsync();
await Echo(context, webSocket);
}
else
{
context.Response.StatusCode = StatusCodes.Status400BadRequest;
}
}
else
{
await next();
}
});
async Task Echo(HttpContext context, WebSocket webSocket)
{
var buffer = new byte[1024 * 4];
var receiveResult = await webSocket.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
var message = Encoding.UTF8.GetBytes("Hello from server");
Task.Run(async () =>
{
receiveResult = await webSocket.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
app.Logger.LogInformation("Received: " + receiveResult.CloseStatusDescription);
});
while (!receiveResult.CloseStatus.HasValue)
{
await webSocket.SendAsync(new ArraySegment<byte>(message, 0, message.Length), WebSocketMessageType.Text, true, CancellationToken.None);
await Task.Delay(1000);
if (Encoding.UTF8.GetString(buffer).Contains("close"))
{
await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, receiveResult.CloseStatusDescription, CancellationToken.None);
return;
}
}
app.Logger.LogInformation("Closing connection");
};
app.Run();
4 replies