错误状态:使用 IOWebSocketChannel 时已监听 Stream
Posted
技术标签:
【中文标题】错误状态:使用 IOWebSocketChannel 时已监听 Stream【英文标题】:Bad state: Stream has already been listened to when using IOWebSocketChannel 【发布时间】:2021-03-30 01:49:27 【问题描述】:我有一个 StreamBuilder,它监听使用包 web_socket_channel: ^1.1.0 创建的流。
Stream getLocationsStream(LatLngBounds latLngBounds, LatLng location)
if (branchMapChannel == null)
branchMapChannel = IOWebSocketChannel.connect(wsEndpointURL("business/branch/maps"));
return branchMapChannel.stream;
StreamBuilder 监听这个流(getLocationsStream())。我在名为 Maps() 的自定义小部件中使用此 Streambuilder。在主页中调用 Maps() 时,它可以正常工作。但是当 Maps() 在另一个页面上被调用时,它会显示以下错误。
错误状态:Stream 已被监听。
当异常被抛出时,这是堆栈: 我/颤振(2977):#3 _CompleterStream.listen 包:async/src/stream_completer.dart:135 我/颤振(2977):#7 _StreamBuilderBaseState._subscribe 包:flutter/…/widgets/async.dart:137 我/颤振(2977):#8 _StreamBuilderBaseState.initState 包:flutter/…/widgets/async.dart:111 我/颤振(2977):#9 StatefulElement._firstBuild 包:flutter/…/widgets/framework.dart:4812 我/颤振(2977):#10 ComponentElement.mount 包:flutter/…/widgets/framework.dart:4649 我/颤振(2977):#11 Element.inflateWidget 包:flutter/…/widgets/framework.dart:3615 我/颤振(2977):#12 Element.updateChild 包:flutter/…/widgets/framework.dart:3377 我/颤振(2977):#13 ComponentElement.performRebuild 包:flutter/…/widgets/framework.dart:4700
【问题讨论】:
【参考方案1】:出现问题是因为您尝试订阅 Single Subscription Stream
两次。
如果你查看IOWebSocketChannel的文档,你可以看到:
流 → 流 从另一个端点发出值的单订阅流。 最终
建议 #1:
而不是直接将套接字流分配给流生成器:
创建一个 Socket Utility 类(一个 Singleton 或使用依赖注入来传递对象) 在 Socket Utility 类中监听套接字事件 在您的 Socket Utility 中提供添加侦听器的选项 每当流发生变化时,通知所有监听器 在您的 Maps 类中使用 Socket Utility 对象并设置侦听器/回调建议 #2:
只需使用asBroadcastStream 将您的流转换为广播流。
Stream getLocationsStream(LatLngBounds latLngBounds, LatLng location)
if (branchMapChannel == null)
branchMapChannel = IOWebSocketChannel.connect(wsEndpointURL("business/branch/maps"));
broadCastStream = branchMapChannel.stream.asBroadcastStream();
return broadCastStream;
【讨论】:
@ChristopherMoore 是的,正在寻找文档。我总是喜欢第一种方式,所以先写了,然后添加 asBroadCastStream 作为第二个选项;) 你能分享第一个选项的代码吗?第二个选项不起作用 @AbhijithK 您是将流存储在变量中还是只是将其返回:return branchMapChannel.stream.asBroadcastStream();
?对于第一个,我已经提到了那里的步骤,如果您需要代码,我必须为您编写一个完整的类。
我尝试将其作为广播流返回,但错误仍然存在。让我试试第一个选项。
不,我的意思是如果你像这样返回它:return branchMapChannel.stream.asBroadcastStream();
错误就会出现。您必须将branchMapChannel.stream.asBroadcastStream();
的值存储在一个变量中并返回该变量。如我的回答所示,broadCastStream 是一个与 branchMapChannel 范围相同的变量以上是关于错误状态:使用 IOWebSocketChannel 时已监听 Stream的主要内容,如果未能解决你的问题,请参考以下文章