@jpool/bond-sdk 0.9.0-next.9 → 0.10.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,6 +1,7 @@
1
1
  'use strict';
2
2
 
3
3
  var anchor = require('@coral-xyz/anchor');
4
+ var bytes = require('@coral-xyz/anchor/dist/cjs/utils/bytes');
4
5
  var splStakePool = require('@solana/spl-stake-pool');
5
6
  var splToken = require('@solana/spl-token');
6
7
  var web3_js = require('@solana/web3.js');
@@ -4579,7 +4580,7 @@ var Seeds = /* @__PURE__ */ ((Seeds2) => {
4579
4580
  Seeds2["GlobalState"] = "global_state";
4580
4581
  Seeds2["BondState"] = "bond_state";
4581
4582
  Seeds2["ValidatorBond"] = "validator_bond";
4582
- Seeds2["PerformanceBond"] = "performance";
4583
+ Seeds2["StandardBond"] = "standard";
4583
4584
  Seeds2["CrowdFundingBond"] = "crowdfunding";
4584
4585
  return Seeds2;
4585
4586
  })(Seeds || {});
@@ -4593,13 +4594,17 @@ init_cjs_shims();
4593
4594
  // src/types/index.ts
4594
4595
  init_cjs_shims();
4595
4596
  var bondTypeToSeed = {
4596
- performance: "performance" /* PerformanceBond */,
4597
+ standard: "standard" /* StandardBond */,
4597
4598
  crowdfunding: "crowdfunding" /* CrowdFundingBond */
4598
4599
  };
4599
4600
  var BondTypeVariant = {
4600
- Performance: { performance: {} },
4601
+ Standard: { standard: {} },
4601
4602
  Crowdfunding: { crowdfunding: {} }
4602
4603
  };
