public async Task NegotiateReturnsAvailableTransports(TransportType transports) { var manager = CreateConnectionManager(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = new DefaultHttpContext(); context.Features.Set <IHttpResponseFeature>(new ResponseFeature()); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); services.AddOptions(); var ms = new MemoryStream(); context.Request.Path = "/foo"; context.Request.Method = "OPTIONS"; context.Response.Body = ms; var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions { Transports = transports }, app); var negotiateResponse = JsonConvert.DeserializeObject <JObject>(Encoding.UTF8.GetString(ms.ToArray())); var availableTransports = (TransportType)0; foreach (var transport in negotiateResponse["availableTransports"]) { availableTransports |= (TransportType)Enum.Parse(typeof(TransportType), transport.Value <string>()); } Assert.Equal(transports, availableTransports); }
public async Task SetsInherentKeepAliveFeatureOnFirstLongPollingRequest() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.LongPolling.PollTimeout = TimeSpan.FromMilliseconds(1); // We don't care about the poll itself Assert.Null(connection.Features.Get <IConnectionInherentKeepAliveFeature>()); await dispatcher.ExecuteAsync(context, options, app).OrTimeout(); Assert.NotNull(connection.Features.Get <IConnectionInherentKeepAliveFeature>()); Assert.Equal(options.LongPolling.PollTimeout, connection.Features.Get <IConnectionInherentKeepAliveFeature>().KeepAliveInterval); }
public async Task NegotiateReservesConnectionIdAndReturnsIt() { var manager = CreateConnectionManager(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = new DefaultHttpContext(); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); services.AddOptions(); var ms = new MemoryStream(); context.Request.Path = "/foo"; context.Request.Method = "OPTIONS"; context.Response.Body = ms; var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); var negotiateResponse = JsonConvert.DeserializeObject <JObject>(Encoding.UTF8.GetString(ms.ToArray())); var connectionId = negotiateResponse.Value <string>("connectionId"); Assert.True(manager.TryGetConnection(connectionId, out var connectionContext)); Assert.Equal(connectionId, connectionContext.ConnectionId); }
public async Task SynchronusExceptionEndsConnection() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); SetTransport(context, TransportType.ServerSentEvents); var services = new ServiceCollection(); services.AddEndPoint <SynchronusExceptionEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <SynchronusExceptionEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); Assert.Equal(StatusCodes.Status200OK, context.Response.StatusCode); bool exists = manager.TryGetConnection(connection.ConnectionId, out _); Assert.False(exists); }
public async Task BlockingConnectionWorksWithLongPollingConnection() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <BlockingEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <BlockingEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); var task = dispatcher.ExecuteAsync(context, options, app); var buffer = Encoding.UTF8.GetBytes("Hello World"); // Write to the application await connection.Application.Writer.WriteAsync(buffer); await task; Assert.Equal(StatusCodes.Status204NoContent, context.Response.StatusCode); bool exists = manager.TryGetConnection(connection.ConnectionId, out _); Assert.False(exists); }
public async Task ConnectionStateSetToInactiveAfterPoll() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); var task = dispatcher.ExecuteAsync(context, options, app); var buffer = Encoding.UTF8.GetBytes("Hello World"); // Write to the transport so the poll yields await connection.Transport.Writer.WriteAsync(buffer); await task; Assert.Equal(DefaultConnectionContext.ConnectionStatus.Inactive, connection.Status); Assert.Null(connection.GetHttpContext()); Assert.Equal(StatusCodes.Status200OK, context.Response.StatusCode); }
public async Task RequestToActiveConnectionIdKillsPreviousConnectionLongPolling() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context1 = MakeRequest("/foo", connection); var context2 = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); var request1 = dispatcher.ExecuteAsync(context1, options, app); var request2 = dispatcher.ExecuteAsync(context2, options, app); await request1; Assert.Equal(StatusCodes.Status204NoContent, context1.Response.StatusCode); Assert.Equal(DefaultConnectionContext.ConnectionStatus.Active, connection.Status); Assert.False(request2.IsCompleted); manager.CloseConnections(); await request2; }
public async Task RequestToDisposedConnectionIdReturns404(TransportType transportType) { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); connection.Status = DefaultConnectionContext.ConnectionStatus.Disposed; var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); SetTransport(context, transportType); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); await dispatcher.ExecuteAsync(context, options, app); Assert.Equal(StatusCodes.Status404NotFound, context.Response.StatusCode); }
public async Task WebSocketTransportTimesOutWhenCloseFrameNotReceived() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); SetTransport(context, TransportType.WebSockets); var services = new ServiceCollection(); services.AddEndPoint <ImmediatelyCompleteEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <ImmediatelyCompleteEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.WebSockets.CloseTimeout = TimeSpan.FromSeconds(1); var task = dispatcher.ExecuteAsync(context, options, app); await task.OrTimeout(); }
public async Task TransportCapabilitiesSet(TransportType transportType, TransferMode expectedTransportCapabilities) { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); SetTransport(context, transportType); var services = new ServiceCollection(); services.AddEndPoint <ImmediatelyCompleteEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <ImmediatelyCompleteEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.WebSockets.CloseTimeout = TimeSpan.FromSeconds(0); await dispatcher.ExecuteAsync(context, options, app); Assert.Equal(expectedTransportCapabilities, connection.TransportCapabilities); }
public async Task AttemptingToPollWhileAlreadyPollingReplacesTheCurrentPoll() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); var context1 = MakeRequest("/foo", connection); var task1 = dispatcher.ExecuteAsync(context1, options, app); var context2 = MakeRequest("/foo", connection); var task2 = dispatcher.ExecuteAsync(context2, options, app); // Task 1 should finish when request 2 arrives await task1.OrTimeout(); // Send a message from the app to complete Task 2 await connection.Transport.Writer.WriteAsync(Encoding.UTF8.GetBytes("Hello, World")); await task2.OrTimeout(); // Verify the results Assert.Equal(StatusCodes.Status204NoContent, context1.Response.StatusCode); Assert.Equal(string.Empty, GetContentAsString(context1.Response.Body)); Assert.Equal(StatusCodes.Status200OK, context2.Response.StatusCode); Assert.Equal("Hello, World", GetContentAsString(context2.Response.Body)); }
public MqttTcpServerListener( AddressFamily addressFamily, MqttServerTcpEndpointBaseOptions options, X509Certificate2 tlsCertificate, CancellationToken cancellationToken, IMqttNetChildLogger logger) { _cancellationToken = cancellationToken; _logger = logger; var sb = new SocketBuilder().SetSocket(Sockets.Model.SocketType.Tcp).UseStream(); if (options is MqttServerTlsTcpEndpointOptions tlsOptions) { sb = sb.WithSsl(tlsCertificate, tlsOptions.SslProtocol); } sb = sb.SetPort(options.Port); if (_addressFamily == AddressFamily.InterNetworkV6) { sb = sb.UseIPV6(); } socketOption = sb.Build(); serverSokcet = (StreamServerSocket)SocketFactory.CreateServerSocket(socketOption, cancellationToken); serverSokcet.OnAccepted += ServerSokcet_OnAccepted; }
public async Task EndpointsThatRequireConnectionId400WhenNoConnectionIdProvidedForPost() { var manager = CreateConnectionManager(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); using (var strm = new MemoryStream()) { var context = new DefaultHttpContext(); context.Response.Body = strm; var services = new ServiceCollection(); services.AddOptions(); services.AddEndPoint <TestEndPoint>(); context.Request.Path = "/foo"; context.Request.Method = "POST"; var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); Assert.Equal(StatusCodes.Status400BadRequest, context.Response.StatusCode); await strm.FlushAsync(); Assert.Equal("Connection ID required", Encoding.UTF8.GetString(strm.ToArray())); } }
public async Task PostNotAllowedForWebSocketConnections() { var manager = CreateConnectionManager(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var connection = manager.CreateConnection(); connection.Metadata[ConnectionMetadataNames.Transport] = TransportType.WebSockets; using (var strm = new MemoryStream()) { var context = new DefaultHttpContext(); context.Response.Body = strm; var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); services.AddOptions(); context.Request.Path = "/foo"; context.Request.Method = "POST"; var values = new Dictionary <string, StringValues>(); values["id"] = connection.ConnectionId; var qs = new QueryCollection(values); context.Request.Query = qs; var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); Assert.Equal(StatusCodes.Status405MethodNotAllowed, context.Response.StatusCode); await strm.FlushAsync(); Assert.Equal("POST requests are not allowed for WebSocket connections.", Encoding.UTF8.GetString(strm.ToArray())); } }
public async Task EndpointsThatAcceptConnectionId404WhenUnknownConnectionIdProvided(TransportType transportType) { var manager = CreateConnectionManager(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); using (var strm = new MemoryStream()) { var context = new DefaultHttpContext(); context.Features.Set <IHttpResponseFeature>(new ResponseFeature()); context.Response.Body = strm; var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); services.AddOptions(); context.Request.Path = "/foo"; context.Request.Method = "GET"; var values = new Dictionary <string, StringValues>(); values["id"] = "unknown"; var qs = new QueryCollection(values); context.Request.Query = qs; SetTransport(context, transportType); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); Assert.Equal(StatusCodes.Status404NotFound, context.Response.StatusCode); await strm.FlushAsync(); Assert.Equal("No Connection with that ID", Encoding.UTF8.GetString(strm.ToArray())); } }
public async Task AuthorizedConnectionWithAcceptedSchemesCanConnectToEndPoint() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = new DefaultHttpContext(); context.Features.Set <IHttpResponseFeature>(new ResponseFeature()); var services = new ServiceCollection(); services.AddOptions(); services.AddEndPoint <TestEndPoint>(); services.AddAuthorization(o => { o.AddPolicy("test", policy => { policy.RequireClaim(ClaimTypes.NameIdentifier); policy.AddAuthenticationSchemes("Default"); }); }); services.AddAuthorizationPolicyEvaluator(); services.AddLogging(); services.AddAuthenticationCore(o => { o.DefaultScheme = "Default"; o.AddScheme("Default", a => a.HandlerType = typeof(TestAuthenticationHandler)); }); var sp = services.BuildServiceProvider(); context.Request.Path = "/foo"; context.Request.Method = "GET"; context.RequestServices = sp; var values = new Dictionary <string, StringValues>(); values["id"] = connection.ConnectionId; var qs = new QueryCollection(values); context.Request.Query = qs; context.Response.Body = new MemoryStream(); var builder = new SocketBuilder(sp); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.AuthorizationData.Add(new AuthorizeAttribute("test")); // "authorize" user context.User = new ClaimsPrincipal(new ClaimsIdentity(new[] { new Claim(ClaimTypes.NameIdentifier, "name") })); var endPointTask = dispatcher.ExecuteAsync(context, options, app); await connection.Transport.Writer.WriteAsync(Encoding.UTF8.GetBytes("Hello, World")).OrTimeout(); await endPointTask.OrTimeout(); Assert.Equal(StatusCodes.Status200OK, context.Response.StatusCode); Assert.Equal("Hello, World", GetContentAsString(context.Response.Body)); }
public async Task AuthorizedConnectionWithRejectedSchemesFailsToConnectToEndPoint() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = new DefaultHttpContext(); var services = new ServiceCollection(); services.AddOptions(); services.AddEndPoint <TestEndPoint>(); services.AddAuthorization(o => { o.AddPolicy("test", policy => { policy.RequireClaim(ClaimTypes.NameIdentifier); policy.AddAuthenticationSchemes("Default"); }); }); services.AddAuthorizationPolicyEvaluator(); services.AddLogging(); services.AddAuthenticationCore(o => { o.DefaultScheme = "Default"; o.AddScheme("Default", a => a.HandlerType = typeof(RejectHandler)); }); var sp = services.BuildServiceProvider(); context.Request.Path = "/foo"; context.Request.Method = "GET"; context.RequestServices = sp; var values = new Dictionary <string, StringValues>(); values["id"] = connection.ConnectionId; var qs = new QueryCollection(values); context.Request.Query = qs; context.Response.Body = new MemoryStream(); var builder = new SocketBuilder(sp); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.AuthorizationData.Add(new AuthorizeAttribute("test")); // "authorize" user context.User = new ClaimsPrincipal(new ClaimsIdentity(new[] { new Claim(ClaimTypes.NameIdentifier, "name") })); // would block if EndPoint was executed await dispatcher.ExecuteAsync(context, options, app).OrTimeout(); Assert.Equal(StatusCodes.Status401Unauthorized, context.Response.StatusCode); }
public async Task AuthenticatedUserWithoutPermissionCausesForbidden() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = new DefaultHttpContext(); var services = new ServiceCollection(); services.AddOptions(); services.AddEndPoint <TestEndPoint>(); services.AddAuthorizationPolicyEvaluator(); services.AddAuthorization(o => { o.AddPolicy("test", policy => policy.RequireClaim(ClaimTypes.NameIdentifier)); }); services.AddAuthenticationCore(o => { o.DefaultScheme = "Default"; o.AddScheme("Default", a => a.HandlerType = typeof(TestAuthenticationHandler)); }); services.AddLogging(); var sp = services.BuildServiceProvider(); context.Request.Path = "/foo"; context.Request.Method = "GET"; context.RequestServices = sp; var values = new Dictionary <string, StringValues>(); values["id"] = connection.ConnectionId; var qs = new QueryCollection(values); context.Request.Query = qs; var builder = new SocketBuilder(sp); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.AuthorizationData.Add(new AuthorizeAttribute("test")); context.User = new ClaimsPrincipal(new ClaimsIdentity("authenticated")); // would hang if EndPoint was running await dispatcher.ExecuteAsync(context, options, app).OrTimeout(); Assert.Equal(StatusCodes.Status403Forbidden, context.Response.StatusCode); }
/// <summary> /// called on client sockets are created in connect /// </summary> public MqttTcpChannel(IMqttClientOptions clientOptions) { _clientOptions = clientOptions ?? throw new ArgumentNullException(nameof(clientOptions)); _options = (MqttClientTcpOptions)clientOptions.ChannelOptions; var builder = new SocketBuilder() .UseStream() .SetIP(_options.Server) .SetPort(_options.Port ?? 1883); if (_options.TlsOptions.UseTls) { builder = builder.WithSsl(_options.TlsOptions.SslProtocol); } var option = builder.Build(); _clientSocket = SocketFactory.CreateClientSocket(option); }
private static async Task CheckTransportSupported(TransportType supportedTransports, TransportType transportType, int status) { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); using (var strm = new MemoryStream()) { var context = new DefaultHttpContext(); context.Features.Set <IHttpResponseFeature>(new ResponseFeature()); context.Response.Body = strm; var services = new ServiceCollection(); services.AddOptions(); services.AddEndPoint <ImmediatelyCompleteEndPoint>(); SetTransport(context, transportType); context.Request.Path = "/foo"; context.Request.Method = "GET"; var values = new Dictionary <string, StringValues>(); values["id"] = connection.ConnectionId; var qs = new QueryCollection(values); context.Request.Query = qs; var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <ImmediatelyCompleteEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.Transports = supportedTransports; await dispatcher.ExecuteAsync(context, options, app); Assert.Equal(status, context.Response.StatusCode); await strm.FlushAsync(); // Check the message for 404 if (status == 404) { Assert.Equal($"{transportType} transport not supported by this end point type", Encoding.UTF8.GetString(strm.ToArray())); } } }
public async Task RequestToActiveConnectionId409ForStreamingTransports(TransportType transportType) { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context1 = MakeRequest("/foo", connection); var context2 = MakeRequest("/foo", connection); SetTransport(context1, transportType); SetTransport(context2, transportType); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); var request1 = dispatcher.ExecuteAsync(context1, options, app); await dispatcher.ExecuteAsync(context2, options, app); Assert.Equal(StatusCodes.Status409Conflict, context2.Response.StatusCode); var webSocketTask = Task.CompletedTask; var ws = (TestWebSocketConnectionFeature)context1.Features.Get <IHttpWebSocketFeature>(); if (ws != null) { await ws.Client.CloseAsync(WebSocketCloseStatus.NormalClosure, "", CancellationToken.None); } manager.CloseConnections(); await request1.OrTimeout(); }
public async Task LongPollingTimeoutSets200StatusCode() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <TestEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <TestEndPoint>(); var app = builder.Build(); var options = new HttpSocketOptions(); options.LongPolling.PollTimeout = TimeSpan.FromSeconds(2); await dispatcher.ExecuteAsync(context, options, app).OrTimeout(); Assert.Equal(StatusCodes.Status200OK, context.Response.StatusCode); }
public async Task CompletedEndPointEndsLongPollingConnection() { var manager = CreateConnectionManager(); var connection = manager.CreateConnection(); var dispatcher = new HttpConnectionDispatcher(manager, new LoggerFactory()); var context = MakeRequest("/foo", connection); var services = new ServiceCollection(); services.AddEndPoint <ImmediatelyCompleteEndPoint>(); var builder = new SocketBuilder(services.BuildServiceProvider()); builder.UseEndPoint <ImmediatelyCompleteEndPoint>(); var app = builder.Build(); await dispatcher.ExecuteAsync(context, new HttpSocketOptions(), app); Assert.Equal(StatusCodes.Status204NoContent, context.Response.StatusCode); bool exists = manager.TryGetConnection(connection.ConnectionId, out _); Assert.False(exists); }