@@ -82,10 +82,8 @@ final class HTTP1ProxyConnectHandler: ChannelDuplexHandler, RemovableChannelHand
8282 preconditionFailure ( " How can we receive a channelInactive before a channelActive? " )
8383 case . connectSent( let timeout) , . headReceived( let timeout) :
8484 timeout. cancel ( )
85- let error = HTTPClientError . remoteConnectionClosed
86- self . state = . failed( error)
87- self . proxyEstablishedPromise? . fail ( error)
88- context. fireErrorCaught ( error)
85+ self . failWithError ( HTTPClientError . remoteConnectionClosed, context: context, closeConnection: false )
86+
8987 case . failed, . completed:
9088 break
9189 }
@@ -98,7 +96,7 @@ final class HTTP1ProxyConnectHandler: ChannelDuplexHandler, RemovableChannelHand
9896 func channelRead( context: ChannelHandlerContext , data: NIOAny ) {
9997 switch self . unwrapInboundIn ( data) {
10098 case . head( let head) :
101- guard case . connectSent( let promise ) = self . state else {
99+ guard case . connectSent( let scheduled ) = self . state else {
102100 preconditionFailure ( " HTTPDecoder should throw an error, if we have not send a request " )
103101 }
104102
@@ -107,34 +105,21 @@ final class HTTP1ProxyConnectHandler: ChannelDuplexHandler, RemovableChannelHand
107105 // Any 2xx (Successful) response indicates that the sender (and all
108106 // inbound proxies) will switch to tunnel mode immediately after the
109107 // blank line that concludes the successful response's header section
110- self . state = . headReceived( promise )
108+ self . state = . headReceived( scheduled )
111109 case 407 :
112- let error = HTTPClientError . proxyAuthenticationRequired
113- self . state = . failed( error)
114- self . proxyEstablishedPromise? . fail ( error)
115- context. fireErrorCaught ( error)
116- context. close ( mode: . all, promise: nil )
110+ self . failWithError ( HTTPClientError . proxyAuthenticationRequired, context: context)
117111
118112 default :
119- // Any response other than a successful response
120- // indicates that the tunnel has not yet been formed and that the
121- // connection remains governed by HTTP.
122- let error = HTTPClientError . invalidProxyResponse
123- self . state = . failed( error)
124- self . proxyEstablishedPromise? . fail ( error)
125- context. fireErrorCaught ( error)
126- context. close ( mode: . all, promise: nil )
113+ // Any response other than a successful response indicates that the tunnel
114+ // has not yet been formed and that the connection remains governed by HTTP.
115+ self . failWithError ( HTTPClientError . invalidProxyResponse, context: context)
127116 }
128117 case . body:
129118 switch self . state {
130119 case . headReceived( let timeout) :
131120 timeout. cancel ( )
132121 // we don't expect a body
133- let error = HTTPClientError . invalidProxyResponse
134- self . state = . failed( error)
135- self . proxyEstablishedPromise? . fail ( error)
136- context. fireErrorCaught ( error)
137- context. close ( mode: . all, promise: nil )
122+ self . failWithError ( HTTPClientError . invalidProxyResponse, context: context)
138123
139124 case . failed:
140125 // ran into an error before... ignore this one
@@ -171,11 +156,7 @@ final class HTTP1ProxyConnectHandler: ChannelDuplexHandler, RemovableChannelHand
171156 preconditionFailure ( " How can we have a scheduled timeout, if the connection is not even up? " )
172157
173158 case . connectSent, . headReceived:
174- let error = HTTPClientError . httpProxyHandshakeTimeout
175- self . state = . failed( error)
176- self . proxyEstablishedPromise? . fail ( error)
177- context. fireErrorCaught ( error)
178- context. close ( mode: . all, promise: nil )
159+ self . failWithError ( HTTPClientError . httpProxyHandshakeTimeout, context: context)
179160
180161 case . failed, . completed:
181162 break
@@ -196,4 +177,13 @@ final class HTTP1ProxyConnectHandler: ChannelDuplexHandler, RemovableChannelHand
196177 context. write ( self . wrapOutboundOut ( . end( nil ) ) , promise: nil )
197178 context. flush ( )
198179 }
180+
181+ private func failWithError( _ error: Error , context: ChannelHandlerContext , closeConnection: Bool = true ) {
182+ self . state = . failed( error)
183+ self . proxyEstablishedPromise? . fail ( error)
184+ context. fireErrorCaught ( error)
185+ if closeConnection {
186+ context. close ( mode: . all, promise: nil )
187+ }
188+ }
199189}
0 commit comments