1
1
use std:: str:: FromStr ;
2
2
3
3
use colored:: * ;
4
- use ore_api:: state:: proof_pda;
4
+ use ore_api:: state:: { proof_pda, Proof } ;
5
5
use ore_boost_api:: {
6
6
consts:: DENOMINATOR_MULTIPLIER ,
7
- state:: { boost_pda, stake_pda, Boost } ,
7
+ state:: { boost_pda, stake_pda, Boost , Stake } ,
8
8
} ;
9
9
use solana_program:: { program_pack:: Pack , pubkey:: Pubkey } ;
10
10
use solana_sdk:: signature:: Signer ;
11
11
use spl_token:: { amount_to_ui_amount, state:: Mint } ;
12
+ use steel:: Numeric ;
12
13
use tabled:: {
13
14
settings:: {
14
15
object:: { Columns , Rows } ,
@@ -120,6 +121,10 @@ impl Miner {
120
121
let mint_address = Pubkey :: from_str ( & mint) . expect ( "Failed to parse mint address" ) ;
121
122
let boost_address = boost_pda ( mint_address) . 0 ;
122
123
let stake_address = stake_pda ( self . signer ( ) . pubkey ( ) , boost_address) . 0 ;
124
+ let boost_proof_address = proof_pda ( boost_address) . 0 ;
125
+ let boost_proof: ore_api:: prelude:: Proof = get_proof ( & self . rpc_client , boost_proof_address)
126
+ . await
127
+ . expect ( "Failed to fetch proof account" ) ;
123
128
let boost = get_boost ( & self . rpc_client , boost_address)
124
129
. await
125
130
. expect ( "Failed to fetch boost account" ) ;
@@ -145,8 +150,15 @@ impl Miner {
145
150
self . fetch_boost_data ( boost_address, boost, mint, symbol. clone ( ) , & mut data)
146
151
. await ;
147
152
let len1 = data. len ( ) ;
148
- self . fetch_stake_data ( stake_address, boost, mint, symbol. clone ( ) , & mut data)
149
- . await ;
153
+ self . fetch_stake_data (
154
+ stake_address,
155
+ boost,
156
+ boost_proof,
157
+ mint,
158
+ symbol. clone ( ) ,
159
+ & mut data,
160
+ )
161
+ . await ;
150
162
let _len2 = data. len ( ) ;
151
163
152
164
// Build table
@@ -164,6 +176,7 @@ impl Miner {
164
176
& self ,
165
177
address : Pubkey ,
166
178
boost : Boost ,
179
+ boost_proof : Proof ,
167
180
mint : Mint ,
168
181
symbol : String ,
169
182
data : & mut Vec < TableData > ,
@@ -174,6 +187,7 @@ impl Miner {
174
187
value : address. to_string ( ) ,
175
188
} ) ;
176
189
if let Ok ( stake) = stake {
190
+ let claimable_yield = calculate_claimable_yield ( boost, boost_proof, stake) ;
177
191
data. push ( TableData {
178
192
key : "Deposits" . to_string ( ) ,
179
193
value : format ! (
@@ -189,13 +203,13 @@ impl Miner {
189
203
} ) ;
190
204
data. push ( TableData {
191
205
key : "Yield" . to_string ( ) ,
192
- value : if stake . rewards > 0 {
193
- format ! ( "{} ORE" , amount_u64_to_f64( stake . rewards ) )
206
+ value : if claimable_yield > 0 {
207
+ format ! ( "{} ORE" , amount_u64_to_f64( claimable_yield ) )
194
208
. yellow ( )
195
209
. bold ( )
196
210
. to_string ( )
197
211
} else {
198
- format ! ( "{} ORE" , amount_u64_to_f64( stake . rewards ) )
212
+ format ! ( "{} ORE" , amount_u64_to_f64( claimable_yield ) )
199
213
} ,
200
214
} ) ;
201
215
} else {
@@ -274,6 +288,11 @@ impl Miner {
274
288
. expect ( "Failed to fetch boosts" ) ;
275
289
for ( address, boost) in boosts {
276
290
// Get relevant accounts
291
+ let boost_proof_address = proof_pda ( address) . 0 ;
292
+ let boost_proof: ore_api:: prelude:: Proof =
293
+ get_proof ( & self . rpc_client , boost_proof_address)
294
+ . await
295
+ . expect ( "Failed to fetch proof account" ) ;
277
296
let stake_address = stake_pda ( authority, address) . 0 ;
278
297
let stake = get_stake ( & self . rpc_client , stake_address) . await ;
279
298
let mint = get_mint ( & self . rpc_client , boost. mint )
@@ -295,7 +314,10 @@ impl Miner {
295
314
296
315
// Parse optional stake data
297
316
let ( stake_balance, stake_rewards) = if let Ok ( stake) = stake {
298
- ( stake. balance , stake. rewards )
317
+ (
318
+ stake. balance ,
319
+ calculate_claimable_yield ( boost, boost_proof, stake) ,
320
+ )
299
321
} else {
300
322
( 0 , 0 )
301
323
} ;
@@ -553,6 +575,20 @@ impl Miner {
553
575
}
554
576
}
555
577
578
+ pub fn calculate_claimable_yield ( boost : Boost , boost_proof : Proof , stake : Stake ) -> u64 {
579
+ let mut rewards = stake. rewards ;
580
+ let mut boost_rewards_factor = boost. rewards_factor ;
581
+ if boost_proof. balance > 0 {
582
+ boost_rewards_factor += Numeric :: from_fraction ( boost_proof. balance , boost. total_deposits ) ;
583
+ }
584
+ if boost_rewards_factor > stake. last_rewards_factor {
585
+ let accumulated_rewards = boost_rewards_factor - stake. last_rewards_factor ;
586
+ let personal_rewards = accumulated_rewards * Numeric :: from_u64 ( stake. balance ) ;
587
+ rewards += personal_rewards. to_u64 ( ) ;
588
+ }
589
+ rewards
590
+ }
591
+
556
592
#[ derive( Tabled ) ]
557
593
pub struct StakeTableData {
558
594
#[ tabled( rename = "Mint" ) ]
0 commit comments