@@ -158,68 +158,66 @@ impl<S: Schema, I: Init<S::ScalarValue, S::Context>> ConnectionState<S, I> {
158158 } => {
159159 let reactions = match msg {
160160 ClientMessage :: Subscribe { id, payload } => {
161+ // Prune stoppers which streams are already completed or canceled.
162+ stoppers. retain ( |_, tx| !tx. is_canceled ( ) ) ;
163+
161164 if stoppers. contains_key ( & id) {
162165 // We already have an operation with this id. We must close the connection.
163166 Output :: Close {
164167 code : 4409 ,
165168 message : format ! ( "Subscriber for {id} already exists" ) ,
166169 }
167170 . into_stream ( )
171+ } else if config. max_in_flight_operations > 0
172+ && stoppers. len ( ) >= config. max_in_flight_operations
173+ {
174+ // Too many in-flight operations. Just send back a validation error.
175+ stream:: iter ( vec ! [
176+ Output :: Message ( ServerMessage :: Error {
177+ id: id. clone( ) ,
178+ payload: GraphQLError :: from( RuleError :: new(
179+ "Too many in-flight operations." ,
180+ & [ ] ,
181+ ) )
182+ . into( ) ,
183+ } ) ,
184+ Output :: Message ( ServerMessage :: Complete { id } ) ,
185+ ] )
186+ . boxed ( )
168187 } else {
169- // Go ahead and prune canceled stoppers before adding a new one.
170- stoppers. retain ( |_, tx| !tx. is_canceled ( ) ) ;
171-
172- if config. max_in_flight_operations > 0
173- && stoppers. len ( ) >= config. max_in_flight_operations
174- {
175- // Too many in-flight operations. Just send back a validation error.
176- stream:: iter ( vec ! [
177- Output :: Message ( ServerMessage :: Error {
178- id: id. clone( ) ,
179- payload: GraphQLError :: from( RuleError :: new(
180- "Too many in-flight operations." ,
181- & [ ] ,
182- ) )
183- . into( ) ,
184- } ) ,
185- Output :: Message ( ServerMessage :: Complete { id } ) ,
186- ] )
187- . boxed ( )
188- } else {
189- // Create a channel that we can use to cancel the operation.
190- let ( tx, rx) = oneshot:: channel :: < ( ) > ( ) ;
191- stoppers. insert ( id. clone ( ) , tx) ;
192-
193- // Create the operation stream. This stream will emit Next and Error
194- // messages, but will not emit Complete – that part is up to us.
195- let s = Self :: start (
196- id. clone ( ) ,
197- ExecutionParams {
198- subscribe_payload : payload,
199- config : config. clone ( ) ,
200- schema : schema. clone ( ) ,
201- } ,
202- )
203- . into_stream ( )
204- . flatten ( ) ;
205-
206- // Combine this with our oneshot channel so that the stream ends if the
207- // oneshot is ever fired.
208- let s = stream:: unfold ( ( rx, s. boxed ( ) ) , async |( rx, mut s) | {
209- let next = match future:: select ( rx, s. next ( ) ) . await {
210- Either :: Left ( _) => None ,
211- Either :: Right ( ( r, rx) ) => r. map ( |r| ( r, rx) ) ,
212- } ;
213- next. map ( |( r, rx) | ( r, ( rx, s) ) )
214- } ) ;
215-
216- // Once the stream ends, send the Complete message.
217- let s = s. chain (
218- Output :: Message ( ServerMessage :: Complete { id } ) . into_stream ( ) ,
219- ) ;
220-
221- s. boxed ( )
222- }
188+ // Create a channel that we can use to cancel the operation.
189+ let ( tx, rx) = oneshot:: channel :: < ( ) > ( ) ;
190+ stoppers. insert ( id. clone ( ) , tx) ;
191+
192+ // Create the operation stream. This stream will emit Next and Error
193+ // messages, but will not emit Complete – that part is up to us.
194+ let s = Self :: start (
195+ id. clone ( ) ,
196+ ExecutionParams {
197+ subscribe_payload : payload,
198+ config : config. clone ( ) ,
199+ schema : schema. clone ( ) ,
200+ } ,
201+ )
202+ . into_stream ( )
203+ . flatten ( ) ;
204+
205+ // Combine this with our oneshot channel so that the stream ends if the
206+ // oneshot is ever fired.
207+ let s = stream:: unfold ( ( rx, s. boxed ( ) ) , async |( rx, mut s) | {
208+ let next = match future:: select ( rx, s. next ( ) ) . await {
209+ Either :: Left ( _) => None ,
210+ Either :: Right ( ( r, rx) ) => r. map ( |r| ( r, rx) ) ,
211+ } ;
212+ next. map ( |( r, rx) | ( r, ( rx, s) ) )
213+ } ) ;
214+
215+ // Once the stream ends, send the Complete message.
216+ let s = s. chain (
217+ Output :: Message ( ServerMessage :: Complete { id } ) . into_stream ( ) ,
218+ ) ;
219+
220+ s. boxed ( )
223221 }
224222 }
225223 ClientMessage :: Complete { id } => {
0 commit comments