@@ -665,11 +665,11 @@ internal struct TaskCancelEvent {}
665
665
internal class TaskHandler < Delegate: HTTPClientResponseDelegate > : RemovableChannelHandler {
666
666
enum State {
667
667
case idle
668
- case bodySent
669
- case sent
670
- case head
668
+ case sendingBodyWaitingResponseHead
669
+ case sendingBodyResponseHeadReceived
670
+ case bodySentWaitingResponseHead
671
+ case bodySentResponseHeadReceived
671
672
case redirected( HTTPResponseHead , URL )
672
- case body
673
673
case endOrError
674
674
}
675
675
@@ -794,7 +794,8 @@ extension TaskHandler: ChannelDuplexHandler {
794
794
typealias OutboundOut = HTTPClientRequestPart
795
795
796
796
func write( context: ChannelHandlerContext , data: NIOAny , promise: EventLoopPromise < Void > ? ) {
797
- self . state = . idle
797
+ self . state = . sendingBodyWaitingResponseHead
798
+
798
799
let request = self . unwrapOutboundIn ( data)
799
800
800
801
var head = HTTPRequestHead ( version: HTTPVersion ( major: 1 , minor: 1 ) ,
@@ -840,23 +841,32 @@ extension TaskHandler: ChannelDuplexHandler {
840
841
self . writeBody ( request: request, context: context)
841
842
} . flatMap {
842
843
context. eventLoop. assertInEventLoop ( )
843
- if case . endOrError = self . state {
844
+
845
+ switch self . state {
846
+ case . idle:
847
+ preconditionFailure ( " should not happen " )
848
+ case . sendingBodyWaitingResponseHead:
849
+ self . state = . bodySentWaitingResponseHead
850
+ case . sendingBodyResponseHeadReceived:
851
+ self . state = . bodySentResponseHeadReceived
852
+ case . bodySentWaitingResponseHead, . bodySentResponseHeadReceived:
853
+ preconditionFailure ( " should not happen " )
854
+ case . endOrError, . redirected:
844
855
return context. eventLoop. makeSucceededFuture ( ( ) )
845
856
}
846
857
847
- self . state = . bodySent
848
858
if let expectedBodyLength = self . expectedBodyLength, expectedBodyLength != self . actualBodyLength {
849
859
let error = HTTPClientError . bodyLengthMismatch
850
860
return context. eventLoop. makeFailedFuture ( error)
851
861
}
852
862
return context. writeAndFlush ( self . wrapOutboundOut ( . end( nil ) ) )
853
863
} . map {
854
864
context. eventLoop. assertInEventLoop ( )
865
+
855
866
if case . endOrError = self . state {
856
867
return
857
868
}
858
869
859
- self . state = . sent
860
870
self . callOutToDelegateFireAndForget ( self . delegate. didSendRequest)
861
871
} . flatMapErrorThrowing { error in
862
872
context. eventLoop. assertInEventLoop ( )
@@ -903,6 +913,8 @@ extension TaskHandler: ChannelDuplexHandler {
903
913
private func writeBodyPart( context: ChannelHandlerContext , part: IOData , promise: EventLoopPromise < Void > ) {
904
914
switch self . state {
905
915
case . idle:
916
+ preconditionFailure ( " should not happen " )
917
+ case . sendingBodyWaitingResponseHead, . sendingBodyResponseHeadReceived:
906
918
if let limit = self . expectedBodyLength, self . actualBodyLength + part. readableBytes > limit {
907
919
let error = HTTPClientError . bodyLengthMismatch
908
920
self . errorCaught ( context: context, error: error)
@@ -911,7 +923,7 @@ extension TaskHandler: ChannelDuplexHandler {
911
923
}
912
924
self . actualBodyLength += part. readableBytes
913
925
context. writeAndFlush ( self . wrapOutboundOut ( . body( part) ) , promise: promise)
914
- default :
926
+ case . bodySentWaitingResponseHead , . bodySentResponseHeadReceived , . redirected , . endOrError :
915
927
let error = HTTPClientError . writeAfterRequestSent
916
928
self . errorCaught ( context: context, error: error)
917
929
promise. fail ( error)
@@ -931,7 +943,16 @@ extension TaskHandler: ChannelDuplexHandler {
931
943
let response = self . unwrapInboundIn ( data)
932
944
switch response {
933
945
case . head( let head) :
934
- if case . endOrError = self . state {
946
+ switch self . state {
947
+ case . idle:
948
+ preconditionFailure ( " should not happen " )
949
+ case . sendingBodyWaitingResponseHead:
950
+ self . state = . sendingBodyResponseHeadReceived
951
+ case . bodySentWaitingResponseHead:
952
+ self . state = . bodySentResponseHeadReceived
953
+ case . sendingBodyResponseHeadReceived, . bodySentResponseHeadReceived, . redirected:
954
+ preconditionFailure ( " should not happen " )
955
+ case . endOrError:
935
956
return
936
957
}
937
958
@@ -942,7 +963,6 @@ extension TaskHandler: ChannelDuplexHandler {
942
963
if let redirectURL = self . redirectHandler? . redirectTarget ( status: head. status, headers: head. headers) {
943
964
self . state = . redirected( head, redirectURL)
944
965
} else {
945
- self . state = . head
946
966
self . mayRead = false
947
967
self . callOutToDelegate ( value: head, channelEventLoop: context. eventLoop, self . delegate. didReceiveHead)
948
968
. whenComplete { result in
@@ -954,7 +974,6 @@ extension TaskHandler: ChannelDuplexHandler {
954
974
case . redirected, . endOrError:
955
975
break
956
976
default :
957
- self . state = . body
958
977
self . mayRead = false
959
978
self . callOutToDelegate ( value: body, channelEventLoop: context. eventLoop, self . delegate. didReceiveBodyPart)
960
979
. whenComplete { result in
@@ -1009,10 +1028,10 @@ extension TaskHandler: ChannelDuplexHandler {
1009
1028
1010
1029
func channelInactive( context: ChannelHandlerContext ) {
1011
1030
switch self . state {
1031
+ case . idle, . sendingBodyWaitingResponseHead, . sendingBodyResponseHeadReceived, . bodySentWaitingResponseHead, . bodySentResponseHeadReceived, . redirected:
1032
+ self . errorCaught ( context: context, error: HTTPClientError . remoteConnectionClosed)
1012
1033
case . endOrError:
1013
1034
break
1014
- case . body, . head, . idle, . redirected, . sent, . bodySent:
1015
- self . errorCaught ( context: context, error: HTTPClientError . remoteConnectionClosed)
1016
1035
}
1017
1036
context. fireChannelInactive ( )
1018
1037
}
@@ -1025,8 +1044,8 @@ extension TaskHandler: ChannelDuplexHandler {
1025
1044
/// Some HTTP Servers can 'forget' to respond with CloseNotify when client is closing connection,
1026
1045
/// this could lead to incomplete SSL shutdown. But since request is already processed, we can ignore this error.
1027
1046
break
1028
- case . head where self . ignoreUncleanSSLShutdown,
1029
- . body where self . ignoreUncleanSSLShutdown:
1047
+ case . sendingBodyResponseHeadReceived where self . ignoreUncleanSSLShutdown,
1048
+ . bodySentResponseHeadReceived where self . ignoreUncleanSSLShutdown:
1030
1049
/// We can also ignore this error like `.end`.
1031
1050
break
1032
1051
default :
@@ -1035,7 +1054,7 @@ extension TaskHandler: ChannelDuplexHandler {
1035
1054
}
1036
1055
default :
1037
1056
switch self . state {
1038
- case . idle, . bodySent , . sent , . head , . redirected , . body :
1057
+ case . idle, . sendingBodyWaitingResponseHead , . sendingBodyResponseHeadReceived , . bodySentWaitingResponseHead , . bodySentResponseHeadReceived , . redirected :
1039
1058
self . state = . endOrError
1040
1059
self . failTaskAndNotifyDelegate ( error: error, self . delegate. didReceiveError)
1041
1060
case . endOrError:
0 commit comments