gemworks / gem-farm

Configurable staking for NFT Projects on Solana
https://gemfarm.gg/
MIT License
340 stars 252 forks source link

Add Single Stake and Unstake Functionality #51

Open studentofcoding opened 2 years ago

studentofcoding commented 2 years ago

With the standard of Staking individually / NFT, please add this functionality to cover the universal staking function

Thanks @ilmoi !

CMHayden commented 2 years ago

The functionality exists in this repo already. You simply need to change the calls to rust to return instructions and then send all the transactions at the same time

UPLukeet commented 2 years ago

Hey, I wanted to leave this here to help people struggling with this issue. Here's an example of creating a transaction instruction for un-staking that wraps un-staking, ends cooldown and retrieves rewards into one transaction.

  async unstakeNfts(
    bank: any,
    vault: PublicKey,
    farm: PublicKey,
    rewardAMint: PublicKey,
    rewardBMint: PublicKey
  ) {
    const trxInstructions = [];

    const [farmer, farmerBump] = await findFarmerPDA(
      farm,
      this.wallet.publicKey
    );
    const [farmAuth, farmAuthBump] = await findFarmAuthorityPDA(farm);

    const [farmTreasury, farmTreasuryBump] = await findFarmTreasuryPDA(farm);

    const [potA, potABump] = await findRewardsPotPDA(farm, rewardAMint);
    const [potB, potBBump] = await findRewardsPotPDA(farm, rewardBMint);
    const rewardADestination = await this.findATA(
      rewardAMint,
      this.wallet.publicKey
    );
    const rewardBDestination = await this.findATA(
      rewardBMint,
      this.wallet.publicKey
    );

    const endStakingInst = this.farmProgram.instruction.unstake(
      farmAuthBump,
      farmTreasuryBump,
      farmerBump,
      false,
      {
        accounts: {
          farm,
          farmer,
          farmTreasury,
          identity: this.wallet.publicKey,
          bank,
          vault,
          farmAuthority: farmAuth,
          gemBank: this.bankProgram.programId,
          systemProgram: web3.SystemProgram.programId,
        },
        signers: [this.wallet.publicKey] as any,
      }
    );

    const rewardsInst = this.farmProgram.instruction.claim(
      farmAuthBump,
      farmerBump,
      potABump,
      potBBump,
      {
        accounts: {
          farm,
          farmAuthority: farmAuth,
          farmer,
          identity: this.wallet.publicKey,
          rewardAPot: potA,
          rewardAMint,
          rewardADestination,
          rewardBPot: potB,
          rewardBMint,
          rewardBDestination,
          tokenProgram: TOKEN_PROGRAM_ID,
          associatedTokenProgram: ASSOCIATED_TOKEN_PROGRAM_ID,
          systemProgram: web3.SystemProgram.programId,
          rent: web3.SYSVAR_RENT_PUBKEY,
        },
        signers: [this.wallet.publicKey] as any[],
      }
    );
    trxInstructions.push(endStakingInst);
    trxInstructions.push(endStakingInst);
    trxInstructions.push(rewardsInst);

    return new Transaction().add(...trxInstructions);
  }

The code above returns instructions all you need to do is call sendTransaction(instructions, connection, options) and you should be good to go :)

rashidkhokhar98 commented 2 years ago

hi i am using above code to buy-pass cool-down functionality but compiler shows errors and it seems that this code is written using class component. can anyone tell me in which file or where should i add this code.