【问题标题】:SignalR: Cancellation in Case of Client to Server Streaming makes code buggy in case of dotnet clientSignalR:在客户端到服务器流式传输的情况下取消会使代码在 dotnet 客户端的情况下出现错误
【发布时间】:2021-12-14 21:31:05
【问题描述】:

我尝试通过向服务器集线器上的方法发送调用,将流从客户端发送到服务器,从 dotnet 客户端到另一个 dotnet 服务器,如下所示:

// Method on Server Hub which should read the stream
public async Task UploadChannelReader(ChannelReader<string> stream, CancellationToken cancellationToken)
        {
            while (await stream.WaitToReadAsync(cancellationToken))
            {
                var item = await stream.ReadAsync(cancellationToken);
                Console.WriteLine(item);
            }
        }

我在 dotnet 客户端上的实现如下:

    // My method on dotnet client which used to invoke method on server

public async Task SendChannelStream(CounterInput counter, CancellationToken cancellationToken)
        {

            if (_hubConnection.State == HubConnectionState.Disconnected)
            {
                await _hubConnection.StartAsync();
            }
                var channel = Channel.CreateBounded<string>(10);
                await _hubConnection.SendAsync(ServerChatEvents.UploadChannelReader, channel.Reader, cancellationToken);
                await writeToChannel(channel.Writer, counter, cancellationToken);
        }

        private async Task writeToChannel(ChannelWriter<string> writer, CounterInput counter, CancellationToken cancellationToken)
        {
            Exception writeException = null;
            try
            {
                    await writer.WriteAsync("This is the first item sent from client to server", cancellationToken);
                    await writer.WriteAsync("This is the second item sent from client to server which can be received immidiately", cancellationToken);
                    await Task.Delay(counter.Delay, cancellationToken);
                    await writer.WriteAsync("This is the third item sent from client to server after a delay", cancellationToken);
                    await writer.WriteAsync("After this item we complete the writer and so the reader should mark completed!", cancellationToken);
                
            }
            catch (System.Exception ex)
            {
                writeException = ex;
                Console.WriteLine(ex.Message);
            }
            finally
            {
                writer.Complete(writeException);
            }
        }

其中_hubConnection 是到服务器集线器的 HubConnection。

代码不起作用,我不确定它是否在 dotnet 客户端或 dotnet 集线器服务器中取消。 但是在从服务器集线器方法签名中删除 cancellationToken 之后,它就可以工作了。 我认为这是正确的行为,因为从客户端取消等于不再发送流,由于通道读取器/写入器或 IAsyncEnumerable 的异步性质,服务器代码会自动捕获该流。但是从调试的角度来看,我真的很难找到它(花了一整天)。 我的问题是 1-为什么在集线器方法签名中使用取消令牌时,它不起作用(似乎它在调用方法后立即取消)和 2-取消发生在哪里?在 dotnet 客户端还是在集线器中?

提前致谢

【问题讨论】:

  • 你有没有按照教程来实现这个功能?
  • @TinyWang 不是。在相反的情况下,从服务器到客户端的流式传输,以类似的方式将取消令牌馈送到方法,并且由于它们都是异步的,我只是认为它应该以类似的方式实现。由于我做了几乎一天的尝试和错误来修复它,我只想分享它。甚至可能是微软故意的。

标签: asp.net-core websocket asp.net-core-signalr cancellation cancellation-token


【解决方案1】:

相关 SignalR issue 说它是 WIP。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-05-10
    • 2011-02-15
    • 1970-01-01
    相关资源
    最近更新 更多