Skip to content

Conversation

hchen2020
Copy link
Contributor

@hchen2020 hchen2020 commented Sep 23, 2025

PR Type

Bug fix


Description

  • Remove manual WebSocket dispose calls causing disposal issues

  • Replace field-based session with using statement for proper disposal

  • Fix resource management in Twilio streaming middleware


Diagram Walkthrough

flowchart LR
  A["Manual Dispose Calls"] --> B["Resource Management Issues"]
  B --> C["Remove Manual Dispose"]
  C --> D["Using Statement Pattern"]
  D --> E["Proper Resource Cleanup"]
Loading

File Walkthrough

Relevant files
Bug fix
AsyncWebsocketDataResultEnumerator.cs
Remove manual WebSocket disposal                                                 

src/Infrastructure/BotSharp.Core/Infrastructures/Websocket/AsyncWebsocketDataResultEnumerator.cs

  • Remove manual WebSocket dispose call from DisposeAsync method
+0/-1     
LlmRealtimeSession.cs
Remove WebSocket disposal in ConnectAsync                               

src/Infrastructure/BotSharp.Core/Session/LlmRealtimeSession.cs

  • Remove manual WebSocket dispose call before creating new instance
+0/-1     
RealTimeCompletionProvider.cs
Remove session disposal in Connect                                             

src/Plugins/BotSharp.Plugin.OpenAI/Providers/Realtime/RealTimeCompletionProvider.cs

  • Remove manual session dispose call before creating new session
+0/-1     
TwilioStreamMiddleware.cs
Fix session disposal with using pattern                                   

src/Plugins/BotSharp.Plugin.Twilio/TwilioStreamMiddleware.cs

  • Remove private session field and manual dispose calls
  • Replace with using statement for proper resource management
  • Update session usage throughout HandleWebSocket method
+3/-7     

Copy link

PR Reviewer Guide 🔍

Here are some key observations to aid the review process:

⏱️ Estimated effort to review: 2 🔵🔵⚪⚪⚪
🧪 No relevant tests
🔒 No security concerns identified
⚡ Recommended focus areas for review

Disposal Semantics

Ensure the new 'using var session' pattern guarantees timely cleanup in all control flows (including exceptions) and that no background operations reference the session after the method returns.

private async Task HandleWebSocket(IServiceProvider services, string agentId, string conversationId, WebSocket webSocket)
{
    using var session = new BotSharpRealtimeSession(services, webSocket, new ChatSessionOptions
    {
        Provider = "BotSharp Twilio Stream",
        BufferSize = 1024 * 32,
        JsonOptions = BotSharpOptions.defaultJsonOptions,
WebSocket Lifetime

Verify that removing manual '_webSocket?.Dispose()' does not leave sockets undisposed and that ownership is clearly transferred elsewhere to prevent leaks.

public ValueTask DisposeAsync()
{
    ArrayPool<byte>.Shared.Return(_buffer, clearArray: true);
    return new ValueTask(Task.CompletedTask);
}
Disconnect Ordering

Validate that calling 'await session.DisconnectAsync()' before 'using' scope ends is sufficient and that no additional explicit Dispose is required for underlying resources.

    convService.SaveStates();
    await session.DisconnectAsync();
}

@Oceania2018 Oceania2018 merged commit 3b692a9 into SciSharp:master Sep 23, 2025
3 of 4 checks passed
Copy link

PR Code Suggestions ✨

Explore these optional code suggestions:

CategorySuggestion                                                                                                                                    Impact
Possible issue
Use await using for async disposal

Replace using with await using for the BotSharpRealtimeSession object to ensure
its DisposeAsync method is called for correct asynchronous resource disposal.

src/Plugins/BotSharp.Plugin.Twilio/TwilioStreamMiddleware.cs [65-71]

-using var session = new BotSharpRealtimeSession(services, webSocket, new ChatSessionOptions
+await using var session = new BotSharpRealtimeSession(services, webSocket, new ChatSessionOptions
 {
     Provider = "BotSharp Twilio Stream",
     BufferSize = 1024 * 32,
     JsonOptions = BotSharpOptions.defaultJsonOptions,
     Logger = _logger
 });
  • Apply / Chat
Suggestion importance[1-10]: 8

__

Why: The suggestion correctly identifies that using should be await using for a resource that likely implements IAsyncDisposable, which is a critical fix to prevent potential deadlocks and ensure proper asynchronous cleanup.

Medium
  • More

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants