@@ -269,6 +269,47 @@ def test_error_stream_stream(self):
269269            trace .StatusCode .ERROR ,
270270        )
271271
272+     def  test_client_interceptor_falsy_response (
273+         self ,
274+     ):  # pylint: disable=no-self-use 
275+         """ensure that client interceptor closes the span only once even if the response is falsy.""" 
276+ 
277+         span_end_count  =  0 
278+         tracer_provider , _exporter  =  self .create_tracer_provider ()
279+         tracer  =  tracer_provider .get_tracer (__name__ )
280+         original_start_span  =  tracer .start_span 
281+ 
282+         def  counting_span_end (original_end ):
283+             def  wrapper (* args , ** kwargs ):
284+                 nonlocal  span_end_count 
285+                 span_end_count  +=  1 
286+                 return  original_end (* args , ** kwargs )
287+ 
288+             return  wrapper 
289+ 
290+         def  patched_start_span (* args , ** kwargs ):
291+             span  =  original_start_span (* args , ** kwargs )
292+             span .end  =  counting_span_end (span .end )
293+             return  span 
294+ 
295+         tracer .start_span  =  patched_start_span 
296+         interceptor  =  OpenTelemetryClientInterceptor (tracer )
297+ 
298+         def  invoker (_request , _metadata ):
299+             return  {}
300+ 
301+         request  =  Request (client_id = 1 , request_data = "data" )
302+         interceptor .intercept_unary (
303+             request ,
304+             {},
305+             _UnaryClientInfo (
306+                 full_method = "/GRPCTestServer/SimpleMethod" ,
307+                 timeout = None ,
308+             ),
309+             invoker = invoker ,
310+         )
311+         assert  span_end_count  ==  1 
312+ 
272313    def  test_client_interceptor_trace_context_propagation (
273314        self ,
274315    ):  # pylint: disable=no-self-use 
0 commit comments