@@ -8,29 +8,50 @@ namespace Cnblogs.DashScope.Core;
88public sealed class DashScopeClientWebSocketPool : IDisposable
99{
1010 private readonly ConcurrentBag < DashScopeClientWebSocket > _available = new ( ) ;
11- private readonly ConcurrentBag < DashScopeClientWebSocket > _active = new ( ) ;
11+ private readonly ConcurrentDictionary < Guid , DashScopeClientWebSocket > _active = new ( ) ;
1212 private readonly DashScopeOptions _options ;
13+ private readonly IDashScopeClientWebSocketFactory _dashScopeClientWebSocketFactory ;
1314
1415 /// <summary>
1516 /// Socket pool for DashScope API.
1617 /// </summary>
18+ /// <param name="dashScopeClientWebSocketFactory"></param>
1719 /// <param name="options">Options for DashScope sdk.</param>
18- public DashScopeClientWebSocketPool ( DashScopeOptions options )
20+ public DashScopeClientWebSocketPool (
21+ IDashScopeClientWebSocketFactory dashScopeClientWebSocketFactory ,
22+ DashScopeOptions options )
1923 {
24+ _dashScopeClientWebSocketFactory = dashScopeClientWebSocketFactory ;
2025 _options = options ;
2126 }
2227
23- internal DashScopeClientWebSocketPool ( IEnumerable < DashScopeClientWebSocket > sockets )
28+ /// <summary>
29+ /// Get available connection count.
30+ /// </summary>
31+ internal int AvailableSocketCount => _available . Count ;
32+
33+ /// <summary>
34+ /// Get active connection count.
35+ /// </summary>
36+ internal int ActiveSocketCount => _active . Count ;
37+
38+ internal DashScopeClientWebSocketPool (
39+ IEnumerable < DashScopeClientWebSocket > sockets ,
40+ IDashScopeClientWebSocketFactory dashScopeClientWebSocketFactory )
2441 {
2542 _options = new DashScopeOptions ( ) ;
2643 foreach ( var socket in sockets )
2744 {
2845 _available . Add ( socket ) ;
2946 }
47+
48+ _dashScopeClientWebSocketFactory = dashScopeClientWebSocketFactory ;
3049 }
3150
32- internal void ReturnSocketAsync ( DashScopeClientWebSocket socket )
51+ internal void ReturnSocket ( DashScopeClientWebSocket socket )
3352 {
53+ _active . Remove ( socket . Id , out _ ) ;
54+
3455 if ( socket . State != DashScopeWebSocketState . Ready )
3556 {
3657 // not returnable, disposing.
@@ -45,11 +66,8 @@ internal void ReturnSocketAsync(DashScopeClientWebSocket socket)
4566 /// Rent or create a socket connection from pool.
4667 /// </summary>
4768 /// <param name="cancellationToken"></param>
48- /// <typeparam name="TOutput">The output type.</typeparam>
4969 /// <returns></returns>
50- public async Task < DashScopeClientWebSocketWrapper > RentSocketAsync < TOutput > (
51- CancellationToken cancellationToken = default )
52- where TOutput : class
70+ public async Task < DashScopeClientWebSocketWrapper > RentSocketAsync ( CancellationToken cancellationToken = default )
5371 {
5472 var found = false ;
5573 DashScopeClientWebSocket ? socket = null ;
@@ -67,7 +85,7 @@ public async Task<DashScopeClientWebSocketWrapper> RentSocketAsync<TOutput>(
6785 }
6886 else
6987 {
70- socket = await InitializeNewSocketAsync < TOutput > ( _options . BaseWebsocketAddress , cancellationToken ) ;
88+ socket = await InitializeNewSocketAsync ( _options . WebsocketBaseAddress , cancellationToken ) ;
7189 found = true ;
7290 }
7391 }
@@ -77,22 +95,21 @@ public async Task<DashScopeClientWebSocketWrapper> RentSocketAsync<TOutput>(
7795
7896 private DashScopeClientWebSocketWrapper ActivateSocket ( DashScopeClientWebSocket socket )
7997 {
80- _active . Add ( socket ) ;
98+ _active . TryAdd ( socket . Id , socket ) ;
8199 return new DashScopeClientWebSocketWrapper ( socket , this ) ;
82100 }
83101
84- private async Task < DashScopeClientWebSocket > InitializeNewSocketAsync < TOutput > (
102+ private async Task < DashScopeClientWebSocket > InitializeNewSocketAsync (
85103 string url ,
86104 CancellationToken cancellationToken = default )
87- where TOutput : class
88105 {
89106 if ( _available . Count + _active . Count >= _options . SocketPoolSize )
90107 {
91108 throw new InvalidOperationException ( "[DashScopeSDK] Socket pool is full" ) ;
92109 }
93110
94- var socket = new DashScopeClientWebSocket ( _options . ApiKey , _options . WorkspaceId ) ;
95- await socket . ConnectAsync < TOutput > ( new Uri ( url ) , cancellationToken ) ;
111+ var socket = _dashScopeClientWebSocketFactory . GetClientWebSocket ( _options . ApiKey , _options . WorkspaceId ) ;
112+ await socket . ConnectAsync ( new Uri ( url ) , cancellationToken ) ;
96113 return socket ;
97114 }
98115
@@ -107,10 +124,10 @@ private void Dispose(bool disposing)
107124 socket ? . Dispose ( ) ;
108125 }
109126
110- while ( _active . IsEmpty == false )
127+ var activeSockets = _active . Values ;
128+ foreach ( var activeSocket in activeSockets )
111129 {
112- _active . TryTake ( out var socket ) ;
113- socket ? . Dispose ( ) ;
130+ activeSocket . Dispose ( ) ;
114131 }
115132 }
116133 }
0 commit comments