gpu-compute-chain/x/colinearcore/keeper/msg_server_claim_funds.go

73 lines
2.3 KiB
Go
Raw Normal View History

package keeper
import (
"context"
"errors"
"fmt"
"math/big"
"time"
colinearmath "colinear/x/colinearcore/math"
"colinear/x/colinearcore/types"
sdk "github.com/cosmos/cosmos-sdk/types"
)
func (k msgServer) ClaimFunds(goCtx context.Context, msg *types.MsgClaimFunds) (*types.MsgClaimFundsResponse, error) {
ctx := sdk.UnwrapSDKContext(goCtx)
// check that auction exists
auction, found := k.Keeper.GetAuction(ctx, msg.AuctionId)
if !found {
return nil, fmt.Errorf("auction %s not found", msg.AuctionId)
}
// check that auction is finalized
if auction.Best == nil {
return nil, fmt.Errorf("auction %s is not finalized", msg.AuctionId)
}
// check that auction has remaining funds to pay out
if auction.Remaining == "0" {
return nil, fmt.Errorf("auction %s has no payable CLR remaining", msg.AuctionId)
}
// check that sender is the selected provider for the auction
if auction.Best.Owner != msg.Creator {
return nil, fmt.Errorf("lease reward is only claimable by selected provider (%s) (got %s)", auction.Best.Owner, msg.Creator)
}
// parse address to send to
sendTo, err := sdk.AccAddressFromBech32(auction.Best.Owner)
if err != nil {
return nil, fmt.Errorf("failed to parse address %s: %s", auction.Best.Owner, err)
}
// calculate payable amount
total := new(big.Int)
total.SetString(auction.Best.Amount, 10)
remaining := new(big.Int)
remaining.SetString(auction.Remaining, 10)
leaseBegin := time.Unix(int64(auction.LeaseStart), 0)
leaseEnd := time.Unix(int64(auction.LeaseEnd), 0)
now := ctx.BlockTime()
subAmt, err := colinearmath.CalcAmountVestableLinear(total, remaining, now, leaseBegin, leaseEnd)
if err != nil {
return nil, errors.New("unable to calculate vestable amount")
}
// pay from module to user account
coins := sdk.NewCoins(sdk.NewCoin("uclr", sdk.NewIntFromBigInt(subAmt)))
if err := k.bank.SendCoinsFromModuleToAccount(ctx, types.ModuleName, sendTo, coins); err != nil {
return nil, fmt.Errorf("failed to send %s uCLR from module %s", subAmt.String(), types.ModuleName)
}
// subtract paid amount off of remaining payout tally & commit to chain state
newRemaining := new(big.Int)
newRemaining.Sub(remaining, subAmt)
auction.Remaining = subAmt.String()
k.Keeper.SetAuction(ctx, auction)
return &types.MsgClaimFundsResponse{}, nil
}