4604
+ var BondStateStatusVariant = {
4605
+ Active: { active: {} },
4606
+ Disabled: { disabled: {} }
4607
+ };
4603
4608
  var BondTransactionType = /* @__PURE__ */ ((BondTransactionType2) => {
4604
4609
  BondTransactionType2["Deposit"] = "deposit";
4605
4610
  BondTransactionType2["Withdrawal"] = "withdrawal";
@@ -4747,23 +4752,12 @@ var HistoryManager = class {
4747
4752
  if (!type || amount <= 0) {
4748
4753
  continue;
4749
4754
  }
4750
- let beforeBalance;
4751
- let afterBalance;
4752
- const accIdx = tx.transaction.message.accountKeys.findIndex(
4753
- (k) => k.pubkey.equals(validatorBondAccount)
4754
- );
4755
- if (accIdx !== -1 && tx.meta.preBalances && tx.meta.postBalances) {
4756
- beforeBalance = Number(tx.meta.preBalances[accIdx] ?? 0) / web3_js.LAMPORTS_PER_SOL;
4757
- afterBalance = Number(tx.meta.postBalances[accIdx] ?? 0) / web3_js.LAMPORTS_PER_SOL;
4758
- }
4759
4755
  history.push({
4760
4756
  signature: sig,
4761
4757
  slot,
4762
4758
  epoch: slotToEpoch(slot, cluster),
4763
4759
  type,
4764
- amount,
4765
- beforeBalance,
4766
- afterBalance
4760
+ amount
4767
4761
  });
4768
4762
  }
4769
4763
  }
@@ -4838,7 +4832,7 @@ var HistoryManager = class {
4838
4832
 
4839
4833
  // src/idl/jbond.json
4840
4834
  var jbond_default = {
4841
- address: "DBuUGWbLz8CkAMQiagMfrQzj8SSg1rHQJWrTSc97HWfR",
4835
+ address: "BondQ7KqZreTcW2UbeTNDcLCJQ3aXAtLn2Fm6ftaJDU",
4842
4836
  metadata: {
4843
4837
  name: "jbond",
4844
4838
  version: "0.2.1",
@@ -5015,10 +5009,6 @@ var jbond_default = {
5015
5009
  210
5016
5010
  ],
5017
5011
  accounts: [
5018
- {
5019
- name: "global_state",
5020
- writable: true
5021
- },
5022
5012
  {
5023
5013
  name: "bond_state",
5024
5014
  writable: true,
@@ -5551,9 +5541,6 @@ var jbond_default = {
5551
5541
  },
5552
5542
  {
5553
5543
  name: "global_initialize",
5554
- docs: [
5555
- "----------------------------- Global Instructions ----------------------------"
5556
- ],
5557
5544
  discriminator: [
5558
5545
  30,
5559
5546
  79,
@@ -5602,6 +5589,111 @@ var jbond_default = {
5602
5589
  ],
5603
5590
  args: []
5604
5591
  },
5592
+ {
5593
+ name: "migrate_bond",
5594
+ docs: [
5595
+ "Migrates validator bond data from legacy structure to new structure."
5596
+ ],
5597
+ discriminator: [
5598
+ 107,
5599
+ 119,
5600
+ 59,
5601
+ 110,
5602
+ 76,
5603
+ 18,
5604
+ 37,
5605
+ 163
5606
+ ],
5607
+ accounts: [
5608
+ {
5609
+ name: "bond_state",
5610
+ writable: true
5611
+ },
5612
+ {
5613
+ name: "legacy_validator_bond",
5614
+ writable: true
5615
+ },
5616
+ {
5617
+ name: "legacy_vote_account"
5618
+ },
5619
+ {
5620
+ name: "validator_bond",
5621
+ writable: true,
5622
+ pda: {
5623
+ seeds: [
5624
+ {
5625
+ kind: "const",
5626
+ value: [
5627
+ 118,
5628
+ 97,
5629
+ 108,
5630
+ 105,
5631
+ 100,
5632
+ 97,
5633
+ 116,
5634
+ 111,
5635
+ 114,
5636
+ 95,
5637
+ 98,
5638
+ 111,
5639
+ 110,
5640
+ 100
5641
+ ]
5642
+ },
5643
+ {
5644
+ kind: "account",
5645
+ path: "bond_state"
5646
+ },
5647
+ {
5648
+ kind: "account",
5649
+ path: "legacy_vote_account"
5650
+ }
5651
+ ]
5652
+ }
5653
+ },
5654
+ {
5655
+ name: "creator",
5656
+ writable: true,
5657
+ signer: true
5658
+ },
5659
+ {
5660
+ name: "system_program",
5661
+ address: "11111111111111111111111111111111"
5662
+ }
5663
+ ],
5664
+ args: []
5665
+ },
5666
+ {
5667
+ name: "session_finish",
5668
+ docs: [
5669
+ "Finishes a bond, preventing further deposits and withdrawals."
5670
+ ],
5671
+ discriminator: [
5672
+ 230,
5673
+ 209,
5674
+ 54,
5675
+ 205,
5676
+ 127,
5677
+ 141,
5678
+ 137,
5679
+ 113
5680
+ ],
5681
+ accounts: [
5682
+ {
5683
+ name: "bond_state",
5684
+ writable: true
5685
+ },
5686
+ {
5687
+ name: "authority",
5688
+ writable: true,
5689
+ signer: true,
5690
+ relations: [
5691
+ "bond_state"
5692
+ ]
5693
+ }
5694
+ ],
5695
+ args: []
5696
+ },
5605
5697
  {
5606
5698
  name: "session_start",
5607
5699
  docs: [
@@ -5870,6 +5962,16 @@ var jbond_default = {
5870
5962
  code: 6021,
5871
5963
  name: "InvalidArgument",
5872
5964
  msg: "Invalid argument provided"
5965
+ },
5966
+ {
5967
+ code: 6022,
5968
+ name: "BondNotDisabled",
5969
+ msg: "Bond is not disabled"
5970
+ },
5971
+ {
5972
+ code: 6023,
5973
+ name: "BondNotEnabled",
5974
+ msg: "Bond is not enabled"
5873
5975
  }
5874
5976
  ],
5875
5977
  types: [
@@ -5878,6 +5980,16 @@ var jbond_default = {
5878
5980
  type: {
5879
5981
  kind: "struct",
5880
5982
  fields: [
5983
+ {
5984
+ name: "status",
5985
+ type: {
5986
+ option: {
5987
+ defined: {
5988
+ name: "BondStatus"
5989
+ }
5990
+ }
5991
+ }
5992
+ },
5881
5993
  {
5882
5994
  name: "new_reserve",
5883
5995
  type: {
@@ -5980,7 +6092,7 @@ var jbond_default = {
5980
6092
  {
5981
6093
  name: "bond_type",
5982
6094
  docs: [
5983
- "The type of bond (e.g., Performance, Crowdfunding)"
6095
+ "The type of bond (e.g., Standard, Crowdfunding)"
5984
6096
  ],
5985
6097
  type: {
5986
6098
  defined: {
@@ -6048,6 +6160,17 @@ var jbond_default = {
6048
6160
  ],
6049
6161
  type: "i64"
6050
6162
  },
6163
+ {
6164
+ name: "status",
6165
+ docs: [
6166
+ "Current status of the bond"
6167
+ ],
6168
+ type: {
6169
+ defined: {
6170
+ name: "BondStatus"
6171
+ }
6172
+ }
6173
+ },
6051
6174
  {
6052
6175
  name: "bump",
6053
6176
  docs: [
@@ -6058,6 +6181,20 @@ var jbond_default = {
6058
6181
  ]
6059
6182
  }
6060
6183
  },
6184
+ {
6185
+ name: "BondStatus",
6186
+ type: {
6187
+ kind: "enum",
6188
+ variants: [
6189
+ {
6190
+ name: "Active"
6191
+ },
6192
+ {
6193
+ name: "Disabled"
6194
+ }
6195
+ ]
6196
+ }
6197
+ },
6061
6198
  {
6062
6199
  name: "BondType",
6063
6200
  docs: [
@@ -6067,7 +6204,7 @@ var jbond_default = {
6067
6204
  kind: "enum",
6068
6205
  variants: [
6069
6206
  {
6070
- name: "Performance"
6207
+ name: "Standard"
6071
6208
  },
6072
6209
  {
6073
6210
  name: "Crowdfunding"
@@ -6193,15 +6330,6 @@ var jbond_default = {
6193
6330
  type: {
6194
6331
  kind: "struct",
6195
6332
  fields: [
6196
- {
6197
- name: "bonds",
6198
- docs: [
6199
- "List of all registered bonds"
6200
- ],
6201
- type: {
6202
- vec: "pubkey"
6203
- }
6204
- },
6205
6333
  {
6206
6334
  name: "authority",
6207
6335
  docs: [
@@ -6225,7 +6353,7 @@ var jbond_default = {
6225
6353
  kind: "struct",
6226
6354
  fields: [
6227
6355
  {
6228
- name: "bond",
6356
+ name: "state",
6229
6357
  type: "pubkey"
6230
6358
  },
6231
6359
  {
@@ -6246,26 +6374,10 @@ var jbond_default = {
6246
6374
  option: "pubkey"
6247
6375
  }
6248
6376
  },
6249
- {
6250
- name: "total_compensation_amount",
6251
- type: "u64"
6252
- },
6253
- {
6254
- name: "last_compensation_amount",
6255
- type: "u64"
6256
- },
6257
- {
6258
- name: "last_compensation_epoch",
6259
- type: "u64"
6260
- },
6261
6377
  {
6262
6378
  name: "created_at",
6263
6379
  type: "i64"
6264
6380
  },
6265
- {
6266
- name: "is_active",
6267
- type: "bool"
6268
- },
6269
6381
  {
6270
6382
  name: "bump",
6271
6383
  type: "u8"
@@ -6563,10 +6675,8 @@ var JBondClient = class _JBondClient {
6563
6675
  * Build initialize instruction
6564
6676
  */
6565
6677
  async buildBondInitializeIx(props) {
6566
- const [globalState] = this.pda.globalState();
6567
6678
  const [bondState] = this.pda.bondState(props.bondType, props.name);
6568
6679
  const accounts = {
6569
- globalState,
6570
6680
  bondState,
6571
6681
  authority: props.authority ?? this.program.provider.wallet?.publicKey,
6572
6682
  reserve: props.reserve,
@@ -6581,8 +6691,6 @@ var JBondClient = class _JBondClient {
6581
6691
  token: (mint) => {
6582
6692
  accounts.reserveTokenAccount = splToken.getAssociatedTokenAddressSync(mint, props.reserve);
6583
6693
  accounts.mint = mint;
6584
- },
6585
- stakeAccount: () => {
6586
6694
  }
6587
6695
  });
6588
6696
  return this.program.methods.bondInitialize({
@@ -6597,6 +6705,7 @@ var JBondClient = class _JBondClient {
6597
6705
  async buildConfigureIx(props) {
6598
6706
  const [bondState] = this.pda.bondState(props.bondType, props.name);
6599
6707
  return this.program.methods.bondConfigure({
6708
+ status: props.bondStateStatus ?? null,
6600
6709
  newReserve: props.newReserve ?? null,
6601
6710
  newAuthority: props.newAuthority ?? null
6602
6711
  }).accountsStrict({
@@ -6612,7 +6721,7 @@ var JBondClient = class _JBondClient {
6612
6721
  if (!creator) {
6613
6722
  throw new Error("Missing creator");
6614
6723
  }
6615
- const collateralType = (await this.getBondState(bondType, name)).collateralType;
6724
+ const collateralType = (await this.getBondState(bondType, name)).bondState.collateralType;
6616
6725
  const accounts = {
6617
6726
  bondState,
6618
6727
  validatorBond,
@@ -6631,9 +6740,6 @@ var JBondClient = class _JBondClient {
6631
6740
  token: (mint) => {
6632
6741
  accounts.bondTokenAccount = splToken.getAssociatedTokenAddressSync(mint, validatorBond, true);
6633
6742
  Object.assign(accounts, { mint, bondTokenAccount: accounts.bondTokenAccount });
6634
- },
6635
- stakeAccount: () => {
6636
- throw new Error("Stake account collateral type is not currently supported");
6637
6743
  }
6638
6744
  });
6639
6745
  return this.program.methods.bondRegister(bondType, name).accountsPartial(accounts).instruction();
@@ -6647,16 +6753,18 @@ var JBondClient = class _JBondClient {
6647
6753
  const instructions = [];
6648
6754
  const [bondState] = this.pda.bondState(bondType, name);
6649
6755
  const [validatorBond] = this.pda.validatorBond(bondType, name, voteAccount);
6756
+ console.log("Top up collateral for bond:", { bondState: bondState.toBase58(), validatorBond: validatorBond.toBase58() });
6650
6757
  const bond = await this.getValidatorBond(props.bondType, props.name, props.voteAccount);
6651
6758
  if (!bond) {
6652
6759
  instructions.push(await this.buildRegisterIx({
6653
6760
  bondType: props.bondType,
6654
6761
  name: props.name,
6655
6762
  voteAccount: props.voteAccount,
6656
- identity: props.identity
6763
+ identity: props.identity,
6764
+ creator: props.payer
6657
6765
  }));
6658
6766
  }
6659
- const collateralType = (await this.getBondState(bondType, name)).collateralType;
6767
+ const collateralType = (await this.getBondState(bondType, name)).bondState.collateralType;
6660
6768
  const accounts = {
6661
6769
  bondState,
6662
6770
  validatorBond,
@@ -6677,13 +6785,6 @@ var JBondClient = class _JBondClient {
6677
6785
  accounts.bondTokenAccount = splToken.getAssociatedTokenAddressSync(mint, validatorBond, true);
6678
6786
  accounts.tokenProgram = splToken.TOKEN_PROGRAM_ID;
6679
6787
  accounts.associatedTokenProgram = splToken.ASSOCIATED_TOKEN_PROGRAM_ID;
6680
- },
6681
- stakeAccount: () => {
6682
- if (!collateral.stakeAccount) {
6683
- throw new Error("Missing stakeAccount for stake collateral");
6684
- }
6685
- accounts.stakeAccount = collateral.stakeAccount;
6686
- accounts.stakeProgram = web3_js.StakeProgram.programId;
6687
6788
  }
6688
6789
  });
6689
6790
  instructions.push(
@@ -6700,7 +6801,7 @@ var JBondClient = class _JBondClient {
6700
6801
  if (!payer || !destination) {
6701
6802
  throw new Error("Missing payer/destination");
6702
6803
  }
6703
- const collateralType = (await this.getBondState(bondType, name)).collateralType;
6804
+ const collateralType = (await this.getBondState(bondType, name)).bondState.collateralType;
6704
6805
  const accounts = {
6705
6806
  bondState,
6706
6807
  validatorBond,
@@ -6720,27 +6821,20 @@ var JBondClient = class _JBondClient {
6720
6821
  accounts.destinationTokenAccount = splToken.getAssociatedTokenAddressSync(mint, destination, true);
6721
6822
  accounts.bondTokenAccount = splToken.getAssociatedTokenAddressSync(mint, validatorBond, true);
6722
6823
  accounts.tokenProgram = splToken.TOKEN_PROGRAM_ID;
6723
- },
6724
- stakeAccount: () => {
6725
- if (!withdraw.stakeAccount) {
6726
- throw new Error("Missing stakeAccount for stake collateral");
6727
- }
6728
- accounts.stakeAccount = withdraw.stakeAccount;
6729
- accounts.stakeProgram = web3_js.StakeProgram.programId;
6730
6824
  }
6731
6825
  });
6732
6826
  return this.program.methods.bondWithdraw(this.lamports(withdraw.amount)).accountsPartial(accounts).instruction();
6733
6827
  }
6734
6828
  async buildClaimIx(props) {
6735
- const { claim, bondType, name } = props;
6829
+ const { bondType, name } = props;
6736
6830
  const [bondState] = this.pda.bondState(bondType, name);
6737
6831
  const [validatorBond] = this.pda.validatorBond(bondType, name, props.voteAccount);
6738
- const reserve = props.reserve ?? (await this.getBondState(bondType, name)).reserve;
6832
+ const reserve = props.reserve ?? (await this.getBondState(bondType, name)).bondState.reserve;
6739
6833
  const authority = props.authority ?? this.program.provider.wallet?.publicKey;
6740
6834
  if (!reserve) {
6741
6835
  throw new Error("Reserve not set");
6742
6836
  }
6743
- const collateralType = (await this.getBondState(bondType, name)).collateralType;
6837
+ const collateralType = (await this.getBondState(bondType, name)).bondState.collateralType;
6744
6838
  const accounts = {
6745
6839
  bondState,
6746
6840
  validatorBond,
@@ -6761,13 +6855,6 @@ var JBondClient = class _JBondClient {
6761
6855
  accounts.bondTokenAccount = splToken.getAssociatedTokenAddressSync(mint, validatorBond, true);
6762
6856
  accounts.reserveTokenAccount = splToken.getAssociatedTokenAddressSync(mint, reserve, true);
6763
6857
  accounts.tokenProgram = splToken.TOKEN_PROGRAM_ID;
6764
- },
6765
- stakeAccount: () => {
6766
- if (!claim.stakeAccount) {
6767
- throw new Error("Missing stakeAccount for stake collateral");
6768
- }
6769
- accounts.stakeAccount = claim.stakeAccount;
6770
- accounts.stakeProgram = web3_js.StakeProgram.programId;
6771
6858
  }
6772
6859
  });
6773
6860
  return this.program.methods.bondClaim(this.lamports(props.claim.amount)).accountsPartial(
@@ -6782,8 +6869,34 @@ var JBondClient = class _JBondClient {
6782
6869
  newWithdrawAuthority: props.newWithdrawAuthority ?? null
6783
6870
  }).instruction();
6784
6871
  }
6785
- async buildBondFinishIx(_props) {
6786
- throw new Error("Crowdfunding bond currently does not support finish operation");
6872
+ async buildBondFinishIx(props) {
6873
+ const [bondState] = this.pda.bondState(props.bondType, props.name);
6874
+ return this.program.methods.sessionFinish().accountsPartial({
6875
+ bondState,
6876
+ authority: this.program.provider.wallet?.publicKey
6877
+ }).instruction();
6878
+ }
6879
+ async migrateBond(props) {
6880
+ const ix = await this.buildBondMigrateIx(props);
6881
+ return this.provider.sendAndConfirm?.(new web3_js.Transaction().add(ix));
6882
+ }
6883
+ async buildBondMigrateIx(props) {
6884
+ const [bondState] = this.pda.bondState(props.bondType, props.name);
6885
+ const [legacyValidatorBond] = web3_js.PublicKey.findProgramAddressSync(
6886
+ [
6887
+ Buffer.from("validator_bond"),
6888
+ new web3_js.PublicKey(props.voteAccount).toBuffer()
6889
+ ],
6890
+ this.programId
6891
+ );
6892
+ const [validatorBond] = this.pda.validatorBond(props.bondType, props.name, props.voteAccount);
6893
+ return this.program.methods.migrateBond().accountsPartial({
6894
+ bondState,
6895
+ legacyValidatorBond,
6896
+ legacyVoteAccount: new web3_js.PublicKey(props.voteAccount),
6897
+ validatorBond,
6898
+ creator: this.program.provider.wallet?.publicKey
6899
+ }).instruction();
6787
6900
  }
6788
6901
  async buildBondStartIx(props) {
6789
6902
  const [bondState] = this.pda.bondState(props.bondType, props.name);
@@ -6799,38 +6912,47 @@ var JBondClient = class _JBondClient {
6799
6912
  const [globalState] = this.pda.globalState();
6800
6913
  return await this.program.account.globalState.fetch(globalState);
6801
6914
  }
6802
- async getBondState(bondType, bondName) {
6803
- const [bondState] = this.pda.bondState(bondType, bondName);
6804
- return await this.program.account.bondState.fetch(bondState);
6915
+ /**
6916
+ * Fetch bond state with stats
6917
+ * @param bondType - Type of the bond
6918
+ * @param bondName - Name of the bond
6919
+ * @param withStats
6920
+ */
6921
+ async getBondState(bondType, bondName, withStats = false) {
6922
+ const bondState = await this.program.account.bondState.fetch(this.pda.bondState(bondType, bondName)[0]);
6923
+ return {
6924
+ bondState,
6925
+ stateStats: withStats ? await this.getBondStateStats(bondState) : null
6926
+ };
6805
6927
  }
6806
6928
  /**
6807
6929
  * Get all bond states with total collected collateral
6808
6930
  */
6809
- async getAllBondStates(bondType) {
6931
+ async getAllBondStates(bondType, sessionStatus) {
6810
6932
  const bondStates = [];
6811
6933
  const bondStateAccounts = await this.program.account.bondState.all();
6812
- for (const { account: state } of bondStateAccounts) {
6934
+ for (const { publicKey, account: state } of bondStateAccounts) {
6813
6935
  if (!sameVariant(state.bondType, bondType)) {
6814
6936
  continue;
6815
6937
  }
6816
- const validatorBonds = await this.getValidatorBondsByState(state.bondType, state.name);
6817
- const balances = await Promise.all(
6818
- validatorBonds.map(
6819
- (vb) => this.getValidatorBondBalance(state.bondType, state.name, vb.voteAccount).then((v) => v ?? 0)
6820
- )
6938
+ if (sessionStatus !== void 0 && this.getBondStateSessionStatus(state) !== sessionStatus) {
6939
+ continue;
6940
+ }
6941
+ const bondStateStats = await this.getBondStateStats(state);
6942
+ bondStates.push(
6943
+ {
6944
+ publicKey,
6945
+ bondState: state,
6946
+ stateStats: bondStateStats
6947
+ }
6821
6948
  );
6822
- const bondStateStats = {
6823
- totalCollected: balances.reduce((sum, v) => sum + v, 0),
6824
- status: await this.getBondStateSessionStatus(state)
6825
- };
6826
- bondStates.push([state, bondStateStats]);
6827
6949
  }
6828
6950
  return bondStates;
6829
6951
  }
6830
6952
  /**
6831
6953
  * Get session status for bond state
6832
6954
  */
6833
- async getBondStateSessionStatus(bondState) {
6955
+ getBondStateSessionStatus(bondState) {
6834
6956
  const now = Math.floor(Date.now() / 1e3);
6835
6957
  if (bondState.sessionFinishTs.toNumber() > now) {
6836
6958
  return 0 /* Live */;
@@ -6838,7 +6960,9 @@ var JBondClient = class _JBondClient {
6838
6960
  return 1 /* Finished */;
6839
6961
  }
6840
6962
  }
6841
- /** Get all validator bonds for a given bond state */
6963
+ /**
6964
+ * Get all validator bonds for a given bond state
6965
+ */
6842
6966
  async getValidatorBondsByState(bondType, bondName) {
6843
6967
  const validatorBonds = [];
6844
6968
  const bondStatePda = this.pda.bondState(bondType, bondName)[0];
@@ -6857,9 +6981,6 @@ var JBondClient = class _JBondClient {
6857
6981
  }
6858
6982
  /**
6859
6983
  * Fetch validator bond data or null if not found
6860
- * @param bondType
6861
- * @param bondName
6862
- * @param vote
6863
6984
  */
6864
6985
  async getValidatorBond(bondType, bondName, vote) {
6865
6986
  const [address] = this.pda.validatorBond(bondType, bondName, new web3_js.PublicKey(vote));
@@ -6874,7 +6995,7 @@ var JBondClient = class _JBondClient {
6874
6995
  */
6875
6996
  async getBondCollateralType(bondType, bondName) {
6876
6997
  const bondState = await this.getBondState(bondType, bondName);
6877
- return bondState.collateralType;
6998
+ return bondState.bondState.collateralType;
6878
6999
  }
6879
7000
  /**
6880
7001
  * Get validator bond account balance (in SOL)
@@ -6886,7 +7007,7 @@ var JBondClient = class _JBondClient {
6886
7007
  async getValidatorBondBalance(bondType, bondName, vote) {
6887
7008
  const [address] = this.pda.validatorBond(bondType, bondName, new web3_js.PublicKey(vote));
6888
7009
  const bondStateData = await this.getBondState(bondType, bondName);
6889
- const bondStateCollateralType = bondStateData.collateralType;
7010
+ const bondStateCollateralType = bondStateData.bondState.collateralType;
6890
7011
  return await matchVariant(bondStateCollateralType, {
6891
7012
  native: async () => {
6892
7013
  const accountInfo = await this.connection.getAccountInfo(address).catch(() => null);
@@ -6901,22 +7022,267 @@ var JBondClient = class _JBondClient {
6901
7022
  const tokenAccount = splToken.getAssociatedTokenAddressSync(mint, address, true);
6902
7023
  try {
6903
7024
  const balance = await this.connection.getTokenAccountBalance(tokenAccount);
6904
- return Number(balance.value.uiAmount ?? 0);
7025
+ return Number(balance.value.uiAmount ?? 0) * web3_js.LAMPORTS_PER_SOL;
6905
7026
  } catch {
6906
7027
  return 0;
6907
7028
  }
7029
+ }
7030
+ });
7031
+ }
7032
+ /**
7033
+ * Get total collected collateral for a bond state
7034
+ */
7035
+ async getBondStateTotalCollected(bondType, bondName, votes) {
7036
+ const bondStateData = await this.getBondState(bondType, bondName);
7037
+ const bondStateCollateralType = bondStateData.bondState.collateralType;
7038
+ const chunk = (arr, n = 100) => {
7039
+ const res = [];
7040
+ for (let i = 0; i < arr.length; i += n) {
7041
+ res.push(arr.slice(i, i + n));
7042
+ }
7043
+ return res;
7044
+ };
7045
+ return await matchVariant(bondStateCollateralType, {
7046
+ native: async () => {
7047
+ const addresses = votes.map((vote) => {
7048
+ const [address] = this.pda.validatorBond(bondType, bondName, new web3_js.PublicKey(vote));
7049
+ return address;
7050
+ });
7051
+ const accountInfos = await this.connection.getMultipleAccountsInfo(addresses);
7052
+ const balances = await Promise.all(
7053
+ accountInfos.map(async (accountInfo) => {
7054
+ if (!accountInfo) {
7055
+ return 0;
7056
+ }
7057
+ const { lamports } = accountInfo;
7058
+ return lamports;
7059
+ })
7060
+ );
7061
+ return balances.reduce((sum, v) => sum + v, 0);
6908
7062
  },
6909
- stakeAccount: async () => {
6910
- const accountInfo = await this.connection.getAccountInfo(address).catch(() => null);
6911
- if (!accountInfo) {
7063
+ token: async (mint) => {
7064
+ const tokenAccounts = votes.map((vote) => {
7065
+ const [validatorBondAddress] = this.pda.validatorBond(bondType, bondName, new web3_js.PublicKey(vote));
7066
+ return splToken.getAssociatedTokenAddressSync(mint, validatorBondAddress, true);
7067
+ });
7068
+ if (tokenAccounts.length === 0) {
6912
7069
  return 0;
6913
7070
  }
6914
- const { data, lamports } = accountInfo;
6915
- const rentExempt = await this.connection.getMinimumBalanceForRentExemption(data.length);
6916
- return Math.max(0, lamports - rentExempt);
7071
+ let total = 0n;
7072
+ for (const part of chunk(tokenAccounts, 100)) {
7073
+ const infos = await this.connection.getMultipleAccountsInfo(part).catch(() => []);
7074
+ for (let i = 0; i < infos.length; i++) {
7075
+ const info = infos[i];
7076
+ if (!info) {
7077
+ continue;
7078
+ }
7079
+ if (info.data.length !== splToken.ACCOUNT_SIZE) {
7080
+ continue;
7081
+ }
7082
+ try {
7083
+ const acc = splToken.AccountLayout.decode(info.data);
7084
+ const raw = BigInt(acc.amount.toString());
7085
+ total += raw;
7086
+ } catch {
7087
+ }
7088
+ }
7089
+ }
7090
+ const asNumber = Number(total);
7091
+ return Number.isFinite(asNumber) ? asNumber : Number.MAX_SAFE_INTEGER;
6917
7092
  }
6918
7093
  });
6919
7094
  }
7095
+ /**
7096
+ * Get transaction history for a specific validator bond account
7097
+ */
7098
+ async getHistory(bondType, bondName, vote, options) {
7099
+ const [legacyValidatorBondAccount] = web3_js.PublicKey.findProgramAddressSync(
7100
+ [
7101
+ Buffer.from("validator_bond" /* ValidatorBond */),
7102
+ new web3_js.PublicKey(vote).toBuffer()
7103
+ ],
7104
+ this.programId
7105
+ );
7106
+ const validatorBond = this.pda.validatorBond(bondType, bondName, vote);
7107
+ const legacySignatures = (await this.connection.getSignaturesForAddress(
7108
+ legacyValidatorBondAccount,
7109
+ {
7110
+ limit: options?.limit || 1e3,
7111
+ before: options?.before,
7112
+ until: options?.until
7113
+ },
7114
+ "confirmed"
7115
+ )).filter((sig) => !sig.err);
7116
+ const newSignatures = (await this.connection.getSignaturesForAddress(
7117
+ validatorBond[0],
7118
+ {
7119
+ limit: options?.limit || 1e3,
7120
+ before: options?.before,
7121
+ until: options?.until
7122
+ },
7123
+ "confirmed"
7124
+ )).filter((sig) => !sig.err);
7125
+ const signatureStrings = legacySignatures.map((sig) => sig.signature);
7126
+ signatureStrings.push(...newSignatures.map((sig) => sig.signature));
7127
+ const signatures = [...legacySignatures, ...newSignatures];
7128
+ const BATCH_SIZE = 100;
7129
+ const allTransactions = [];
7130
+ for (let i = 0; i < signatureStrings.length; i += BATCH_SIZE) {
7131
+ const batch = signatureStrings.slice(i, i + BATCH_SIZE);
7132
+ const transactions = await this.connection.getParsedTransactions(
7133
+ batch,
7134
+ {
7135
+ maxSupportedTransactionVersion: 0,
7136
+ commitment: "confirmed"
7137
+ }
7138
+ );
7139
+ allTransactions.push(...transactions);
7140
+ }
7141
+ const cluster = options?.cluster || "mainnet-beta";
7142
+ const history = [];
7143
+ for (const [idx, tx] of allTransactions.entries()) {
7144
+ const sigInfo = signatures[idx];
7145
+ if (!tx || !tx.meta || tx.meta.err !== null) {
7146
+ continue;
7147
+ }
7148
+ try {
7149
+ const slot = tx.slot || 0;
7150
+ const instructions = tx.transaction.message.instructions;
7151
+ for (const instruction of instructions) {
7152
+ if ("programId" in instruction && instruction.programId.equals(this.options.programId ?? this.program.programId)) {
7153
+ const ixData = instruction;
7154
+ if ("parsed" in ixData && ixData.parsed) {
7155
+ continue;
7156
+ }
7157
+ const data = ixData.data;
7158
+ if (!data) {
7159
+ continue;
7160
+ }
7161
+ let type = null;
7162
+ let amount = 0;
7163
+ try {
7164
+ const dataBuffer = bytes.bs58.decode(data);
7165
+ if (dataBuffer.length >= 8) {
7166
+ const discriminator = dataBuffer.subarray(0, 8);
7167
+ const legacyRegisterDiscriminator = this.getInstructionDiscriminator("register");
7168
+ const legacyTopUpDiscriminator = this.getInstructionDiscriminator("topUp");
7169
+ const legacyClaimDiscriminator = this.getInstructionDiscriminator("claim");
7170
+ const legacyWithdrawDiscriminator = this.getInstructionDiscriminator("withdraw");
7171
+ const bondRegisterDiscriminator = this.getInstructionDiscriminator("bondRegister");
7172
+ const bondTopUpDiscriminator = this.getInstructionDiscriminator("bondTopUp");
7173
+ const bondClaimDiscriminator = this.getInstructionDiscriminator("bondClaim");
7174
+ const bondWithdrawDiscriminator = this.getInstructionDiscriminator("bondWithdraw");
7175
+ console.log("Discriminator:", Buffer.from(discriminator).toString("hex"));
7176
+ if (Buffer.from(discriminator).equals(Buffer.from(legacyRegisterDiscriminator)) || Buffer.from(discriminator).equals(Buffer.from(bondRegisterDiscriminator))) {
7177
+ type = "deposit" /* Deposit */;
7178
+ if (dataBuffer.length >= 16 && Buffer.from(discriminator).equals(Buffer.from(legacyRegisterDiscriminator))) {
7179
+ const amountBytes = dataBuffer.subarray(8, 16);
7180
+ const amountBN = new import_bn2.BN(amountBytes, "le");
7181
+ amount = amountBN.toNumber() / web3_js.LAMPORTS_PER_SOL;
7182
+ }
7183
+ } else if (dataBuffer.length >= 16) {
7184
+ const amountBytes = dataBuffer.subarray(8, 16);
7185
+ const amountBN = new import_bn2.BN(amountBytes, "le");
7186
+ amount = amountBN.toNumber() / web3_js.LAMPORTS_PER_SOL;
7187
+ if (Buffer.from(discriminator).equals(Buffer.from(legacyTopUpDiscriminator)) || Buffer.from(discriminator).equals(Buffer.from(bondTopUpDiscriminator))) {
7188
+ type = "deposit" /* Deposit */;
7189
+ } else if (Buffer.from(discriminator).equals(Buffer.from(legacyClaimDiscriminator)) || Buffer.from(discriminator).equals(Buffer.from(bondClaimDiscriminator))) {
7190
+ type = "compensation" /* Compensation */;
7191
+ } else if (Buffer.from(discriminator).equals(Buffer.from(legacyWithdrawDiscriminator)) || Buffer.from(discriminator).equals(Buffer.from(bondWithdrawDiscriminator))) {
7192
+ type = "withdrawal" /* Withdrawal */;
7193
+ }
7194
+ }
7195
+ }
7196
+ } catch (e) {
7197
+ console.warn("Failed to decode instruction data:", e);
7198
+ }
7199
+ if (type && (amount > 0 || type === "deposit" /* Deposit */)) {
7200
+ history.push({
7201
+ signature: sigInfo.signature,
7202
+ slot,
7203
+ epoch: slotToEpoch(slot, cluster),
7204
+ type,
7205
+ amount
7206
+ });
7207
+ }
7208
+ }
7209
+ }
7210
+ } catch (error) {
7211
+ console.error(`Error processing transaction ${sigInfo.signature}:`, error);
7212
+ }
7213
+ }
7214
+ return history.toSorted((a, b) => b.slot - a.slot);
7215
+ }
7216
+ /**
7217
+ * Get full transaction history by paginating through results
7218
+ * @param bondType
7219
+ * @param bondName
7220
+ * @param voteAccount
7221
+ * @param pageSize
7222
+ */
7223
+ async getFullHistory(bondType, bondName, voteAccount, pageSize = 100) {
7224
+ const allHistory = [];
7225
+ let before;
7226
+ while (true) {
7227
+ const batch = await this.getHistory(bondType, bondName, voteAccount, {
7228
+ limit: pageSize,
7229
+ before
7230
+ });
7231
+ if (batch.length === 0) {
7232
+ break;
7233
+ }
7234
+ allHistory.push(...batch);
7235
+ before = batch.at(-1)?.signature;
7236
+ if (batch.length < pageSize) {
7237
+ break;
7238
+ }
7239
+ }
7240
+ return allHistory;
7241
+ }
7242
+ /**
7243
+ * Get instruction discriminator from IDL
7244
+ * @param instructionName
7245
+ * @private
7246
+ */
7247
+ getInstructionDiscriminator(instructionName) {
7248
+ const legacyDiscriminators = {
7249
+ register: [211, 124, 67, 15, 211, 194, 178, 240],
7250
+ topUp: [181, 157, 89, 67, 143, 182, 52, 72],
7251
+ claim: [62, 198, 214, 193, 213, 159, 108, 210],
7252
+ withdraw: [183, 18, 70, 156, 148, 109, 161, 34]
7253
+ };
7254
+ if (legacyDiscriminators[instructionName]) {
7255
+ return new Uint8Array(legacyDiscriminators[instructionName]);
7256
+ }
7257
+ if (instructionName.startsWith("bond")) {
7258
+ const instruction = this.program.idl.instructions.find((ix) => ix.name === instructionName);
7259
+ if (!instruction) {
7260
+ throw new Error(`Instruction ${instructionName} not found in IDL`);
7261
+ }
7262
+ if (!instruction.discriminator || !Array.isArray(instruction.discriminator)) {
7263
+ throw new Error(`Discriminator not found for instruction ${instructionName}`);
7264
+ }
7265
+ return new Uint8Array(instruction.discriminator);
7266
+ }
7267
+ throw new Error(`Unknown instruction: ${instructionName}`);
7268
+ }
7269
+ /**
7270
+ * Get bond state stats
7271
+ * @param state
7272
+ * @private
7273
+ */
7274
+ async getBondStateStats(state) {
7275
+ const validatorBonds = await this.getValidatorBondsByState(state.bondType, state.name);
7276
+ const totalCollected = await this.getBondStateTotalCollected(
7277
+ state.bondType,
7278
+ state.name,
7279
+ validatorBonds.map((vb) => vb.voteAccount)
7280
+ );
7281
+ return {
7282
+ totalCollected,
7283
+ status: this.getBondStateSessionStatus(state)
7284
+ };
7285
+ }
6920
7286
  /**
6921
7287
  * Load stake pool account and cache it if not already cached
6922
7288
  * @private
@@ -6963,6 +7329,7 @@ buffer/index.js:
6963
7329
  */
6964
7330
 
6965
7331
  exports.BondClientEnv = BondClientEnv;
7332
+ exports.BondStateStatusVariant = BondStateStatusVariant;
6966
7333
  exports.BondTransactionType = BondTransactionType;
6967
7334
  exports.BondTypeVariant = BondTypeVariant;
6968
7335
  exports.ENV_PROGRAM_ID = ENV_PROGRAM_ID;