@@ -9,7 +9,15 @@ use solana_dex_superagg::{
99} ;
1010use solana_program:: pubkey:: Pubkey ;
1111use std:: { collections:: HashSet , sync:: Arc } ;
12- use tokio:: runtime:: { Builder , Runtime } ;
12+ use tokio:: {
13+ runtime:: { Builder , Runtime } ,
14+ sync:: Semaphore ,
15+ } ;
16+
17+ /// Concurrent DEX operations allowed across the liquidation workers and the rebalancer. Each one
18+ /// costs several aggregator round-trips, so an unbounded burst trips the Jupiter rate limit (429)
19+ /// and the failing targets then sit in the executor's backoff.
20+ const MAX_CONCURRENT_DEX_CALLS : usize = 2 ;
1321
1422/// Don't bother selling a position worth less than this (USD); the swap fee/dust isn't worth it.
1523const MIN_REBALANCE_VALUE : I80F48 = I80F48 ! ( 1.0 ) ;
@@ -23,6 +31,7 @@ pub struct Rebalancer {
2331 tokio_rt : Runtime ,
2432 cache : Arc < Cache > ,
2533 dex_client : Arc < DexSuperAggClient > ,
34+ dex_gate : Arc < Semaphore > ,
2635 empty_stake_banks : HashSet < Pubkey > ,
2736 unpriceable_mints : HashSet < Pubkey > ,
2837}
@@ -74,6 +83,7 @@ impl Rebalancer {
7483 tokio_rt,
7584 cache,
7685 dex_client,
86+ dex_gate : Arc :: new ( Semaphore :: new ( MAX_CONCURRENT_DEX_CALLS ) ) ,
7787 empty_stake_banks : HashSet :: new ( ) ,
7888 unpriceable_mints : HashSet :: new ( ) ,
7989 } )
@@ -83,6 +93,10 @@ impl Rebalancer {
8393 Arc :: clone ( & self . dex_client )
8494 }
8595
96+ pub fn dex_gate ( & self ) -> Arc < Semaphore > {
97+ Arc :: clone ( & self . dex_gate )
98+ }
99+
86100 /// Sell every non-swap-mint token the wallet holds (above the dust floor) back to the swap mint.
87101 pub fn run ( & mut self ) -> anyhow:: Result < ( ) > {
88102 info ! ( "Running the Rebalancing process..." ) ;
@@ -191,12 +205,17 @@ impl Rebalancer {
191205 const WSOL : Pubkey = Pubkey :: from_str_const ( "So11111111111111111111111111111111111111112" ) ;
192206 let wrap_and_unwrap_sol = input_mint == WSOL || output_mint == WSOL ;
193207
194- let result = self . tokio_rt . block_on ( self . dex_client . swap (
195- & input_mint. to_string ( ) ,
196- & output_mint. to_string ( ) ,
197- amount,
198- wrap_and_unwrap_sol,
199- ) ) ?;
208+ let result = self . tokio_rt . block_on ( async {
209+ let _permit = self . dex_gate . acquire ( ) . await ?;
210+ self . dex_client
211+ . swap (
212+ & input_mint. to_string ( ) ,
213+ & output_mint. to_string ( ) ,
214+ amount,
215+ wrap_and_unwrap_sol,
216+ )
217+ . await
218+ } ) ?;
200219
201220 info ! (
202221 "Swap successful! Transaction: {}, Output: {} tokens of mint {}" ,
0 commit comments