public static async Task <bool> ReceiveData(RemoteJSRuntime runtime, long streamId, long chunkId, byte[] chunk, string error) { if (!runtime.RemoteJSDataStreamInstances.TryGetValue(streamId, out var instance)) { // There is no data stream with the given identifier. It may have already been disposed. // We notify JS that the stream has been cancelled/disposed. return(false); } return(await instance.ReceiveData(chunkId, chunk, error)); }
/// <summary> /// Creates a new <see cref="RemoteRenderer"/>. /// </summary> public RemoteRenderer( IServiceProvider serviceProvider, ILoggerFactory loggerFactory, CircuitOptions options, CircuitClientProxy client, ILogger logger, RemoteJSRuntime jsRuntime, CircuitJSComponentInterop jsComponentInterop) : base(serviceProvider, loggerFactory, jsRuntime.ReadJsonSerializerOptions(), jsComponentInterop) { _client = client; _options = options; _logger = logger; ElementReferenceContext = jsRuntime.ElementReferenceContext; }
public CircuitHost( CircuitId circuitId, AsyncServiceScope scope, CircuitOptions options, CircuitClientProxy client, RemoteRenderer renderer, IReadOnlyList <ComponentDescriptor> descriptors, RemoteJSRuntime jsRuntime, RemoteNavigationManager navigationManager, CircuitHandler[] circuitHandlers, ILogger logger) { CircuitId = circuitId; if (CircuitId.Secret is null) { // Prevent the use of a 'default' secret. throw new ArgumentException($"Property '{nameof(CircuitId.Secret)}' cannot be null.", nameof(circuitId)); } _scope = scope; _options = options ?? throw new ArgumentNullException(nameof(options)); Client = client ?? throw new ArgumentNullException(nameof(client)); Renderer = renderer ?? throw new ArgumentNullException(nameof(renderer)); Descriptors = descriptors ?? throw new ArgumentNullException(nameof(descriptors)); JSRuntime = jsRuntime ?? throw new ArgumentNullException(nameof(jsRuntime)); _navigationManager = navigationManager ?? throw new ArgumentNullException(nameof(navigationManager)); _circuitHandlers = circuitHandlers ?? throw new ArgumentNullException(nameof(circuitHandlers)); _logger = logger ?? throw new ArgumentNullException(nameof(logger)); Services = scope.ServiceProvider; Circuit = new Circuit(this); Handle = new CircuitHandle() { CircuitHost = this, }; // An unhandled exception from the renderer is always fatal because it came from user code. Renderer.UnhandledException += ReportAndInvoke_UnhandledException; Renderer.UnhandledSynchronizationException += SynchronizationContext_UnhandledException; JSRuntime.UnhandledException += ReportAndInvoke_UnhandledException; _navigationManager.UnhandledException += ReportAndInvoke_UnhandledException; }
public static CircuitHost Create( CircuitId?circuitId = null, AsyncServiceScope?serviceScope = null, RemoteRenderer remoteRenderer = null, IReadOnlyList <ComponentDescriptor> descriptors = null, CircuitHandler[] handlers = null, CircuitClientProxy clientProxy = null) { serviceScope = serviceScope ?? new AsyncServiceScope(Mock.Of <IServiceScope>()); clientProxy = clientProxy ?? new CircuitClientProxy(Mock.Of <IClientProxy>(), Guid.NewGuid().ToString()); var jsRuntime = new RemoteJSRuntime(Options.Create(new CircuitOptions()), Options.Create(new HubOptions <ComponentHub>()), Mock.Of <ILogger <RemoteJSRuntime> >()); var navigationManager = new RemoteNavigationManager(Mock.Of <ILogger <RemoteNavigationManager> >()); var serviceProvider = new Mock <IServiceProvider>(); serviceProvider .Setup(services => services.GetService(typeof(IJSRuntime))) .Returns(jsRuntime); if (remoteRenderer == null) { remoteRenderer = new RemoteRenderer( serviceProvider.Object, NullLoggerFactory.Instance, new CircuitOptions(), clientProxy, NullLogger.Instance, jsRuntime, new CircuitJSComponentInterop(new CircuitOptions())); } handlers ??= Array.Empty <CircuitHandler>(); return(new TestCircuitHost( circuitId is null ? new CircuitId(Guid.NewGuid().ToString(), Guid.NewGuid().ToString()) : circuitId.Value, serviceScope.Value, new CircuitOptions(), clientProxy, remoteRenderer, descriptors ?? new List <ComponentDescriptor>(), jsRuntime, navigationManager, handlers, NullLogger <CircuitHost> .Instance)); }
public static async ValueTask <RemoteJSDataStream> CreateRemoteJSDataStreamAsync( RemoteJSRuntime runtime, IJSStreamReference jsStreamReference, long totalLength, long signalRMaximumIncomingBytes, TimeSpan jsInteropDefaultCallTimeout, CancellationToken cancellationToken = default) { // Enforce minimum 1 kb, maximum 50 kb, SignalR message size. // We budget 512 bytes overhead for the transfer, thus leaving at least 512 bytes for data // transfer per chunk with a 1 kb message size. // Additionally, to maintain interactivity, we put an upper limit of 50 kb on the message size. var chunkSize = signalRMaximumIncomingBytes > 1024 ? (int)Math.Min(signalRMaximumIncomingBytes, 50 * 1024) - 512 : throw new ArgumentException($"SignalR MaximumIncomingBytes must be at least 1 kb."); var streamId = runtime.RemoteJSDataStreamNextInstanceId++; var remoteJSDataStream = new RemoteJSDataStream(runtime, streamId, totalLength, chunkSize, jsInteropDefaultCallTimeout, cancellationToken); await runtime.InvokeVoidAsync("Blazor._internal.sendJSDataStream", jsStreamReference, streamId, chunkSize); return(remoteJSDataStream); }
private RemoteJSDataStream( RemoteJSRuntime runtime, long streamId, long totalLength, int chunkSize, TimeSpan jsInteropDefaultCallTimeout, CancellationToken cancellationToken) { _runtime = runtime; _streamId = streamId; _totalLength = totalLength; _chunkSize = chunkSize; _jsInteropDefaultCallTimeout = jsInteropDefaultCallTimeout; _streamCancellationToken = cancellationToken; _lastDataReceivedTime = DateTimeOffset.UtcNow; _ = ThrowOnTimeout(); _runtime.RemoteJSDataStreamInstances.Add(_streamId, this); _pipe = new Pipe(); _pipeReaderStream = _pipe.Reader.AsStream(); PipeReader = _pipe.Reader; }
private TestCircuitHost(CircuitId circuitId, AsyncServiceScope scope, CircuitOptions options, CircuitClientProxy client, RemoteRenderer renderer, IReadOnlyList <ComponentDescriptor> descriptors, RemoteJSRuntime jsRuntime, RemoteNavigationManager navigationManager, CircuitHandler[] circuitHandlers, ILogger logger) : base(circuitId, scope, options, client, renderer, descriptors, jsRuntime, navigationManager, circuitHandlers, logger) { }