WebSocketが実際に閉じられることはないため、デリゲートが呼び出されることはないことがわかりました。SRWebSocketのWebSocketのクローズは、メソッドpumpWritingで次のように行われます。
if (_closeWhenFinishedWriting &&
_outputBuffer.length - _outputBufferOffset == 0 &&
(_inputStream.streamStatus != NSStreamStatusNotOpen &&
_inputStream.streamStatus != NSStreamStatusClosed) &&
!_sentClose) {
_sentClose = YES;
[_outputStream close];
[_inputStream close];
if (!_failed) {
dispatch_async(_callbackQueue, ^{
if ([self.delegate respondsToSelector:@selector(webSocket:didCloseWithCode:reason:wasClean:)]) {
[self.delegate webSocket:self didCloseWithCode:_closeCode reason:_closeReason wasClean:YES];
}
});
}
_selfRetain = nil;
NSLog(@" Is really closed and released ");
}
else {
NSLog(@" Is NOT closed and released ");
}
すべてのストリームとWebSocketを保持するオブジェクトは、そこで閉じられるか削除されます。それらがまだ開いている限り、ソケットは適切に閉じられません。しかし、WebSocketを閉じようとしたときに、_closeWhenFinishedWritingが常にNOであったため、プログラムで閉じが発生することはありませんでした。
このブール値は、disconnectメソッドで1回だけ設定されます。
- (void)_disconnect;
{
assert(dispatch_get_current_queue() == _workQueue);
SRFastLog(@"Trying to disconnect");
_closeWhenFinishedWriting = YES;
[self _pumpWriting];
}
ただし、 SRWebSocketでcloseWithCodeメソッドを呼び出す場合、disconnectが呼び出されるのは1つの場合、つまりWebSocketが接続状態の場合のみです。
BOOL wasConnecting = self.readyState == SR_CONNECTING;
SRFastLog(@"Closing with code %d reason %@", code, reason);
dispatch_async(_workQueue, ^{
if (wasConnecting) {
[self _disconnect];
return;
}
つまり、ソケットが別の状態にある場合、WebSocketが実際に閉じることはありません。回避策の1つは、常に切断メソッドを呼び出すことです。少なくともそれは私にとってはうまくいき、すべてが大丈夫のようです。
SRWebSocketがそのように実装されている理由を誰かが知っている場合は、この回答にコメントを残して、私を助けてください。