@@ -80,6 +80,11 @@ def __init__(
8080 - None: No visualization
8181 stuck_detection: Whether to enable stuck detection
8282 """
83+ super ().__init__ () # Initialize with span tracking
84+ # Mark cleanup as initiated as early as possible to avoid races or partially
85+ # initialized instances during interpreter shutdown.
86+ self ._cleanup_initiated = False
87+
8388 self .agent = agent
8489 if isinstance (workspace , str ):
8590 workspace = LocalWorkspace (working_dir = workspace )
@@ -150,8 +155,6 @@ def _default_callback(e):
150155 secret_values : dict [str , SecretValue ] = {k : v for k , v in secrets .items ()}
151156 self .update_secrets (secret_values )
152157
153- super ().__init__ () # Initialize base class with span tracking
154- self ._cleanup_initiated = False
155158 atexit .register (self .close )
156159 self ._start_observability_span (str (desired_id ))
157160
@@ -395,7 +398,11 @@ def close(self) -> None:
395398 return
396399 self ._cleanup_initiated = True
397400 logger .debug ("Closing conversation and cleaning up tool executors" )
398- self ._end_observability_span ()
401+ try :
402+ self ._end_observability_span ()
403+ except AttributeError :
404+ # Object may be partially constructed; span fields may be missing.
405+ pass
399406 for tool in self .agent .tools_map .values ():
400407 try :
401408 executable_tool = tool .as_executable ()
0 commit comments