Version 1.11.2
Cherry-pick 735e5a3eb4a5028eac3399679b3dcd51360d97c6 to stable
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 9e2340d..cfe595a 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## 1.11.2
+
+### Core library changes
+
+* Fix a bug where `WebSocket.close()` would crash if called after
+ `WebSocket.cancel()`.
+
## 1.11.1
### Tool changes
diff --git a/sdk/lib/io/websocket_impl.dart b/sdk/lib/io/websocket_impl.dart
index 2657606..9693873 100644
--- a/sdk/lib/io/websocket_impl.dart
+++ b/sdk/lib/io/websocket_impl.dart
@@ -903,6 +903,10 @@
_subscription.pause();
_controller = new StreamController(sync: true,
onListen: _subscription.resume,
+ onCancel: () {
+ _subscription.cancel();
+ _subscription = null;
+ },
onPause: _subscription.pause,
onResume: _subscription.resume);
@@ -965,7 +969,7 @@
// processed if received.
// 2) set a timer terminate the connection if a close frame is
// not received.
- if (!_controller.hasListener) {
+ if (!_controller.hasListener && _subscription != null) {
_controller.stream.drain().catchError((_) => {});
}
if (_closeTimer == null) {
@@ -974,7 +978,7 @@
// Reuse code and reason from the local close.
_closeCode = _outCloseCode;
_closeReason = _outCloseReason;
- _subscription.cancel();
+ if (_subscription != null) _subscription.cancel();
_controller.close();
_webSockets.remove(_serviceId);
});
diff --git a/tests/standalone/io/web_socket_test.dart b/tests/standalone/io/web_socket_test.dart
index f3213e6..9ae1758 100644
--- a/tests/standalone/io/web_socket_test.dart
+++ b/tests/standalone/io/web_socket_test.dart
@@ -187,6 +187,36 @@
}
+ void testCancelThenClose() {
+ createServer().then((server) {
+ server.transform(new WebSocketTransformer()).listen((webSocket) {
+ webSocket.listen(null).cancel();
+ webSocket.close();
+ server.close();
+ });
+
+ createClient(server.port).then((webSocket) {
+ webSocket.close();
+ });
+ });
+ }
+
+ void testCloseThenCancel() {
+ createServer().then((server) {
+ server.transform(new WebSocketTransformer()).listen((webSocket) {
+ var subscription = webSocket.listen(null);
+ webSocket.close();
+ subscription.cancel();
+ server.close();
+ });
+
+ createClient(server.port).then((webSocket) {
+ webSocket.close();
+ });
+ });
+ }
+
+
void testListenAfterClose() {
createServer().then((server) {
server.transform(new WebSocketTransformer()).listen((webSocket) {
@@ -543,6 +573,8 @@
testMessageLength(65535);
testMessageLength(65536);
testCloseNoListen();
+ testCancelThenClose();
+ testCloseThenCancel();
testListenAfterClose();
testDoubleCloseClient();
testDoubleCloseServer();
diff --git a/tools/VERSION b/tools/VERSION
index 098b2ed..8a1172e 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -26,6 +26,6 @@
CHANNEL stable
MAJOR 1
MINOR 11
-PATCH 1
+PATCH 2
PRERELEASE 0
PRERELEASE_PATCH 0